1/***************************************************************************** 2* wanpipe_multppp.c Multi-Port PPP driver module. 3* 4* Authors: Nenad Corbic <ncorbic@sangoma.com> 5* 6* Copyright: (c) 1995-2001 Sangoma Technologies Inc. 7* 8* This program is free software; you can redistribute it and/or 9* modify it under the terms of the GNU General Public License 10* as published by the Free Software Foundation; either version 11* 2 of the License, or (at your option) any later version. 12* ============================================================================ 13* Dec 15 2000 Updated for 2.4.X kernel 14* Nov 15 2000 Fixed the SyncPPP support for kernels 2.2.16 and higher. 15* The pppstruct has changed. 16* Jul 13 2000 Using the kernel Syncppp module on top of RAW Wanpipe CHDLC 17* module. 18*****************************************************************************/ 19 20#include <linux/module.h> 21#include <linux/version.h> 22#include <linux/kernel.h> /* printk(), and other useful stuff */ 23#include <linux/stddef.h> /* offsetof(), etc. */ 24#include <linux/errno.h> /* return codes */ 25#include <linux/string.h> /* inline memset(), etc. */ 26#include <linux/slab.h> /* kmalloc(), kfree() */ 27#include <linux/wanrouter.h> /* WAN router definitions */ 28#include <linux/wanpipe.h> /* WANPIPE common user API definitions */ 29#include <linux/if_arp.h> /* ARPHRD_* defines */ 30 31#include <linux/in.h> /* sockaddr_in */ 32#include <linux/inet.h> 33#include <linux/if.h> 34#include <asm/byteorder.h> /* htons(), etc. */ 35#include <linux/sdlapci.h> 36#include <asm/io.h> 37 38#include <linux/sdla_chdlc.h> /* CHDLC firmware API definitions */ 39#include <linux/sdla_asy.h> /* CHDLC (async) API definitions */ 40 41#include <linux/if_wanpipe_common.h> /* Socket Driver common area */ 42#include <linux/if_wanpipe.h> 43 44 45#if defined(LINUX_2_1) || defined(LINUX_2_4) 46 #include <linux/inetdevice.h> 47 #include <asm/uaccess.h> 48 49#if LINUX_VERSION_CODE >= KERNEL_VERSION(2,4,3) 50 #include <net/syncppp.h> 51#else 52 #include "syncppp.h" 53#endif 54 55#else 56 #include <net/route.h> /* Adding new route entries */ 57#endif 58 59/****** Defines & Macros ****************************************************/ 60 61#ifdef _DEBUG_ 62#define STATIC 63#else 64#define STATIC static 65#endif 66 67/* reasons for enabling the timer interrupt on the adapter */ 68#define TMR_INT_ENABLED_UDP 0x01 69#define TMR_INT_ENABLED_UPDATE 0x02 70#define TMR_INT_ENABLED_CONFIG 0x04 71 72#define CHDLC_DFLT_DATA_LEN 1500 /* default MTU */ 73#define CHDLC_HDR_LEN 1 74 75#define IFF_POINTTOPOINT 0x10 76 77#define CHDLC_API 0x01 78 79#define PORT(x) (x == 0 ? "PRIMARY" : "SECONDARY" ) 80#define MAX_BH_BUFF 10 81 82#define CRC_LENGTH 2 83#define PPP_HEADER_LEN 4 84 85/******Data Structures*****************************************************/ 86 87/* This structure is placed in the private data area of the device structure. 88 * The card structure used to occupy the private area but now the following 89 * structure will incorporate the card structure along with CHDLC specific data 90 */ 91 92typedef struct chdlc_private_area 93{ 94 void *if_ptr; /* General Pointer used by SPPP */ 95 wanpipe_common_t common; 96 sdla_t *card; 97 int TracingEnabled; /* For enabling Tracing */ 98 unsigned long curr_trace_addr; /* Used for Tracing */ 99 unsigned long start_trace_addr; 100 unsigned long end_trace_addr; 101 unsigned long base_addr_trace_buffer; 102 unsigned long end_addr_trace_buffer; 103 unsigned short number_trace_elements; 104 unsigned available_buffer_space; 105 unsigned long router_start_time; 106 unsigned char route_status; 107 unsigned char route_removed; 108 unsigned long tick_counter; /* For 5s timeout counter */ 109 unsigned long router_up_time; 110 u32 IP_address; /* IP addressing */ 111 u32 IP_netmask; 112 unsigned char mc; /* Mulitcast support on/off */ 113 unsigned short udp_pkt_lgth; /* udp packet processing */ 114 char udp_pkt_src; 115 char udp_pkt_data[MAX_LGTH_UDP_MGNT_PKT]; 116 unsigned short timer_int_enabled; 117 char update_comms_stats; /* updating comms stats */ 118 119 //FIXME: add driver stats as per frame relay! 120 121} chdlc_private_area_t; 122 123/* Route Status options */ 124#define NO_ROUTE 0x00 125#define ADD_ROUTE 0x01 126#define ROUTE_ADDED 0x02 127#define REMOVE_ROUTE 0x03 128 129 130/* variable for keeping track of enabling/disabling FT1 monitor status */ 131static int rCount = 0; 132 133/* variable for tracking how many interfaces to open for WANPIPE on the 134 two ports */ 135 136extern void disable_irq(unsigned int); 137extern void enable_irq(unsigned int); 138 139/****** Function Prototypes *************************************************/ 140/* WAN link driver entry points. These are called by the WAN router module. */ 141static int update (wan_device_t* wandev); 142static int new_if (wan_device_t* wandev, netdevice_t* dev, 143 wanif_conf_t* conf); 144static int del_if (wan_device_t* wandev, netdevice_t* dev); 145 146/* Network device interface */ 147static int if_init (netdevice_t* dev); 148static int if_open (netdevice_t* dev); 149static int if_close (netdevice_t* dev); 150static int if_send (struct sk_buff* skb, netdevice_t* dev); 151#if defined(LINUX_2_1) || defined(LINUX_2_4) 152static struct net_device_stats* if_stats (netdevice_t* dev); 153#else 154static struct enet_statistics* if_stats (netdevice_t* dev); 155#endif 156 157#ifdef LINUX_2_4 158static void if_tx_timeout (netdevice_t *dev); 159#endif 160 161/* CHDLC Firmware interface functions */ 162static int chdlc_configure (sdla_t* card, void* data); 163static int chdlc_comm_enable (sdla_t* card); 164static int chdlc_comm_disable (sdla_t* card); 165static int chdlc_read_version (sdla_t* card, char* str); 166static int chdlc_set_intr_mode (sdla_t* card, unsigned mode); 167static int chdlc_send (sdla_t* card, void* data, unsigned len); 168static int chdlc_read_comm_err_stats (sdla_t* card); 169static int chdlc_read_op_stats (sdla_t* card); 170static int config_chdlc (sdla_t *card); 171 172 173/* Miscellaneous CHDLC Functions */ 174static int set_chdlc_config (sdla_t* card); 175static void init_chdlc_tx_rx_buff( sdla_t* card, netdevice_t *dev ); 176static int chdlc_error (sdla_t *card, int err, CHDLC_MAILBOX_STRUCT *mb); 177static int process_chdlc_exception(sdla_t *card); 178static int process_global_exception(sdla_t *card); 179static int update_comms_stats(sdla_t* card, 180 chdlc_private_area_t* chdlc_priv_area); 181static void port_set_state (sdla_t *card, int); 182 183/* Interrupt handlers */ 184static void wsppp_isr (sdla_t* card); 185static void rx_intr (sdla_t* card); 186static void timer_intr(sdla_t *); 187 188/* Miscellaneous functions */ 189static int reply_udp( unsigned char *data, unsigned int mbox_len ); 190static int intr_test( sdla_t* card); 191static int udp_pkt_type( struct sk_buff *skb , sdla_t* card); 192static int store_udp_mgmt_pkt(char udp_pkt_src, sdla_t* card, 193 struct sk_buff *skb, netdevice_t* dev, 194 chdlc_private_area_t* chdlc_priv_area); 195static int process_udp_mgmt_pkt(sdla_t* card, netdevice_t* dev, 196 chdlc_private_area_t* chdlc_priv_area); 197static unsigned short calc_checksum (char *, int); 198static void s508_lock (sdla_t *card, unsigned long *smp_flags); 199static void s508_unlock (sdla_t *card, unsigned long *smp_flags); 200static void send_ppp_term_request (netdevice_t*); 201 202 203static int Intr_test_counter; 204/****** Public Functions ****************************************************/ 205 206/*============================================================================ 207 * Cisco HDLC protocol initialization routine. 208 * 209 * This routine is called by the main WANPIPE module during setup. At this 210 * point adapter is completely initialized and firmware is running. 211 * o read firmware version (to make sure it's alive) 212 * o configure adapter 213 * o initialize protocol-specific fields of the adapter data space. 214 * 215 * Return: 0 o.k. 216 * < 0 failure. 217 */ 218int wsppp_init (sdla_t* card, wandev_conf_t* conf) 219{ 220 unsigned char port_num; 221 int err; 222 unsigned long max_permitted_baud = 0; 223 SHARED_MEMORY_INFO_STRUCT *flags; 224 225 union 226 { 227 char str[80]; 228 } u; 229 volatile CHDLC_MAILBOX_STRUCT* mb; 230 CHDLC_MAILBOX_STRUCT* mb1; 231 unsigned long timeout; 232 233 /* Verify configuration ID */ 234 if (conf->config_id != WANCONFIG_MPPP) { 235 printk(KERN_INFO "%s: invalid configuration ID %u!\n", 236 card->devname, conf->config_id); 237 return -EINVAL; 238 } 239 240 /* Find out which Port to use */ 241 if ((conf->comm_port == WANOPT_PRI) || (conf->comm_port == WANOPT_SEC)){ 242 if (card->next){ 243 244 if (conf->comm_port != card->next->u.c.comm_port){ 245 card->u.c.comm_port = conf->comm_port; 246 }else{ 247 printk(KERN_ERR "%s: ERROR - %s port used!\n", 248 card->wandev.name, PORT(conf->comm_port)); 249 return -EINVAL; 250 } 251 }else{ 252 card->u.c.comm_port = conf->comm_port; 253 } 254 }else{ 255 printk(KERN_ERR "%s: ERROR - Invalid Port Selected!\n", 256 card->wandev.name); 257 return -EINVAL; 258 } 259 260 261 /* Initialize protocol-specific fields */ 262 if(card->hw.type != SDLA_S514){ 263 264 if (card->u.c.comm_port == WANOPT_PRI){ 265 card->mbox = (void *) card->hw.dpmbase; 266 }else{ 267 card->mbox = (void *) card->hw.dpmbase + 268 SEC_BASE_ADDR_MB_STRUCT - PRI_BASE_ADDR_MB_STRUCT; 269 } 270 }else{ 271 /* for a S514 adapter, set a pointer to the actual mailbox in the */ 272 /* allocated virtual memory area */ 273 if (card->u.c.comm_port == WANOPT_PRI){ 274 card->mbox = (void *) card->hw.dpmbase + PRI_BASE_ADDR_MB_STRUCT; 275 }else{ 276 card->mbox = (void *) card->hw.dpmbase + SEC_BASE_ADDR_MB_STRUCT; 277 } 278 } 279 280 mb = mb1 = card->mbox; 281 282 if (!card->configured){ 283 284 /* The board will place an 'I' in the return code to indicate that it is 285 ready to accept commands. We expect this to be completed in less 286 than 1 second. */ 287 288 timeout = jiffies; 289 while (mb->return_code != 'I') /* Wait 1s for board to initialize */ 290 if ((jiffies - timeout) > 1*HZ) break; 291 292 if (mb->return_code != 'I') { 293 printk(KERN_INFO 294 "%s: Initialization not completed by adapter\n", 295 card->devname); 296 printk(KERN_INFO "Please contact Sangoma representative.\n"); 297 return -EIO; 298 } 299 } 300 301 /* Read firmware version. Note that when adapter initializes, it 302 * clears the mailbox, so it may appear that the first command was 303 * executed successfully when in fact it was merely erased. To work 304 * around this, we execute the first command twice. 305 */ 306 307 if (chdlc_read_version(card, u.str)) 308 return -EIO; 309 310 printk(KERN_INFO "%s: Running Raw CHDLC firmware v%s\n" 311 "%s: for Multi-Port PPP protocol.\n", 312 card->devname,u.str,card->devname); 313 314 card->isr = &wsppp_isr; 315 card->poll = NULL; 316 card->exec = NULL; 317 card->wandev.update = &update; 318 card->wandev.new_if = &new_if; 319 card->wandev.del_if = &del_if; 320 card->wandev.udp_port = conf->udp_port; 321 322 card->wandev.new_if_cnt = 0; 323 324 /* reset the number of times the 'update()' proc has been called */ 325 card->u.c.update_call_count = 0; 326 327 card->wandev.ttl = conf->ttl; 328 card->wandev.interface = conf->interface; 329 330 if ((card->u.c.comm_port == WANOPT_SEC && conf->interface == WANOPT_V35)&& 331 card->hw.type != SDLA_S514){ 332 printk(KERN_INFO "%s: ERROR - V35 Interface not supported on S508 %s port \n", 333 card->devname, PORT(card->u.c.comm_port)); 334 return -EIO; 335 } 336 337 338 card->wandev.clocking = conf->clocking; 339 340 port_num = card->u.c.comm_port; 341 342 /* Setup Port Bps */ 343 344 if(card->wandev.clocking) { 345 if((port_num == WANOPT_PRI) || card->u.c.receive_only) { 346 /* For Primary Port 0 */ 347 max_permitted_baud = 348 (card->hw.type == SDLA_S514) ? 349 PRI_MAX_BAUD_RATE_S514 : 350 PRI_MAX_BAUD_RATE_S508; 351 } 352 else if(port_num == WANOPT_SEC) { 353 /* For Secondary Port 1 */ 354 max_permitted_baud = 355 (card->hw.type == SDLA_S514) ? 356 SEC_MAX_BAUD_RATE_S514 : 357 SEC_MAX_BAUD_RATE_S508; 358 } 359 360 if(conf->bps > max_permitted_baud) { 361 conf->bps = max_permitted_baud; 362 printk(KERN_INFO "%s: Baud too high!\n", 363 card->wandev.name); 364 printk(KERN_INFO "%s: Baud rate set to %lu bps\n", 365 card->wandev.name, max_permitted_baud); 366 } 367 368 card->wandev.bps = conf->bps; 369 }else{ 370 card->wandev.bps = 0; 371 } 372 373 /* Setup the Port MTU */ 374 if((port_num == WANOPT_PRI) || card->u.c.receive_only) { 375 376 /* For Primary Port 0 */ 377 card->wandev.mtu = 378 (conf->mtu >= MIN_LGTH_CHDLC_DATA_CFG) ? 379 min_t(unsigned int, conf->mtu, PRI_MAX_NO_DATA_BYTES_IN_FRAME) : 380 CHDLC_DFLT_DATA_LEN; 381 } else if(port_num == WANOPT_SEC) { 382 /* For Secondary Port 1 */ 383 card->wandev.mtu = 384 (conf->mtu >= MIN_LGTH_CHDLC_DATA_CFG) ? 385 min_t(unsigned int, conf->mtu, SEC_MAX_NO_DATA_BYTES_IN_FRAME) : 386 CHDLC_DFLT_DATA_LEN; 387 } 388 389 /* Add on a PPP Header */ 390 card->wandev.mtu += PPP_HEADER_LEN; 391 392 /* Set up the interrupt status area */ 393 /* Read the CHDLC Configuration and obtain: 394 * Ptr to shared memory infor struct 395 * Use this pointer to calculate the value of card->u.c.flags ! 396 */ 397 mb1->buffer_length = 0; 398 mb1->command = READ_CHDLC_CONFIGURATION; 399 err = sdla_exec(mb1) ? mb1->return_code : CMD_TIMEOUT; 400 if(err != COMMAND_OK) { 401 clear_bit(1, (void*)&card->wandev.critical); 402 403 if(card->hw.type != SDLA_S514) 404 enable_irq(card->hw.irq); 405 406 chdlc_error(card, err, mb1); 407 return -EIO; 408 } 409 410 if(card->hw.type == SDLA_S514){ 411 card->u.c.flags = (void *)(card->hw.dpmbase + 412 (((CHDLC_CONFIGURATION_STRUCT *)mb1->data)-> 413 ptr_shared_mem_info_struct)); 414 }else{ 415 card->u.c.flags = (void *)(card->hw.dpmbase + 416 (((CHDLC_CONFIGURATION_STRUCT *)mb1->data)-> 417 ptr_shared_mem_info_struct % SDLA_WINDOWSIZE)); 418 } 419 420 flags = card->u.c.flags; 421 422 /* This is for the ports link state */ 423 card->wandev.state = WAN_DUALPORT; 424 card->u.c.state = WAN_DISCONNECTED; 425 426 427 if (!card->wandev.piggyback){ 428 err = intr_test(card); 429 430 if(err || (Intr_test_counter < MAX_INTR_TEST_COUNTER)) { 431 printk(KERN_ERR "%s: Interrupt test failed (%i)\n", 432 card->devname, Intr_test_counter); 433 printk(KERN_ERR "%s: Please choose another interrupt\n", 434 card->devname); 435 return -EIO; 436 } 437 438 printk(KERN_INFO "%s: Interrupt test passed (%i)\n", 439 card->devname, Intr_test_counter); 440 } 441 442 443 if (chdlc_set_intr_mode(card, APP_INT_ON_TIMER)){ 444 printk (KERN_INFO "%s: Failed to set interrupt triggers!\n", 445 card->devname); 446 return -EIO; 447 } 448 449 /* Mask the Timer interrupt */ 450 flags->interrupt_info_struct.interrupt_permission &= 451 ~APP_INT_ON_TIMER; 452 453 printk(KERN_INFO "\n"); 454 455 return 0; 456} 457 458/******* WAN Device Driver Entry Points *************************************/ 459 460/*============================================================================ 461 * Update device status & statistics 462 * This procedure is called when updating the PROC file system and returns 463 * various communications statistics. These statistics are accumulated from 3 464 * different locations: 465 * 1) The 'if_stats' recorded for the device. 466 * 2) Communication error statistics on the adapter. 467 * 3) CHDLC operational statistics on the adapter. 468 * The board level statistics are read during a timer interrupt. Note that we 469 * read the error and operational statistics during consecitive timer ticks so 470 * as to minimize the time that we are inside the interrupt handler. 471 * 472 */ 473static int update (wan_device_t* wandev) 474{ 475 sdla_t* card = wandev->private; 476 netdevice_t* dev; 477 volatile chdlc_private_area_t* chdlc_priv_area; 478 SHARED_MEMORY_INFO_STRUCT *flags; 479 unsigned long timeout; 480 481 /* sanity checks */ 482 if((wandev == NULL) || (wandev->private == NULL)) 483 return -EFAULT; 484 485 if(wandev->state == WAN_UNCONFIGURED) 486 return -ENODEV; 487 488 /* more sanity checks */ 489 if(!card->u.c.flags) 490 return -ENODEV; 491 492 if((dev=card->wandev.dev) == NULL) 493 return -ENODEV; 494 495 if((chdlc_priv_area=dev->priv) == NULL) 496 return -ENODEV; 497 498 flags = card->u.c.flags; 499 500 if(chdlc_priv_area->update_comms_stats){ 501 return -EAGAIN; 502 } 503 504 /* we will need 2 timer interrupts to complete the */ 505 /* reading of the statistics */ 506 chdlc_priv_area->update_comms_stats = 2; 507 flags->interrupt_info_struct.interrupt_permission |= APP_INT_ON_TIMER; 508 chdlc_priv_area->timer_int_enabled = TMR_INT_ENABLED_UPDATE; 509 510 /* wait a maximum of 1 second for the statistics to be updated */ 511 timeout = jiffies; 512 for(;;) { 513 if(chdlc_priv_area->update_comms_stats == 0) 514 break; 515 if ((jiffies - timeout) > (1 * HZ)){ 516 chdlc_priv_area->update_comms_stats = 0; 517 chdlc_priv_area->timer_int_enabled &= 518 ~TMR_INT_ENABLED_UPDATE; 519 return -EAGAIN; 520 } 521 } 522 523 return 0; 524} 525 526 527/*============================================================================ 528 * Create new logical channel. 529 * This routine is called by the router when ROUTER_IFNEW IOCTL is being 530 * handled. 531 * o parse media- and hardware-specific configuration 532 * o make sure that a new channel can be created 533 * o allocate resources, if necessary 534 * o prepare network device structure for registaration. 535 * 536 * Return: 0 o.k. 537 * < 0 failure (channel will not be created) 538 */ 539static int new_if (wan_device_t* wandev, netdevice_t* pdev, wanif_conf_t* conf) 540{ 541 542 struct ppp_device *pppdev = (struct ppp_device *)pdev; 543 netdevice_t *dev=NULL; 544 struct sppp *sp; 545 sdla_t* card = wandev->private; 546 chdlc_private_area_t* chdlc_priv_area; 547 548 if ((conf->name[0] == '\0') || (strlen(conf->name) > WAN_IFNAME_SZ)) { 549 printk(KERN_INFO "%s: invalid interface name!\n", 550 card->devname); 551 return -EINVAL; 552 } 553 554 /* allocate and initialize private data */ 555 chdlc_priv_area = kmalloc(sizeof(chdlc_private_area_t), GFP_KERNEL); 556 557 if(chdlc_priv_area == NULL) 558 return -ENOMEM; 559 560 memset(chdlc_priv_area, 0, sizeof(chdlc_private_area_t)); 561 562 chdlc_priv_area->card = card; 563 564 /* initialize data */ 565 strcpy(card->u.c.if_name, conf->name); 566 567 if(card->wandev.new_if_cnt > 0) { 568 kfree(chdlc_priv_area); 569 return -EEXIST; 570 } 571 572 card->wandev.new_if_cnt++; 573 574 chdlc_priv_area->TracingEnabled = 0; 575 576 //We don't need this any more 577 chdlc_priv_area->route_status = NO_ROUTE; 578 chdlc_priv_area->route_removed = 0; 579 580 printk(KERN_INFO "%s: Firmware running in HDLC STREAMING Mode\n", 581 wandev->name); 582 583 /* Setup wanpipe as a router (WANPIPE) or as an API */ 584 if( strcmp(conf->usedby, "WANPIPE") == 0) { 585 printk(KERN_INFO "%s: Driver running in WANPIPE mode!\n", 586 wandev->name); 587 card->u.c.usedby = WANPIPE; 588 } else { 589 printk(KERN_INFO 590 "%s: API Mode is not supported for SyncPPP!\n", 591 wandev->name); 592 kfree(chdlc_priv_area); 593 return -EINVAL; 594 } 595 596 /* Get Multicast Information */ 597 chdlc_priv_area->mc = conf->mc; 598 599 600 chdlc_priv_area->if_ptr = pppdev; 601 602 /* prepare network device data space for registration */ 603 604#ifdef LINUX_2_4 605 strcpy(dev->name,card->u.c.if_name); 606#else 607 dev->name = (char *)kmalloc(strlen(card->u.c.if_name) + 2, GFP_KERNEL); 608 if(dev->name == NULL) 609 { 610 kfree(chdlc_priv_area); 611 return -ENOMEM; 612 } 613 sprintf(dev->name, "%s", card->u.c.if_name); 614#endif 615 616 /* Attach PPP protocol layer to pppdev 617 * The sppp_attach() will initilize the dev structure 618 * and setup ppp layer protocols. 619 * All we have to do is to bind in: 620 * if_open(), if_close(), if_send() and get_stats() functions. 621 */ 622 sppp_attach(pppdev); 623#if LINUX_VERSION_CODE >= KERNEL_VERSION(2,2,16) 624 dev = pppdev->dev; 625#else 626 dev = &pppdev->dev; 627#endif 628 sp = &pppdev->sppp; 629 630 /* Enable PPP Debugging */ 631 // FIXME Fix this up somehow 632 //sp->pp_flags |= PP_DEBUG; 633 sp->pp_flags &= ~PP_CISCO; 634 635 dev->init = &if_init; 636 dev->priv = chdlc_priv_area; 637 638 return 0; 639} 640 641 642 643 644/*============================================================================ 645 * Delete logical channel. 646 */ 647static int del_if (wan_device_t* wandev, netdevice_t* dev) 648{ 649 chdlc_private_area_t *chdlc_priv_area = dev->priv; 650 sdla_t *card = chdlc_priv_area->card; 651 unsigned long smp_lock; 652 653 /* Detach the PPP layer */ 654 printk(KERN_INFO "%s: Detaching SyncPPP Module from %s\n", 655 wandev->name,dev->name); 656 657 lock_adapter_irq(&wandev->lock,&smp_lock); 658 659 sppp_detach(dev); 660 chdlc_priv_area->if_ptr=NULL; 661 662 chdlc_set_intr_mode(card, 0); 663 if (card->u.c.comm_enabled) 664 chdlc_comm_disable(card); 665 unlock_adapter_irq(&wandev->lock,&smp_lock); 666 667 port_set_state(card, WAN_DISCONNECTED); 668 669 return 0; 670} 671 672 673/****** Network Device Interface ********************************************/ 674 675/*============================================================================ 676 * Initialize Linux network interface. 677 * 678 * This routine is called only once for each interface, during Linux network 679 * interface registration. Returning anything but zero will fail interface 680 * registration. 681 */ 682static int if_init (netdevice_t* dev) 683 { 684 chdlc_private_area_t* chdlc_priv_area = dev->priv; 685 sdla_t* card = chdlc_priv_area->card; 686 wan_device_t* wandev = &card->wandev; 687#ifdef LINUX_2_0 688 int i; 689#endif 690 691 /* NOTE: Most of the dev initialization was 692 * done in sppp_attach(), called by new_if() 693 * function. All we have to do here is 694 * to link four major routines below. 695 */ 696 697 /* Initialize device driver entry points */ 698 dev->open = &if_open; 699 dev->stop = &if_close; 700 dev->hard_start_xmit = &if_send; 701 dev->get_stats = &if_stats; 702#ifdef LINUX_2_4 703 dev->tx_timeout = &if_tx_timeout; 704 dev->watchdog_timeo = TX_TIMEOUT; 705#endif 706 707 708#ifdef LINUX_2_0 709 dev->family = AF_INET; 710#endif 711 712 /* Initialize hardware parameters */ 713 dev->irq = wandev->irq; 714 dev->dma = wandev->dma; 715 dev->base_addr = wandev->ioport; 716 dev->mem_start = wandev->maddr; 717 dev->mem_end = wandev->maddr + wandev->msize - 1; 718 719 /* Set transmit buffer queue length 720 * If we over fill this queue the packets will 721 * be droped by the kernel. 722 * sppp_attach() sets this to 10, but 723 * 100 will give us more room at low speeds. 724 */ 725 dev->tx_queue_len = 100; 726 727 /* Initialize socket buffers */ 728#if !defined(LINUX_2_1) && !defined(LINUX_2_4) 729 for (i = 0; i < DEV_NUMBUFFS; ++i) 730 skb_queue_head_init(&dev->buffs[i]); 731#endif 732 733 return 0; 734} 735 736 737#ifdef LINUX_2_4 738/*============================================================================ 739 * Handle transmit timeout event from netif watchdog 740 */ 741static void if_tx_timeout (netdevice_t *dev) 742{ 743 chdlc_private_area_t* chan = dev->priv; 744 sdla_t *card = chan->card; 745 746 /* If our device stays busy for at least 5 seconds then we will 747 * kick start the device by making dev->tbusy = 0. We expect 748 * that our device never stays busy more than 5 seconds. So this 749 * is only used as a last resort. 750 */ 751 752 ++card->wandev.stats.collisions; 753 754 printk (KERN_INFO "%s: Transmit timed out on %s\n", card->devname,dev->name); 755 netif_wake_queue (dev); 756} 757#endif 758 759 760 761/*============================================================================ 762 * Open network interface. 763 * o enable communications and interrupts. 764 * o prevent module from unloading by incrementing use count 765 * 766 * Return 0 if O.k. or errno. 767 */ 768static int if_open (netdevice_t* dev) 769{ 770 chdlc_private_area_t* chdlc_priv_area = dev->priv; 771 sdla_t* card = chdlc_priv_area->card; 772 struct timeval tv; 773 SHARED_MEMORY_INFO_STRUCT *flags = card->u.c.flags; 774 775 /* Only one open per interface is allowed */ 776 777#ifdef LINUX_2_4 778 if (netif_running(dev)) 779 return -EBUSY; 780#else 781 if (dev->start) 782 return -EBUSY; /* only one open is allowed */ 783#endif 784 785 /* Start PPP Layer */ 786 if (sppp_open(dev)){ 787 return -EIO; 788 } 789 790 do_gettimeofday(&tv); 791 chdlc_priv_area->router_start_time = tv.tv_sec; 792 793#ifdef LINUX_2_4 794 netif_start_queue(dev); 795#else 796 dev->interrupt = 0; 797 dev->tbusy = 0; 798 dev->start = 1; 799#endif 800 801 wanpipe_open(card); 802 803 chdlc_priv_area->timer_int_enabled |= TMR_INT_ENABLED_CONFIG; 804 flags->interrupt_info_struct.interrupt_permission |= APP_INT_ON_TIMER; 805 return 0; 806} 807 808/*============================================================================ 809 * Close network interface. 810 * o if this is the last close, then disable communications and interrupts. 811 * o reset flags. 812 */ 813static int if_close (netdevice_t* dev) 814{ 815 chdlc_private_area_t* chdlc_priv_area = dev->priv; 816 sdla_t* card = chdlc_priv_area->card; 817 818 /* Stop the PPP Layer */ 819 sppp_close(dev); 820 stop_net_queue(dev); 821 822#ifndef LINUX_2_4 823 dev->start=0; 824#endif 825 826 wanpipe_close(card); 827 828 return 0; 829} 830 831/*============================================================================ 832 * Send a packet on a network interface. 833 * o set tbusy flag (marks start of the transmission) to block a timer-based 834 * transmit from overlapping. 835 * o check link state. If link is not up, then drop the packet. 836 * o execute adapter send command. 837 * o free socket buffer 838 * 839 * Return: 0 complete (socket buffer must be freed) 840 * non-0 packet may be re-transmitted (tbusy must be set) 841 * 842 * Notes: 843 * 1. This routine is called either by the protocol stack or by the "net 844 * bottom half" (with interrupts enabled). 845 * 2. Setting tbusy flag will inhibit further transmit requests from the 846 * protocol stack and can be used for flow control with protocol layer. 847 */ 848static int if_send (struct sk_buff* skb, netdevice_t* dev) 849{ 850 chdlc_private_area_t *chdlc_priv_area = dev->priv; 851 sdla_t *card = chdlc_priv_area->card; 852 SHARED_MEMORY_INFO_STRUCT *flags = card->u.c.flags; 853 INTERRUPT_INFORMATION_STRUCT *chdlc_int = &flags->interrupt_info_struct; 854 int udp_type = 0; 855 unsigned long smp_flags; 856 int err=0; 857 858#ifdef LINUX_2_4 859 netif_stop_queue(dev); 860#endif 861 862 863 if (skb == NULL){ 864 /* If we get here, some higher layer thinks we've missed an 865 * tx-done interrupt. 866 */ 867 printk(KERN_INFO "%s: Received NULL skb buffer! interface %s got kicked!\n", 868 card->devname, dev->name); 869 870 wake_net_dev(dev); 871 return 0; 872 } 873 874#ifndef LINUX_2_4 875 if (dev->tbusy){ 876 877 /* If our device stays busy for at least 5 seconds then we will 878 * kick start the device by making dev->tbusy = 0. We expect 879 * that our device never stays busy more than 5 seconds. So this 880 * is only used as a last resort. 881 */ 882 ++card->wandev.stats.collisions; 883 884 if((jiffies - chdlc_priv_area->tick_counter) < (5 * HZ)) { 885 return 1; 886 } 887 888 printk (KERN_INFO "%s: Transmit (tbusy) timeout !\n", 889 card->devname); 890 891 /* unbusy the interface */ 892 dev->tbusy = 0; 893 } 894#endif 895 896 if (ntohs(skb->protocol) != htons(PVC_PROT)){ 897 /* check the udp packet type */ 898 899 udp_type = udp_pkt_type(skb, card); 900 if (udp_type == UDP_CPIPE_TYPE){ 901 if(store_udp_mgmt_pkt(UDP_PKT_FRM_STACK, card, skb, dev, 902 chdlc_priv_area)){ 903 chdlc_int->interrupt_permission |= 904 APP_INT_ON_TIMER; 905 } 906 start_net_queue(dev); 907 return 0; 908 } 909 } 910 911 /* Lock the 508 Card: SMP is supported */ 912 if(card->hw.type != SDLA_S514){ 913 s508_lock(card,&smp_flags); 914 } 915 916 if (test_and_set_bit(SEND_CRIT, (void*)&card->wandev.critical)){ 917 918 printk(KERN_INFO "%s: Critical in if_send: %lx\n", 919 card->wandev.name,card->wandev.critical); 920 ++card->wandev.stats.tx_dropped; 921 start_net_queue(dev); 922 goto if_send_crit_exit; 923 } 924 925 if (card->wandev.state != WAN_CONNECTED){ 926 ++card->wandev.stats.tx_dropped; 927 start_net_queue(dev); 928 goto if_send_crit_exit; 929 } 930 931 if (chdlc_send(card, skb->data, skb->len)){ 932 stop_net_queue(dev); 933 934 }else{ 935 ++card->wandev.stats.tx_packets; 936#if defined(LINUX_2_1) || defined(LINUX_2_4) 937 card->wandev.stats.tx_bytes += skb->len; 938#endif 939#ifdef LINUX_2_4 940 dev->trans_start = jiffies; 941#endif 942 start_net_queue(dev); 943 } 944 945if_send_crit_exit: 946 if (!(err=is_queue_stopped(dev))){ 947 wan_dev_kfree_skb(skb, FREE_WRITE); 948 }else{ 949 chdlc_priv_area->tick_counter = jiffies; 950 chdlc_int->interrupt_permission |= APP_INT_ON_TX_FRAME; 951 } 952 953 clear_bit(SEND_CRIT, (void*)&card->wandev.critical); 954 if(card->hw.type != SDLA_S514){ 955 s508_unlock(card,&smp_flags); 956 } 957 958 return err; 959} 960 961 962/*============================================================================ 963 * Reply to UDP Management system. 964 * Return length of reply. 965 */ 966static int reply_udp( unsigned char *data, unsigned int mbox_len ) 967{ 968 969 unsigned short len, udp_length, temp, ip_length; 970 unsigned long ip_temp; 971 int even_bound = 0; 972 chdlc_udp_pkt_t *c_udp_pkt = (chdlc_udp_pkt_t *)data; 973 974 /* Set length of packet */ 975 len = sizeof(ip_pkt_t)+ 976 sizeof(udp_pkt_t)+ 977 sizeof(wp_mgmt_t)+ 978 sizeof(cblock_t)+ 979 sizeof(trace_info_t)+ 980 mbox_len; 981 982 /* fill in UDP reply */ 983 c_udp_pkt->wp_mgmt.request_reply = UDPMGMT_REPLY; 984 985 /* fill in UDP length */ 986 udp_length = sizeof(udp_pkt_t)+ 987 sizeof(wp_mgmt_t)+ 988 sizeof(cblock_t)+ 989 sizeof(trace_info_t)+ 990 mbox_len; 991 992 /* put it on an even boundary */ 993 if ( udp_length & 0x0001 ) { 994 udp_length += 1; 995 len += 1; 996 even_bound = 1; 997 } 998 999 temp = (udp_length<<8)|(udp_length>>8); 1000 c_udp_pkt->udp_pkt.udp_length = temp; 1001 1002 /* swap UDP ports */ 1003 temp = c_udp_pkt->udp_pkt.udp_src_port; 1004 c_udp_pkt->udp_pkt.udp_src_port = 1005 c_udp_pkt->udp_pkt.udp_dst_port; 1006 c_udp_pkt->udp_pkt.udp_dst_port = temp; 1007 1008 /* add UDP pseudo header */ 1009 temp = 0x1100; 1010 *((unsigned short *)(c_udp_pkt->data+mbox_len+even_bound)) = temp; 1011 temp = (udp_length<<8)|(udp_length>>8); 1012 *((unsigned short *)(c_udp_pkt->data+mbox_len+even_bound+2)) = temp; 1013 1014 1015 /* calculate UDP checksum */ 1016 c_udp_pkt->udp_pkt.udp_checksum = 0; 1017 c_udp_pkt->udp_pkt.udp_checksum = calc_checksum(&data[UDP_OFFSET],udp_length+UDP_OFFSET); 1018 1019 /* fill in IP length */ 1020 ip_length = len; 1021 temp = (ip_length<<8)|(ip_length>>8); 1022 c_udp_pkt->ip_pkt.total_length = temp; 1023 1024 /* swap IP addresses */ 1025 ip_temp = c_udp_pkt->ip_pkt.ip_src_address; 1026 c_udp_pkt->ip_pkt.ip_src_address = c_udp_pkt->ip_pkt.ip_dst_address; 1027 c_udp_pkt->ip_pkt.ip_dst_address = ip_temp; 1028 1029 /* fill in IP checksum */ 1030 c_udp_pkt->ip_pkt.hdr_checksum = 0; 1031 c_udp_pkt->ip_pkt.hdr_checksum = calc_checksum(data,sizeof(ip_pkt_t)); 1032 1033 return len; 1034 1035} /* reply_udp */ 1036 1037unsigned short calc_checksum (char *data, int len) 1038{ 1039 unsigned short temp; 1040 unsigned long sum=0; 1041 int i; 1042 1043 for( i = 0; i <len; i+=2 ) { 1044 memcpy(&temp,&data[i],2); 1045 sum += (unsigned long)temp; 1046 } 1047 1048 while (sum >> 16 ) { 1049 sum = (sum & 0xffffUL) + (sum >> 16); 1050 } 1051 1052 temp = (unsigned short)sum; 1053 temp = ~temp; 1054 1055 if( temp == 0 ) 1056 temp = 0xffff; 1057 1058 return temp; 1059} 1060 1061 1062/*============================================================================ 1063 * Get ethernet-style interface statistics. 1064 * Return a pointer to struct enet_statistics. 1065 */ 1066#if defined(LINUX_2_1) || defined(LINUX_2_4) 1067static struct net_device_stats* if_stats (netdevice_t* dev) 1068{ 1069 sdla_t *my_card; 1070 chdlc_private_area_t* chdlc_priv_area; 1071 1072 /* Shutdown bug fix. In del_if() we kill 1073 * dev->priv pointer. This function, gets 1074 * called after del_if(), thus check 1075 * if pointer has been deleted */ 1076 if ((chdlc_priv_area=dev->priv) == NULL) 1077 return NULL; 1078 1079 my_card = chdlc_priv_area->card; 1080 return &my_card->wandev.stats; 1081} 1082#else 1083static struct enet_statistics* if_stats (netdevice_t* dev) 1084{ 1085 sdla_t *my_card; 1086 chdlc_private_area_t* chdlc_priv_area = dev->priv; 1087 1088 /* Shutdown bug fix. In del_if() we kill 1089 * dev->priv pointer. This function, gets 1090 * called after del_if(), thus check 1091 * if pointer has been deleted */ 1092 if ((chdlc_priv_area=dev->priv) == NULL) 1093 return NULL; 1094 1095 my_card = chdlc_priv_area->card; 1096 return &my_card->wandev.stats; 1097} 1098#endif 1099 1100/****** Cisco HDLC Firmware Interface Functions *******************************/ 1101 1102/*============================================================================ 1103 * Read firmware code version. 1104 * Put code version as ASCII string in str. 1105 */ 1106static int chdlc_read_version (sdla_t* card, char* str) 1107{ 1108 CHDLC_MAILBOX_STRUCT* mb = card->mbox; 1109 int len; 1110 char err; 1111 mb->buffer_length = 0; 1112 mb->command = READ_CHDLC_CODE_VERSION; 1113 err = sdla_exec(mb) ? mb->return_code : CMD_TIMEOUT; 1114 1115 if(err != COMMAND_OK) { 1116 chdlc_error(card,err,mb); 1117 } 1118 else if (str) { /* is not null */ 1119 len = mb->buffer_length; 1120 memcpy(str, mb->data, len); 1121 str[len] = '\0'; 1122 } 1123 return (err); 1124} 1125 1126/*----------------------------------------------------------------------------- 1127 * Configure CHDLC firmware. 1128 */ 1129static int chdlc_configure (sdla_t* card, void* data) 1130{ 1131 int err; 1132 CHDLC_MAILBOX_STRUCT *mailbox = card->mbox; 1133 int data_length = sizeof(CHDLC_CONFIGURATION_STRUCT); 1134 1135 mailbox->buffer_length = data_length; 1136 memcpy(mailbox->data, data, data_length); 1137 mailbox->command = SET_CHDLC_CONFIGURATION; 1138 err = sdla_exec(mailbox) ? mailbox->return_code : CMD_TIMEOUT; 1139 1140 if (err != COMMAND_OK) chdlc_error (card, err, mailbox); 1141 1142 return err; 1143} 1144 1145 1146/*============================================================================ 1147 * Set interrupt mode -- HDLC Version. 1148 */ 1149 1150static int chdlc_set_intr_mode (sdla_t* card, unsigned mode) 1151{ 1152 CHDLC_MAILBOX_STRUCT* mb = card->mbox; 1153 CHDLC_INT_TRIGGERS_STRUCT* int_data = 1154 (CHDLC_INT_TRIGGERS_STRUCT *)mb->data; 1155 int err; 1156 1157 int_data->CHDLC_interrupt_triggers = mode; 1158 int_data->IRQ = card->hw.irq; 1159 int_data->interrupt_timer = 1; 1160 1161 mb->buffer_length = sizeof(CHDLC_INT_TRIGGERS_STRUCT); 1162 mb->command = SET_CHDLC_INTERRUPT_TRIGGERS; 1163 err = sdla_exec(mb) ? mb->return_code : CMD_TIMEOUT; 1164 if (err != COMMAND_OK) 1165 chdlc_error (card, err, mb); 1166 return err; 1167} 1168 1169 1170/*============================================================================ 1171 * Enable communications. 1172 */ 1173 1174static int chdlc_comm_enable (sdla_t* card) 1175{ 1176 int err; 1177 CHDLC_MAILBOX_STRUCT* mb = card->mbox; 1178 1179 mb->buffer_length = 0; 1180 mb->command = ENABLE_CHDLC_COMMUNICATIONS; 1181 err = sdla_exec(mb) ? mb->return_code : CMD_TIMEOUT; 1182 if (err != COMMAND_OK) 1183 chdlc_error(card, err, mb); 1184 else 1185 card->u.c.comm_enabled=1; 1186 1187 return err; 1188} 1189 1190/*============================================================================ 1191 * Disable communications and Drop the Modem lines (DCD and RTS). 1192 */ 1193static int chdlc_comm_disable (sdla_t* card) 1194{ 1195 int err; 1196 CHDLC_MAILBOX_STRUCT* mb = card->mbox; 1197 1198 mb->buffer_length = 0; 1199 mb->command = DISABLE_CHDLC_COMMUNICATIONS; 1200 err = sdla_exec(mb) ? mb->return_code : CMD_TIMEOUT; 1201 if (err != COMMAND_OK) 1202 chdlc_error(card,err,mb); 1203 1204 return err; 1205} 1206 1207/*============================================================================ 1208 * Read communication error statistics. 1209 */ 1210static int chdlc_read_comm_err_stats (sdla_t* card) 1211{ 1212 int err; 1213 CHDLC_MAILBOX_STRUCT* mb = card->mbox; 1214 1215 mb->buffer_length = 0; 1216 mb->command = READ_COMMS_ERROR_STATS; 1217 err = sdla_exec(mb) ? mb->return_code : CMD_TIMEOUT; 1218 if (err != COMMAND_OK) 1219 chdlc_error(card,err,mb); 1220 return err; 1221} 1222 1223 1224/*============================================================================ 1225 * Read CHDLC operational statistics. 1226 */ 1227static int chdlc_read_op_stats (sdla_t* card) 1228{ 1229 int err; 1230 CHDLC_MAILBOX_STRUCT* mb = card->mbox; 1231 1232 mb->buffer_length = 0; 1233 mb->command = READ_CHDLC_OPERATIONAL_STATS; 1234 err = sdla_exec(mb) ? mb->return_code : CMD_TIMEOUT; 1235 if (err != COMMAND_OK) 1236 chdlc_error(card,err,mb); 1237 return err; 1238} 1239 1240 1241/*============================================================================ 1242 * Update communications error and general packet statistics. 1243 */ 1244static int update_comms_stats(sdla_t* card, 1245 chdlc_private_area_t* chdlc_priv_area) 1246{ 1247 CHDLC_MAILBOX_STRUCT* mb = card->mbox; 1248 COMMS_ERROR_STATS_STRUCT* err_stats; 1249 CHDLC_OPERATIONAL_STATS_STRUCT *op_stats; 1250 1251 /* on the first timer interrupt, read the comms error statistics */ 1252 if(chdlc_priv_area->update_comms_stats == 2) { 1253 if(chdlc_read_comm_err_stats(card)) 1254 return 1; 1255 err_stats = (COMMS_ERROR_STATS_STRUCT *)mb->data; 1256 card->wandev.stats.rx_over_errors = 1257 err_stats->Rx_overrun_err_count; 1258 card->wandev.stats.rx_crc_errors = 1259 err_stats->CRC_err_count; 1260 card->wandev.stats.rx_frame_errors = 1261 err_stats->Rx_abort_count; 1262 card->wandev.stats.rx_fifo_errors = 1263 err_stats->Rx_dis_pri_bfrs_full_count; 1264 card->wandev.stats.rx_missed_errors = 1265 card->wandev.stats.rx_fifo_errors; 1266 card->wandev.stats.tx_aborted_errors = 1267 err_stats->sec_Tx_abort_count; 1268 } 1269 1270 /* on the second timer interrupt, read the operational statistics */ 1271 else { 1272 if(chdlc_read_op_stats(card)) 1273 return 1; 1274 op_stats = (CHDLC_OPERATIONAL_STATS_STRUCT *)mb->data; 1275 card->wandev.stats.rx_length_errors = 1276 (op_stats->Rx_Data_discard_short_count + 1277 op_stats->Rx_Data_discard_long_count); 1278 } 1279 1280 return 0; 1281} 1282 1283/*============================================================================ 1284 * Send packet. 1285 * Return: 0 - o.k. 1286 * 1 - no transmit buffers available 1287 */ 1288static int chdlc_send (sdla_t* card, void* data, unsigned len) 1289{ 1290 CHDLC_DATA_TX_STATUS_EL_STRUCT *txbuf = card->u.c.txbuf; 1291 1292 if (txbuf->opp_flag) 1293 return 1; 1294 1295 sdla_poke(&card->hw, txbuf->ptr_data_bfr, data, len); 1296 1297 txbuf->frame_length = len; 1298 txbuf->opp_flag = 1; /* start transmission */ 1299 1300 /* Update transmit buffer control fields */ 1301 card->u.c.txbuf = ++txbuf; 1302 1303 if ((void*)txbuf > card->u.c.txbuf_last) 1304 card->u.c.txbuf = card->u.c.txbuf_base; 1305 1306 return 0; 1307} 1308 1309/****** Firmware Error Handler **********************************************/ 1310 1311/*============================================================================ 1312 * Firmware error handler. 1313 * This routine is called whenever firmware command returns non-zero 1314 * return code. 1315 * 1316 * Return zero if previous command has to be cancelled. 1317 */ 1318static int chdlc_error (sdla_t *card, int err, CHDLC_MAILBOX_STRUCT *mb) 1319{ 1320 unsigned cmd = mb->command; 1321 1322 switch (err) { 1323 1324 case CMD_TIMEOUT: 1325 printk(KERN_ERR "%s: command 0x%02X timed out!\n", 1326 card->devname, cmd); 1327 break; 1328 1329 case S514_BOTH_PORTS_SAME_CLK_MODE: 1330 if(cmd == SET_CHDLC_CONFIGURATION) { 1331 printk(KERN_INFO 1332 "%s: Configure both ports for the same clock source\n", 1333 card->devname); 1334 break; 1335 } 1336 1337 default: 1338 printk(KERN_INFO "%s: command 0x%02X returned 0x%02X!\n", 1339 card->devname, cmd, err); 1340 } 1341 1342 return 0; 1343} 1344 1345/****** Interrupt Handlers **************************************************/ 1346 1347/*============================================================================ 1348 * Cisco HDLC interrupt service routine. 1349 */ 1350STATIC void wsppp_isr (sdla_t* card) 1351{ 1352 netdevice_t* dev; 1353 SHARED_MEMORY_INFO_STRUCT* flags = NULL; 1354 int i; 1355 sdla_t *my_card; 1356 1357 1358 /* Check for which port the interrupt has been generated 1359 * Since Secondary Port is piggybacking on the Primary 1360 * the check must be done here. 1361 */ 1362 1363 flags = card->u.c.flags; 1364 if (!flags->interrupt_info_struct.interrupt_type){ 1365 /* Check for a second port (piggybacking) */ 1366 if((my_card = card->next)){ 1367 flags = my_card->u.c.flags; 1368 if (flags->interrupt_info_struct.interrupt_type){ 1369 card = my_card; 1370 card->isr(card); 1371 return; 1372 } 1373 } 1374 } 1375 1376 dev = card->wandev.dev; 1377 card->in_isr = 1; 1378 flags = card->u.c.flags; 1379 1380 /* If we get an interrupt with no network device, stop the interrupts 1381 * and issue an error */ 1382 if ((!dev || !dev->priv) && flags->interrupt_info_struct.interrupt_type != 1383 COMMAND_COMPLETE_APP_INT_PEND){ 1384 goto isr_done; 1385 } 1386 1387 1388 /* if critical due to peripheral operations 1389 * ie. update() or getstats() then reset the interrupt and 1390 * wait for the board to retrigger. 1391 */ 1392 if(test_bit(PERI_CRIT, (void*)&card->wandev.critical)) { 1393 flags->interrupt_info_struct. 1394 interrupt_type = 0; 1395 goto isr_done; 1396 } 1397 1398 1399 /* On a 508 Card, if critical due to if_send 1400 * Major Error !!! 1401 */ 1402 if(card->hw.type != SDLA_S514) { 1403 if(test_bit(0, (void*)&card->wandev.critical)) { 1404 printk(KERN_INFO "%s: Critical while in ISR: %lx\n", 1405 card->devname, card->wandev.critical); 1406 goto isr_done; 1407 } 1408 } 1409 1410 switch(flags->interrupt_info_struct.interrupt_type) { 1411 1412 case RX_APP_INT_PEND: /* 0x01: receive interrupt */ 1413 rx_intr(card); 1414 break; 1415 1416 case TX_APP_INT_PEND: /* 0x02: transmit interrupt */ 1417 flags->interrupt_info_struct.interrupt_permission &= 1418 ~APP_INT_ON_TX_FRAME; 1419 1420 wake_net_dev(dev); 1421 break; 1422 1423 case COMMAND_COMPLETE_APP_INT_PEND:/* 0x04: cmd cplt */ 1424 ++ Intr_test_counter; 1425 break; 1426 1427 case CHDLC_EXCEP_COND_APP_INT_PEND: /* 0x20 */ 1428 process_chdlc_exception(card); 1429 break; 1430 1431 case GLOBAL_EXCEP_COND_APP_INT_PEND: 1432 process_global_exception(card); 1433 break; 1434 1435 case TIMER_APP_INT_PEND: 1436 timer_intr(card); 1437 break; 1438 1439 default: 1440 printk(KERN_INFO "%s: spurious interrupt 0x%02X!\n", 1441 card->devname, 1442 flags->interrupt_info_struct.interrupt_type); 1443 printk(KERN_INFO "Code name: "); 1444 for(i = 0; i < 4; i ++) 1445 printk(KERN_INFO "%c", 1446 flags->global_info_struct.codename[i]); 1447 printk(KERN_INFO "\nCode version: "); 1448 for(i = 0; i < 4; i ++) 1449 printk(KERN_INFO "%c", 1450 flags->global_info_struct.codeversion[i]); 1451 printk(KERN_INFO "\n"); 1452 break; 1453 } 1454 1455isr_done: 1456 card->in_isr = 0; 1457 flags->interrupt_info_struct.interrupt_type = 0; 1458} 1459 1460/*============================================================================ 1461 * Receive interrupt handler. 1462 */ 1463static void rx_intr (sdla_t* card) 1464{ 1465 netdevice_t *dev; 1466 chdlc_private_area_t *chdlc_priv_area; 1467 SHARED_MEMORY_INFO_STRUCT *flags = card->u.c.flags; 1468 CHDLC_DATA_RX_STATUS_EL_STRUCT *rxbuf = card->u.c.rxmb; 1469 struct sk_buff *skb; 1470 unsigned len; 1471 unsigned addr = rxbuf->ptr_data_bfr; 1472 void *buf; 1473 int i,udp_type; 1474 1475 if (rxbuf->opp_flag != 0x01) { 1476 printk(KERN_INFO 1477 "%s: corrupted Rx buffer @ 0x%X, flag = 0x%02X!\n", 1478 card->devname, (unsigned)rxbuf, rxbuf->opp_flag); 1479 printk(KERN_INFO "Code name: "); 1480 for(i = 0; i < 4; i ++) 1481 printk(KERN_INFO "%c", 1482 flags->global_info_struct.codename[i]); 1483 printk(KERN_INFO "\nCode version: "); 1484 for(i = 0; i < 4; i ++) 1485 printk(KERN_INFO "%c", 1486 flags->global_info_struct.codeversion[i]); 1487 printk(KERN_INFO "\n"); 1488 1489 1490 /* Bug Fix: Mar 6 2000 1491 * If we get a corrupted mailbox, it measn that driver 1492 * is out of sync with the firmware. There is no recovery. 1493 * If we don't turn off all interrupts for this card 1494 * the machine will crash. 1495 */ 1496 printk(KERN_INFO "%s: Critical router failure ...!!!\n", card->devname); 1497 printk(KERN_INFO "Please contact Sangoma Technologies !\n"); 1498 chdlc_set_intr_mode(card,0); 1499 return; 1500 } 1501 1502 dev = card->wandev.dev; 1503 1504 if (!dev){ 1505 goto rx_exit; 1506 } 1507 1508#ifdef LINUX_2_4 1509 if (!netif_running(dev)){ 1510 goto rx_exit; 1511 } 1512#else 1513 if (!dev->start){ 1514 goto rx_exit; 1515 } 1516#endif 1517 1518 chdlc_priv_area = dev->priv; 1519 1520 if (rxbuf->error_flag){ 1521 goto rx_exit; 1522 } 1523 /* Take off two CRC bytes */ 1524 1525 if (rxbuf->frame_length < 7 || rxbuf->frame_length > 1506 ){ 1526 goto rx_exit; 1527 } 1528 1529 len = rxbuf->frame_length - CRC_LENGTH; 1530 1531 /* Allocate socket buffer */ 1532 skb = dev_alloc_skb(len); 1533 1534 if (skb == NULL) { 1535 if (net_ratelimit()){ 1536 printk(KERN_INFO "%s: no socket buffers available!\n", 1537 card->devname); 1538 } 1539 ++card->wandev.stats.rx_dropped; 1540 goto rx_exit; 1541 } 1542 1543 /* Copy data to the socket buffer */ 1544 if((addr + len) > card->u.c.rx_top + 1) { 1545 unsigned tmp = card->u.c.rx_top - addr + 1; 1546 buf = skb_put(skb, tmp); 1547 sdla_peek(&card->hw, addr, buf, tmp); 1548 addr = card->u.c.rx_base; 1549 len -= tmp; 1550 } 1551 1552 buf = skb_put(skb, len); 1553 sdla_peek(&card->hw, addr, buf, len); 1554 1555 skb->protocol = htons(ETH_P_WAN_PPP); 1556 1557 card->wandev.stats.rx_packets ++; 1558#if defined(LINUX_2_1) || defined(LINUX_2_4) 1559 card->wandev.stats.rx_bytes += skb->len; 1560#endif 1561 udp_type = udp_pkt_type( skb, card ); 1562 1563 if(udp_type == UDP_CPIPE_TYPE) { 1564 if(store_udp_mgmt_pkt(UDP_PKT_FRM_NETWORK, 1565 card, skb, dev, chdlc_priv_area)) { 1566 flags->interrupt_info_struct. 1567 interrupt_permission |= 1568 APP_INT_ON_TIMER; 1569 } 1570 }else{ 1571 /* Pass it up the protocol stack */ 1572 skb->dev = dev; 1573 skb->mac.raw = skb->data; 1574 netif_rx(skb); 1575 } 1576 1577rx_exit: 1578 /* Release buffer element and calculate a pointer to the next one */ 1579 rxbuf->opp_flag = 0x00; 1580 card->u.c.rxmb = ++ rxbuf; 1581 if((void*)rxbuf > card->u.c.rxbuf_last){ 1582 card->u.c.rxmb = card->u.c.rxbuf_base; 1583 } 1584} 1585 1586/*============================================================================ 1587 * Timer interrupt handler. 1588 * The timer interrupt is used for two purposes: 1589 * 1) Processing udp calls from 'cpipemon'. 1590 * 2) Reading board-level statistics for updating the proc file system. 1591 */ 1592void timer_intr(sdla_t *card) 1593{ 1594 netdevice_t* dev; 1595 chdlc_private_area_t* chdlc_priv_area = NULL; 1596 SHARED_MEMORY_INFO_STRUCT* flags = NULL; 1597 1598 dev = card->wandev.dev; 1599 chdlc_priv_area = dev->priv; 1600 1601 if (chdlc_priv_area->timer_int_enabled & TMR_INT_ENABLED_CONFIG) { 1602 if (!config_chdlc(card)){ 1603 chdlc_priv_area->timer_int_enabled &= ~TMR_INT_ENABLED_CONFIG; 1604 } 1605 } 1606 1607 /* process a udp call if pending */ 1608 if(chdlc_priv_area->timer_int_enabled & TMR_INT_ENABLED_UDP) { 1609 process_udp_mgmt_pkt(card, dev, 1610 chdlc_priv_area); 1611 chdlc_priv_area->timer_int_enabled &= ~TMR_INT_ENABLED_UDP; 1612 } 1613 1614 1615 /* read the communications statistics if required */ 1616 if(chdlc_priv_area->timer_int_enabled & TMR_INT_ENABLED_UPDATE) { 1617 update_comms_stats(card, chdlc_priv_area); 1618 if(!(-- chdlc_priv_area->update_comms_stats)) { 1619 chdlc_priv_area->timer_int_enabled &= 1620 ~TMR_INT_ENABLED_UPDATE; 1621 } 1622 } 1623 1624 /* only disable the timer interrupt if there are no udp or statistic */ 1625 /* updates pending */ 1626 if(!chdlc_priv_area->timer_int_enabled) { 1627 flags = card->u.c.flags; 1628 flags->interrupt_info_struct.interrupt_permission &= 1629 ~APP_INT_ON_TIMER; 1630 } 1631} 1632 1633/*------------------------------------------------------------------------------ 1634 Miscellaneous Functions 1635 - set_chdlc_config() used to set configuration options on the board 1636------------------------------------------------------------------------------*/ 1637 1638static int set_chdlc_config(sdla_t* card) 1639{ 1640 1641 CHDLC_CONFIGURATION_STRUCT cfg; 1642 1643 memset(&cfg, 0, sizeof(CHDLC_CONFIGURATION_STRUCT)); 1644 1645 if(card->wandev.clocking) 1646 cfg.baud_rate = card->wandev.bps; 1647 1648 cfg.line_config_options = (card->wandev.interface == WANOPT_RS232) ? 1649 INTERFACE_LEVEL_RS232 : INTERFACE_LEVEL_V35; 1650 1651 cfg.modem_config_options = 0; 1652 //API OPTIONS 1653 cfg.CHDLC_API_options = DISCARD_RX_ERROR_FRAMES; 1654 cfg.modem_status_timer = 100; 1655 cfg.CHDLC_protocol_options = HDLC_STREAMING_MODE; 1656 cfg.percent_data_buffer_for_Tx = 50; 1657 cfg.CHDLC_statistics_options = (CHDLC_TX_DATA_BYTE_COUNT_STAT | 1658 CHDLC_RX_DATA_BYTE_COUNT_STAT); 1659 cfg.max_CHDLC_data_field_length = card->wandev.mtu; 1660 1661 cfg.transmit_keepalive_timer = 0; 1662 cfg.receive_keepalive_timer = 0; 1663 cfg.keepalive_error_tolerance = 0; 1664 cfg.SLARP_request_timer = 0; 1665 1666 cfg.IP_address = 0; 1667 cfg.IP_netmask = 0; 1668 1669 return chdlc_configure(card, &cfg); 1670} 1671 1672/*============================================================================ 1673 * Process global exception condition 1674 */ 1675static int process_global_exception(sdla_t *card) 1676{ 1677 CHDLC_MAILBOX_STRUCT* mbox = card->mbox; 1678 int err; 1679 1680 mbox->buffer_length = 0; 1681 mbox->command = READ_GLOBAL_EXCEPTION_CONDITION; 1682 err = sdla_exec(mbox) ? mbox->return_code : CMD_TIMEOUT; 1683 1684 if(err != CMD_TIMEOUT ){ 1685 1686 switch(mbox->return_code) { 1687 1688 case EXCEP_MODEM_STATUS_CHANGE: 1689 1690 printk(KERN_INFO "%s: Modem status change\n", 1691 card->devname); 1692 1693 switch(mbox->data[0] & (DCD_HIGH | CTS_HIGH)) { 1694 case (DCD_HIGH): 1695 printk(KERN_INFO "%s: DCD high, CTS low\n",card->devname); 1696 break; 1697 case (CTS_HIGH): 1698 printk(KERN_INFO "%s: DCD low, CTS high\n",card->devname); 1699 break; 1700 case ((DCD_HIGH | CTS_HIGH)): 1701 printk(KERN_INFO "%s: DCD high, CTS high\n",card->devname); 1702 break; 1703 default: 1704 printk(KERN_INFO "%s: DCD low, CTS low\n",card->devname); 1705 break; 1706 } 1707 1708 if (!(mbox->data[0] & DCD_HIGH) || !(mbox->data[0] & DCD_HIGH)){ 1709 //printk(KERN_INFO "Sending TERM Request Manually !\n"); 1710 send_ppp_term_request(card->wandev.dev); 1711 } 1712 break; 1713 1714 case EXCEP_TRC_DISABLED: 1715 printk(KERN_INFO "%s: Line trace disabled\n", 1716 card->devname); 1717 break; 1718 1719 case EXCEP_IRQ_TIMEOUT: 1720 printk(KERN_INFO "%s: IRQ timeout occurred\n", 1721 card->devname); 1722 break; 1723 1724 default: 1725 printk(KERN_INFO "%s: Global exception %x\n", 1726 card->devname, mbox->return_code); 1727 break; 1728 } 1729 } 1730 return 0; 1731} 1732 1733 1734/*============================================================================ 1735 * Process chdlc exception condition 1736 */ 1737static int process_chdlc_exception(sdla_t *card) 1738{ 1739 CHDLC_MAILBOX_STRUCT* mb = card->mbox; 1740 int err; 1741 1742 mb->buffer_length = 0; 1743 mb->command = READ_CHDLC_EXCEPTION_CONDITION; 1744 err = sdla_exec(mb) ? mb->return_code : CMD_TIMEOUT; 1745 if(err != CMD_TIMEOUT) { 1746 1747 switch (err) { 1748 1749 case EXCEP_LINK_ACTIVE: 1750 port_set_state(card, WAN_CONNECTED); 1751 break; 1752 1753 case EXCEP_LINK_INACTIVE_MODEM: 1754 port_set_state(card, WAN_DISCONNECTED); 1755 break; 1756 1757 case EXCEP_LOOPBACK_CONDITION: 1758 printk(KERN_INFO "%s: Loopback Condition Detected.\n", 1759 card->devname); 1760 break; 1761 1762 case NO_CHDLC_EXCEP_COND_TO_REPORT: 1763 printk(KERN_INFO "%s: No exceptions reported.\n", 1764 card->devname); 1765 break; 1766 default: 1767 printk(KERN_INFO "%s: Exception Condition %x!\n", 1768 card->devname,err); 1769 break; 1770 } 1771 1772 } 1773 return 0; 1774} 1775 1776 1777/*============================================================================= 1778 * Store a UDP management packet for later processing. 1779 */ 1780 1781static int store_udp_mgmt_pkt(char udp_pkt_src, sdla_t* card, 1782 struct sk_buff *skb, netdevice_t* dev, 1783 chdlc_private_area_t* chdlc_priv_area ) 1784{ 1785 int udp_pkt_stored = 0; 1786 1787 if(!chdlc_priv_area->udp_pkt_lgth && 1788 (skb->len <= MAX_LGTH_UDP_MGNT_PKT)) { 1789 chdlc_priv_area->udp_pkt_lgth = skb->len; 1790 chdlc_priv_area->udp_pkt_src = udp_pkt_src; 1791 memcpy(chdlc_priv_area->udp_pkt_data, skb->data, skb->len); 1792 chdlc_priv_area->timer_int_enabled = TMR_INT_ENABLED_UDP; 1793 udp_pkt_stored = 1; 1794 } 1795 1796 if(udp_pkt_src == UDP_PKT_FRM_STACK) 1797 wan_dev_kfree_skb(skb, FREE_WRITE); 1798 else 1799 wan_dev_kfree_skb(skb, FREE_READ); 1800 1801 return(udp_pkt_stored); 1802} 1803 1804 1805/*============================================================================= 1806 * Process UDP management packet. 1807 */ 1808 1809static int process_udp_mgmt_pkt(sdla_t* card, netdevice_t* dev, 1810 chdlc_private_area_t* chdlc_priv_area ) 1811{ 1812 unsigned char *buf; 1813 unsigned int frames, len; 1814 struct sk_buff *new_skb; 1815 unsigned short buffer_length, real_len; 1816 unsigned long data_ptr; 1817 unsigned data_length; 1818 int udp_mgmt_req_valid = 1; 1819 CHDLC_MAILBOX_STRUCT *mb = card->mbox; 1820 SHARED_MEMORY_INFO_STRUCT *flags = card->u.c.flags; 1821 chdlc_udp_pkt_t *chdlc_udp_pkt; 1822 struct timeval tv; 1823 int err; 1824 char ut_char; 1825 1826 chdlc_udp_pkt = (chdlc_udp_pkt_t *) chdlc_priv_area->udp_pkt_data; 1827 1828 if(chdlc_priv_area->udp_pkt_src == UDP_PKT_FRM_NETWORK) { 1829 1830 switch(chdlc_udp_pkt->cblock.command) { 1831 case READ_GLOBAL_STATISTICS: 1832 case READ_MODEM_STATUS: 1833 case READ_CHDLC_LINK_STATUS: 1834 case CPIPE_ROUTER_UP_TIME: 1835 case READ_COMMS_ERROR_STATS: 1836 case READ_CHDLC_OPERATIONAL_STATS: 1837 1838 /* These two commands are executed for 1839 * each request */ 1840 case READ_CHDLC_CONFIGURATION: 1841 case READ_CHDLC_CODE_VERSION: 1842 udp_mgmt_req_valid = 1; 1843 break; 1844 default: 1845 udp_mgmt_req_valid = 0; 1846 break; 1847 } 1848 } 1849 1850 if(!udp_mgmt_req_valid) { 1851 1852 /* set length to 0 */ 1853 chdlc_udp_pkt->cblock.buffer_length = 0; 1854 1855 /* set return code */ 1856 chdlc_udp_pkt->cblock.return_code = 0xCD; 1857 1858 if (net_ratelimit()){ 1859 printk(KERN_INFO 1860 "%s: Warning, Illegal UDP command attempted from network: %x\n", 1861 card->devname,chdlc_udp_pkt->cblock.command); 1862 } 1863 1864 } else { 1865 unsigned long trace_status_cfg_addr = 0; 1866 TRACE_STATUS_EL_CFG_STRUCT trace_cfg_struct; 1867 TRACE_STATUS_ELEMENT_STRUCT trace_element_struct; 1868 1869 switch(chdlc_udp_pkt->cblock.command) { 1870 1871 case CPIPE_ENABLE_TRACING: 1872 if (!chdlc_priv_area->TracingEnabled) { 1873 1874 /* OPERATE_DATALINE_MONITOR */ 1875 1876 mb->buffer_length = sizeof(LINE_TRACE_CONFIG_STRUCT); 1877 mb->command = SET_TRACE_CONFIGURATION; 1878 1879 ((LINE_TRACE_CONFIG_STRUCT *)mb->data)-> 1880 trace_config = TRACE_ACTIVE; 1881 /* Trace delay mode is not used because it slows 1882 down transfer and results in a standoff situation 1883 when there is a lot of data */ 1884 1885 /* Configure the Trace based on user inputs */ 1886 ((LINE_TRACE_CONFIG_STRUCT *)mb->data)->trace_config |= 1887 chdlc_udp_pkt->data[0]; 1888 1889 ((LINE_TRACE_CONFIG_STRUCT *)mb->data)-> 1890 trace_deactivation_timer = 4000; 1891 1892 1893 err = sdla_exec(mb) ? mb->return_code : CMD_TIMEOUT; 1894 if (err != COMMAND_OK) { 1895 chdlc_error(card,err,mb); 1896 card->TracingEnabled = 0; 1897 chdlc_udp_pkt->cblock.return_code = err; 1898 mb->buffer_length = 0; 1899 break; 1900 } 1901 1902 /* Get the base address of the trace element list */ 1903 mb->buffer_length = 0; 1904 mb->command = READ_TRACE_CONFIGURATION; 1905 err = sdla_exec(mb) ? mb->return_code : CMD_TIMEOUT; 1906 1907 if (err != COMMAND_OK) { 1908 chdlc_error(card,err,mb); 1909 chdlc_priv_area->TracingEnabled = 0; 1910 chdlc_udp_pkt->cblock.return_code = err; 1911 mb->buffer_length = 0; 1912 break; 1913 } 1914 1915 trace_status_cfg_addr =((LINE_TRACE_CONFIG_STRUCT *) 1916 mb->data) -> ptr_trace_stat_el_cfg_struct; 1917 1918 sdla_peek(&card->hw, trace_status_cfg_addr, 1919 &trace_cfg_struct, sizeof(trace_cfg_struct)); 1920 1921 chdlc_priv_area->start_trace_addr = trace_cfg_struct. 1922 base_addr_trace_status_elements; 1923 1924 chdlc_priv_area->number_trace_elements = 1925 trace_cfg_struct.number_trace_status_elements; 1926 1927 chdlc_priv_area->end_trace_addr = (unsigned long) 1928 ((TRACE_STATUS_ELEMENT_STRUCT *) 1929 chdlc_priv_area->start_trace_addr + 1930 (chdlc_priv_area->number_trace_elements - 1)); 1931 1932 chdlc_priv_area->base_addr_trace_buffer = 1933 trace_cfg_struct.base_addr_trace_buffer; 1934 1935 chdlc_priv_area->end_addr_trace_buffer = 1936 trace_cfg_struct.end_addr_trace_buffer; 1937 1938 chdlc_priv_area->curr_trace_addr = 1939 trace_cfg_struct.next_trace_element_to_use; 1940 1941 chdlc_priv_area->available_buffer_space = 2000 - 1942 sizeof(ip_pkt_t) - 1943 sizeof(udp_pkt_t) - 1944 sizeof(wp_mgmt_t) - 1945 sizeof(cblock_t) - 1946 sizeof(trace_info_t); 1947 } 1948 chdlc_udp_pkt->cblock.return_code = COMMAND_OK; 1949 mb->buffer_length = 0; 1950 chdlc_priv_area->TracingEnabled = 1; 1951 break; 1952 1953 1954 case CPIPE_DISABLE_TRACING: 1955 if (chdlc_priv_area->TracingEnabled) { 1956 1957 /* OPERATE_DATALINE_MONITOR */ 1958 mb->buffer_length = sizeof(LINE_TRACE_CONFIG_STRUCT); 1959 mb->command = SET_TRACE_CONFIGURATION; 1960 ((LINE_TRACE_CONFIG_STRUCT *)mb->data)-> 1961 trace_config = TRACE_INACTIVE; 1962 err = sdla_exec(mb) ? mb->return_code : CMD_TIMEOUT; 1963 } 1964 1965 chdlc_priv_area->TracingEnabled = 0; 1966 chdlc_udp_pkt->cblock.return_code = COMMAND_OK; 1967 mb->buffer_length = 0; 1968 break; 1969 1970 1971 case CPIPE_GET_TRACE_INFO: 1972 1973 if (!chdlc_priv_area->TracingEnabled) { 1974 chdlc_udp_pkt->cblock.return_code = 1; 1975 mb->buffer_length = 0; 1976 break; 1977 } 1978 1979 chdlc_udp_pkt->trace_info.ismoredata = 0x00; 1980 buffer_length = 0; /* offset of packet already occupied */ 1981 1982 for (frames=0; frames < chdlc_priv_area->number_trace_elements; frames++){ 1983 1984 trace_pkt_t *trace_pkt = (trace_pkt_t *) 1985 &chdlc_udp_pkt->data[buffer_length]; 1986 1987 sdla_peek(&card->hw, chdlc_priv_area->curr_trace_addr, 1988 (unsigned char *)&trace_element_struct, 1989 sizeof(TRACE_STATUS_ELEMENT_STRUCT)); 1990 1991 if (trace_element_struct.opp_flag == 0x00) { 1992 break; 1993 } 1994 1995 /* get pointer to real data */ 1996 data_ptr = trace_element_struct.ptr_data_bfr; 1997 1998 /* See if there is actual data on the trace buffer */ 1999 if (data_ptr){ 2000 data_length = trace_element_struct.trace_length; 2001 }else{ 2002 data_length = 0; 2003 chdlc_udp_pkt->trace_info.ismoredata = 0x01; 2004 } 2005 2006 if( (chdlc_priv_area->available_buffer_space - buffer_length) 2007 < ( sizeof(trace_pkt_t) + data_length) ) { 2008 2009 /* indicate there are more frames on board & exit */ 2010 chdlc_udp_pkt->trace_info.ismoredata = 0x01; 2011 break; 2012 } 2013 2014 trace_pkt->status = trace_element_struct.trace_type; 2015 2016 trace_pkt->time_stamp = 2017 trace_element_struct.trace_time_stamp; 2018 2019 trace_pkt->real_length = 2020 trace_element_struct.trace_length; 2021 2022 /* see if we can fit the frame into the user buffer */ 2023 real_len = trace_pkt->real_length; 2024 2025 if (data_ptr == 0) { 2026 trace_pkt->data_avail = 0x00; 2027 } else { 2028 unsigned tmp = 0; 2029 2030 /* get the data from circular buffer 2031 must check for end of buffer */ 2032 trace_pkt->data_avail = 0x01; 2033 2034 if ((data_ptr + real_len) > 2035 chdlc_priv_area->end_addr_trace_buffer + 1){ 2036 2037 tmp = chdlc_priv_area->end_addr_trace_buffer - data_ptr + 1; 2038 sdla_peek(&card->hw, data_ptr, 2039 trace_pkt->data,tmp); 2040 data_ptr = chdlc_priv_area->base_addr_trace_buffer; 2041 } 2042 2043 sdla_peek(&card->hw, data_ptr, 2044 &trace_pkt->data[tmp], real_len - tmp); 2045 } 2046 2047 /* zero the opp flag to show we got the frame */ 2048 ut_char = 0x00; 2049 sdla_poke(&card->hw, chdlc_priv_area->curr_trace_addr, &ut_char, 1); 2050 2051 /* now move onto the next frame */ 2052 chdlc_priv_area->curr_trace_addr += sizeof(TRACE_STATUS_ELEMENT_STRUCT); 2053 2054 /* check if we went over the last address */ 2055 if ( chdlc_priv_area->curr_trace_addr > chdlc_priv_area->end_trace_addr ) { 2056 chdlc_priv_area->curr_trace_addr = chdlc_priv_area->start_trace_addr; 2057 } 2058 2059 if(trace_pkt->data_avail == 0x01) { 2060 buffer_length += real_len - 1; 2061 } 2062 2063 /* for the header */ 2064 buffer_length += sizeof(trace_pkt_t); 2065 2066 } /* For Loop */ 2067 2068 if (frames == chdlc_priv_area->number_trace_elements){ 2069 chdlc_udp_pkt->trace_info.ismoredata = 0x01; 2070 } 2071 chdlc_udp_pkt->trace_info.num_frames = frames; 2072 2073 mb->buffer_length = buffer_length; 2074 chdlc_udp_pkt->cblock.buffer_length = buffer_length; 2075 2076 chdlc_udp_pkt->cblock.return_code = COMMAND_OK; 2077 2078 break; 2079 2080 2081 case CPIPE_FT1_READ_STATUS: 2082 ((unsigned char *)chdlc_udp_pkt->data )[0] = 2083 flags->FT1_info_struct.parallel_port_A_input; 2084 2085 ((unsigned char *)chdlc_udp_pkt->data )[1] = 2086 flags->FT1_info_struct.parallel_port_B_input; 2087 2088 chdlc_udp_pkt->cblock.return_code = COMMAND_OK; 2089 mb->buffer_length = 2; 2090 break; 2091 2092 case CPIPE_ROUTER_UP_TIME: 2093 do_gettimeofday( &tv ); 2094 chdlc_priv_area->router_up_time = tv.tv_sec - 2095 chdlc_priv_area->router_start_time; 2096 *(unsigned long *)&chdlc_udp_pkt->data = 2097 chdlc_priv_area->router_up_time; 2098 mb->buffer_length = sizeof(unsigned long); 2099 break; 2100 2101 case FT1_MONITOR_STATUS_CTRL: 2102 /* Enable FT1 MONITOR STATUS */ 2103 if ((chdlc_udp_pkt->data[0] & ENABLE_READ_FT1_STATUS) || 2104 (chdlc_udp_pkt->data[0] & ENABLE_READ_FT1_OP_STATS)) { 2105 2106 if( rCount++ != 0 ) { 2107 chdlc_udp_pkt->cblock. 2108 return_code = COMMAND_OK; 2109 mb->buffer_length = 1; 2110 break; 2111 } 2112 } 2113 2114 /* Disable FT1 MONITOR STATUS */ 2115 if( chdlc_udp_pkt->data[0] == 0) { 2116 2117 if( --rCount != 0) { 2118 chdlc_udp_pkt->cblock. 2119 return_code = COMMAND_OK; 2120 mb->buffer_length = 1; 2121 break; 2122 } 2123 } 2124 2125 default: 2126 /* it's a board command */ 2127 mb->command = chdlc_udp_pkt->cblock.command; 2128 mb->buffer_length = chdlc_udp_pkt->cblock.buffer_length; 2129 if (mb->buffer_length) { 2130 memcpy(&mb->data, (unsigned char *) chdlc_udp_pkt-> 2131 data, mb->buffer_length); 2132 } 2133 /* run the command on the board */ 2134 err = sdla_exec(mb) ? mb->return_code : CMD_TIMEOUT; 2135 if (err != COMMAND_OK) { 2136 break; 2137 } 2138 2139 /* copy the result back to our buffer */ 2140 memcpy(&chdlc_udp_pkt->cblock, mb, sizeof(cblock_t)); 2141 2142 if (mb->buffer_length) { 2143 memcpy(&chdlc_udp_pkt->data, &mb->data, 2144 mb->buffer_length); 2145 } 2146 2147 } /* end of switch */ 2148 } /* end of else */ 2149 2150 /* Fill UDP TTL */ 2151 chdlc_udp_pkt->ip_pkt.ttl = card->wandev.ttl; 2152 2153 len = reply_udp(chdlc_priv_area->udp_pkt_data, mb->buffer_length); 2154 2155 if(chdlc_priv_area->udp_pkt_src == UDP_PKT_FRM_NETWORK) { 2156 if(!chdlc_send(card, chdlc_priv_area->udp_pkt_data, len)) { 2157 ++ card->wandev.stats.tx_packets; 2158#if defined(LINUX_2_1) || defined(LINUX_2_4) 2159 card->wandev.stats.tx_bytes += len; 2160#endif 2161 } 2162 } else { 2163 2164 /* Pass it up the stack 2165 Allocate socket buffer */ 2166 if ((new_skb = dev_alloc_skb(len)) != NULL) { 2167 /* copy data into new_skb */ 2168 2169 buf = skb_put(new_skb, len); 2170 memcpy(buf, chdlc_priv_area->udp_pkt_data, len); 2171 2172 /* Decapsulate pkt and pass it up the protocol stack */ 2173 new_skb->protocol = htons(ETH_P_IP); 2174 new_skb->dev = dev; 2175 new_skb->mac.raw = new_skb->data; 2176 2177 netif_rx(new_skb); 2178 } else { 2179 2180 printk(KERN_INFO "%s: no socket buffers available!\n", 2181 card->devname); 2182 } 2183 } 2184 2185 chdlc_priv_area->udp_pkt_lgth = 0; 2186 2187 return 0; 2188} 2189 2190/*============================================================================ 2191 * Initialize Receive and Transmit Buffers. 2192 */ 2193 2194static void init_chdlc_tx_rx_buff( sdla_t* card, netdevice_t *dev ) 2195{ 2196 CHDLC_MAILBOX_STRUCT* mb = card->mbox; 2197 CHDLC_TX_STATUS_EL_CFG_STRUCT *tx_config; 2198 CHDLC_RX_STATUS_EL_CFG_STRUCT *rx_config; 2199 char err; 2200 2201 mb->buffer_length = 0; 2202 mb->command = READ_CHDLC_CONFIGURATION; 2203 err = sdla_exec(mb) ? mb->return_code : CMD_TIMEOUT; 2204 2205 if(err != COMMAND_OK) { 2206 chdlc_error(card,err,mb); 2207 return; 2208 } 2209 2210 if(card->hw.type == SDLA_S514) { 2211 tx_config = (CHDLC_TX_STATUS_EL_CFG_STRUCT *)(card->hw.dpmbase + 2212 (((CHDLC_CONFIGURATION_STRUCT *)mb->data)-> 2213 ptr_CHDLC_Tx_stat_el_cfg_struct)); 2214 rx_config = (CHDLC_RX_STATUS_EL_CFG_STRUCT *)(card->hw.dpmbase + 2215 (((CHDLC_CONFIGURATION_STRUCT *)mb->data)-> 2216 ptr_CHDLC_Rx_stat_el_cfg_struct)); 2217 2218 /* Setup Head and Tails for buffers */ 2219 card->u.c.txbuf_base = (void *)(card->hw.dpmbase + 2220 tx_config->base_addr_Tx_status_elements); 2221 card->u.c.txbuf_last = 2222 (CHDLC_DATA_TX_STATUS_EL_STRUCT *) 2223 card->u.c.txbuf_base + 2224 (tx_config->number_Tx_status_elements - 1); 2225 2226 card->u.c.rxbuf_base = (void *)(card->hw.dpmbase + 2227 rx_config->base_addr_Rx_status_elements); 2228 card->u.c.rxbuf_last = 2229 (CHDLC_DATA_RX_STATUS_EL_STRUCT *) 2230 card->u.c.rxbuf_base + 2231 (rx_config->number_Rx_status_elements - 1); 2232 2233 /* Set up next pointer to be used */ 2234 card->u.c.txbuf = (void *)(card->hw.dpmbase + 2235 tx_config->next_Tx_status_element_to_use); 2236 card->u.c.rxmb = (void *)(card->hw.dpmbase + 2237 rx_config->next_Rx_status_element_to_use); 2238 } 2239 else { 2240 tx_config = (CHDLC_TX_STATUS_EL_CFG_STRUCT *)(card->hw.dpmbase + 2241 (((CHDLC_CONFIGURATION_STRUCT *)mb->data)-> 2242 ptr_CHDLC_Tx_stat_el_cfg_struct % SDLA_WINDOWSIZE)); 2243 2244 rx_config = (CHDLC_RX_STATUS_EL_CFG_STRUCT *)(card->hw.dpmbase + 2245 (((CHDLC_CONFIGURATION_STRUCT *)mb->data)-> 2246 ptr_CHDLC_Rx_stat_el_cfg_struct % SDLA_WINDOWSIZE)); 2247 2248 /* Setup Head and Tails for buffers */ 2249 card->u.c.txbuf_base = (void *)(card->hw.dpmbase + 2250 (tx_config->base_addr_Tx_status_elements % SDLA_WINDOWSIZE)); 2251 card->u.c.txbuf_last = 2252 (CHDLC_DATA_TX_STATUS_EL_STRUCT *)card->u.c.txbuf_base 2253 + (tx_config->number_Tx_status_elements - 1); 2254 card->u.c.rxbuf_base = (void *)(card->hw.dpmbase + 2255 (rx_config->base_addr_Rx_status_elements % SDLA_WINDOWSIZE)); 2256 card->u.c.rxbuf_last = 2257 (CHDLC_DATA_RX_STATUS_EL_STRUCT *)card->u.c.rxbuf_base 2258 + (rx_config->number_Rx_status_elements - 1); 2259 2260 /* Set up next pointer to be used */ 2261 card->u.c.txbuf = (void *)(card->hw.dpmbase + 2262 (tx_config->next_Tx_status_element_to_use % SDLA_WINDOWSIZE)); 2263 card->u.c.rxmb = (void *)(card->hw.dpmbase + 2264 (rx_config->next_Rx_status_element_to_use % SDLA_WINDOWSIZE)); 2265 } 2266 2267 /* Setup Actual Buffer Start and end addresses */ 2268 card->u.c.rx_base = rx_config->base_addr_Rx_buffer; 2269 card->u.c.rx_top = rx_config->end_addr_Rx_buffer; 2270 2271} 2272 2273/*============================================================================= 2274 * Perform Interrupt Test by running READ_CHDLC_CODE_VERSION command MAX_INTR 2275 * _TEST_COUNTER times. 2276 */ 2277static int intr_test( sdla_t* card) 2278{ 2279 CHDLC_MAILBOX_STRUCT* mb = card->mbox; 2280 int err,i; 2281 2282 Intr_test_counter = 0; 2283 2284 /* The critical flag is unset because during intialization (if_open) 2285 * we want the interrupts to be enabled so that when the wpc_isr is 2286 * called it does not exit due to critical flag set. 2287 */ 2288 2289 err = chdlc_set_intr_mode(card, APP_INT_ON_COMMAND_COMPLETE); 2290 2291 if (err == CMD_OK) { 2292 for (i = 0; i < MAX_INTR_TEST_COUNTER; i ++) { 2293 mb->buffer_length = 0; 2294 mb->command = READ_CHDLC_CODE_VERSION; 2295 err = sdla_exec(mb) ? mb->return_code : CMD_TIMEOUT; 2296 } 2297 } 2298 else { 2299 return err; 2300 } 2301 2302 err = chdlc_set_intr_mode(card, 0); 2303 2304 if (err != CMD_OK) 2305 return err; 2306 2307 return 0; 2308} 2309 2310/*============================================================================== 2311 * Determine what type of UDP call it is. CPIPEAB ? 2312 */ 2313static int udp_pkt_type(struct sk_buff *skb, sdla_t* card) 2314{ 2315 chdlc_udp_pkt_t *chdlc_udp_pkt = (chdlc_udp_pkt_t *)skb->data; 2316 2317 if (!strncmp(chdlc_udp_pkt->wp_mgmt.signature,UDPMGMT_SIGNATURE,8) && 2318 (chdlc_udp_pkt->udp_pkt.udp_dst_port == ntohs(card->wandev.udp_port)) && 2319 (chdlc_udp_pkt->ip_pkt.protocol == UDPMGMT_UDP_PROTOCOL) && 2320 (chdlc_udp_pkt->wp_mgmt.request_reply == UDPMGMT_REQUEST)) { 2321 return UDP_CPIPE_TYPE; 2322 } 2323 else return UDP_INVALID_TYPE; 2324} 2325 2326/*============================================================================ 2327 * Set PORT state. 2328 */ 2329static void port_set_state (sdla_t *card, int state) 2330{ 2331 netdevice_t *dev = card->wandev.dev; 2332 chdlc_private_area_t *chdlc_priv_area = dev->priv; 2333 2334 if (card->u.c.state != state) 2335 { 2336 switch (state) 2337 { 2338 case WAN_CONNECTED: 2339 printk (KERN_INFO "%s: HDLC link connected!\n", 2340 card->devname); 2341 break; 2342 2343 case WAN_CONNECTING: 2344 printk (KERN_INFO "%s: HDLC link connecting...\n", 2345 card->devname); 2346 break; 2347 2348 case WAN_DISCONNECTED: 2349 printk (KERN_INFO "%s: HDLC link disconnected!\n", 2350 card->devname); 2351 break; 2352 } 2353 2354 card->wandev.state = card->u.c.state = state; 2355 chdlc_priv_area->common.state = state; 2356 } 2357} 2358 2359void s508_lock (sdla_t *card, unsigned long *smp_flags) 2360{ 2361#if defined(__SMP__) || defined(LINUX_2_4) 2362 spin_lock_irqsave(&card->wandev.lock, *smp_flags); 2363 if (card->next){ 2364 /* It is ok to use spin_lock here, since we 2365 * already turned off interrupts */ 2366 spin_lock(&card->next->wandev.lock); 2367 } 2368#else 2369 disable_irq(card->hw.irq); 2370#endif 2371} 2372 2373void s508_unlock (sdla_t *card, unsigned long *smp_flags) 2374{ 2375#if defined(__SMP__) || defined(LINUX_2_4) 2376 if (card->next){ 2377 spin_unlock(&card->next->wandev.lock); 2378 } 2379 spin_unlock_irqrestore(&card->wandev.lock, *smp_flags); 2380#else 2381 enable_irq(card->hw.irq); 2382#endif 2383} 2384 2385 2386 2387/*=========================================================================== 2388 * config_chdlc 2389 * 2390 * Configure the chdlc protocol and enable communications. 2391 * 2392 * The if_open() function binds this function to the poll routine. 2393 * Therefore, this function will run every time the chdlc interface 2394 * is brought up. We cannot run this function from the if_open 2395 * because if_open does not have access to the remote IP address. 2396 * 2397 * If the communications are not enabled, proceed to configure 2398 * the card and enable communications. 2399 * 2400 * If the communications are enabled, it means that the interface 2401 * was shutdown by ether the user or driver. In this case, we 2402 * have to check that the IP addresses have not changed. If 2403 * the IP addresses have changed, we have to reconfigure the firmware 2404 * and update the changed IP addresses. Otherwise, just exit. 2405 * 2406 */ 2407 2408static int config_chdlc (sdla_t *card) 2409{ 2410 netdevice_t *dev = card->wandev.dev; 2411 SHARED_MEMORY_INFO_STRUCT *flags = card->u.c.flags; 2412 2413 if (card->u.c.comm_enabled){ 2414 chdlc_comm_disable(card); 2415 port_set_state(card, WAN_DISCONNECTED); 2416 } 2417 2418 if (set_chdlc_config(card)) { 2419 printk(KERN_INFO "%s: CHDLC Configuration Failed!\n", 2420 card->devname); 2421 return 0; 2422 } 2423 init_chdlc_tx_rx_buff(card, dev); 2424 2425 /* Set interrupt mode and mask */ 2426 if (chdlc_set_intr_mode(card, APP_INT_ON_RX_FRAME | 2427 APP_INT_ON_GLOBAL_EXCEP_COND | 2428 APP_INT_ON_TX_FRAME | 2429 APP_INT_ON_CHDLC_EXCEP_COND | APP_INT_ON_TIMER)){ 2430 printk (KERN_INFO "%s: Failed to set interrupt triggers!\n", 2431 card->devname); 2432 return 0; 2433 } 2434 2435 2436 /* Mask the Transmit and Timer interrupt */ 2437 flags->interrupt_info_struct.interrupt_permission &= 2438 ~(APP_INT_ON_TX_FRAME | APP_INT_ON_TIMER); 2439 2440 2441 if (chdlc_comm_enable(card) != 0) { 2442 printk(KERN_INFO "%s: Failed to enable chdlc communications!\n", 2443 card->devname); 2444 flags->interrupt_info_struct.interrupt_permission = 0; 2445 card->u.c.comm_enabled=0; 2446 chdlc_set_intr_mode(card,0); 2447 return 0; 2448 } 2449 2450 /* Initialize Rx/Tx buffer control fields */ 2451 port_set_state(card, WAN_CONNECTING); 2452 return 0; 2453} 2454 2455 2456static void send_ppp_term_request (netdevice_t *dev) 2457{ 2458 struct sk_buff *new_skb; 2459 unsigned char *buf; 2460 2461 if ((new_skb = dev_alloc_skb(8)) != NULL) { 2462 /* copy data into new_skb */ 2463 2464 buf = skb_put(new_skb, 8); 2465 sprintf(buf,"%c%c%c%c%c%c%c%c", 0xFF,0x03,0xC0,0x21,0x05,0x98,0x00,0x07); 2466 2467 /* Decapsulate pkt and pass it up the protocol stack */ 2468 new_skb->protocol = htons(ETH_P_WAN_PPP); 2469 new_skb->dev = dev; 2470 new_skb->mac.raw = new_skb->data; 2471 2472 netif_rx(new_skb); 2473 } 2474} 2475 2476 2477MODULE_LICENSE("GPL"); 2478 2479/****** End ****************************************************************/ 2480