1/* 2 * IrNET protocol module : Synchronous PPP over an IrDA socket. 3 * 4 * Jean II - HPL `00 - <jt@hpl.hp.com> 5 * 6 * This file implement the IRDA interface of IrNET. 7 * Basically, we sit on top of IrTTP. We set up IrTTP, IrIAS properly, 8 * and exchange frames with IrTTP. 9 */ 10 11#include "irnet_irda.h" /* Private header */ 12 13/* 14 * PPP disconnect work: we need to make sure we're in 15 * process context when calling ppp_unregister_channel(). 16 */ 17static void irnet_ppp_disconnect(struct work_struct *work) 18{ 19 irnet_socket * self = 20 container_of(work, irnet_socket, disconnect_work); 21 22 if (self == NULL) 23 return; 24 /* 25 * If we were connected, cleanup & close the PPP 26 * channel, which will kill pppd (hangup) and the rest. 27 */ 28 if (self->ppp_open && !self->ttp_open && !self->ttp_connect) { 29 ppp_unregister_channel(&self->chan); 30 self->ppp_open = 0; 31 } 32} 33 34/************************* CONTROL CHANNEL *************************/ 35/* 36 * When ppp is not active, /dev/irnet act as a control channel. 37 * Writing allow to set up the IrDA destination of the IrNET channel, 38 * and any application may be read events happening on IrNET... 39 */ 40 41/*------------------------------------------------------------------*/ 42/* 43 * Post an event to the control channel... 44 * Put the event in the log, and then wait all process blocked on read 45 * so they can read the log... 46 */ 47static void 48irnet_post_event(irnet_socket * ap, 49 irnet_event event, 50 __u32 saddr, 51 __u32 daddr, 52 char * name, 53 __u16 hints) 54{ 55 int index; /* In the log */ 56 57 DENTER(CTRL_TRACE, "(ap=0x%p, event=%d, daddr=%08x, name=``%s'')\n", 58 ap, event, daddr, name); 59 60 /* Protect this section via spinlock. 61 * Note : as we are the only event producer, we only need to exclude 62 * ourself when touching the log, which is nice and easy. 63 */ 64 spin_lock_bh(&irnet_events.spinlock); 65 66 /* Copy the event in the log */ 67 index = irnet_events.index; 68 irnet_events.log[index].event = event; 69 irnet_events.log[index].daddr = daddr; 70 irnet_events.log[index].saddr = saddr; 71 /* Try to copy IrDA nickname */ 72 if(name) 73 strcpy(irnet_events.log[index].name, name); 74 else 75 irnet_events.log[index].name[0] = '\0'; 76 /* Copy hints */ 77 irnet_events.log[index].hints.word = hints; 78 /* Try to get ppp unit number */ 79 if((ap != (irnet_socket *) NULL) && (ap->ppp_open)) 80 irnet_events.log[index].unit = ppp_unit_number(&ap->chan); 81 else 82 irnet_events.log[index].unit = -1; 83 84 /* Increment the index 85 * Note that we increment the index only after the event is written, 86 * to make sure that the readers don't get garbage... */ 87 irnet_events.index = (index + 1) % IRNET_MAX_EVENTS; 88 89 DEBUG(CTRL_INFO, "New event index is %d\n", irnet_events.index); 90 91 /* Spin lock end */ 92 spin_unlock_bh(&irnet_events.spinlock); 93 94 /* Now : wake up everybody waiting for events... */ 95 wake_up_interruptible_all(&irnet_events.rwait); 96 97 DEXIT(CTRL_TRACE, "\n"); 98} 99 100/************************* IRDA SUBROUTINES *************************/ 101/* 102 * These are a bunch of subroutines called from other functions 103 * down there, mostly common code or to improve readability... 104 * 105 * Note : we duplicate quite heavily some routines of af_irda.c, 106 * because our input structure (self) is quite different 107 * (struct irnet instead of struct irda_sock), which make sharing 108 * the same code impossible (at least, without templates). 109 */ 110 111/*------------------------------------------------------------------*/ 112/* 113 * Function irda_open_tsap (self) 114 * 115 * Open local Transport Service Access Point (TSAP) 116 * 117 * Create a IrTTP instance for us and set all the IrTTP callbacks. 118 */ 119static inline int 120irnet_open_tsap(irnet_socket * self) 121{ 122 notify_t notify; /* Callback structure */ 123 124 DENTER(IRDA_SR_TRACE, "(self=0x%p)\n", self); 125 126 DABORT(self->tsap != NULL, -EBUSY, IRDA_SR_ERROR, "Already busy !\n"); 127 128 /* Initialize IrTTP callbacks to be used by the IrDA stack */ 129 irda_notify_init(¬ify); 130 notify.connect_confirm = irnet_connect_confirm; 131 notify.connect_indication = irnet_connect_indication; 132 notify.disconnect_indication = irnet_disconnect_indication; 133 notify.data_indication = irnet_data_indication; 134 /*notify.udata_indication = NULL;*/ 135 notify.flow_indication = irnet_flow_indication; 136 notify.status_indication = irnet_status_indication; 137 notify.instance = self; 138 strlcpy(notify.name, IRNET_NOTIFY_NAME, sizeof(notify.name)); 139 140 /* Open an IrTTP instance */ 141 self->tsap = irttp_open_tsap(LSAP_ANY, DEFAULT_INITIAL_CREDIT, 142 ¬ify); 143 DABORT(self->tsap == NULL, -ENOMEM, 144 IRDA_SR_ERROR, "Unable to allocate TSAP !\n"); 145 146 /* Remember which TSAP selector we actually got */ 147 self->stsap_sel = self->tsap->stsap_sel; 148 149 DEXIT(IRDA_SR_TRACE, " - tsap=0x%p, sel=0x%X\n", 150 self->tsap, self->stsap_sel); 151 return 0; 152} 153 154/*------------------------------------------------------------------*/ 155/* 156 * Function irnet_ias_to_tsap (self, result, value) 157 * 158 * Examine an IAS object and extract TSAP 159 * 160 * We do an IAP query to find the TSAP associated with the IrNET service. 161 * When IrIAP pass us the result of the query, this function look at 162 * the return values to check for failures and extract the TSAP if 163 * possible. 164 * Also deallocate value 165 * The failure is in self->errno 166 * Return TSAP or -1 167 */ 168static inline __u8 169irnet_ias_to_tsap(irnet_socket * self, 170 int result, 171 struct ias_value * value) 172{ 173 __u8 dtsap_sel = 0; /* TSAP we are looking for */ 174 175 DENTER(IRDA_SR_TRACE, "(self=0x%p)\n", self); 176 177 /* By default, no error */ 178 self->errno = 0; 179 180 /* Check if request succeeded */ 181 switch(result) 182 { 183 /* Standard errors : service not available */ 184 case IAS_CLASS_UNKNOWN: 185 case IAS_ATTRIB_UNKNOWN: 186 DEBUG(IRDA_SR_INFO, "IAS object doesn't exist ! (%d)\n", result); 187 self->errno = -EADDRNOTAVAIL; 188 break; 189 190 /* Other errors, most likely IrDA stack failure */ 191 default : 192 DEBUG(IRDA_SR_INFO, "IAS query failed ! (%d)\n", result); 193 self->errno = -EHOSTUNREACH; 194 break; 195 196 /* Success : we got what we wanted */ 197 case IAS_SUCCESS: 198 break; 199 } 200 201 /* Check what was returned to us */ 202 if(value != NULL) 203 { 204 /* What type of argument have we got ? */ 205 switch(value->type) 206 { 207 case IAS_INTEGER: 208 DEBUG(IRDA_SR_INFO, "result=%d\n", value->t.integer); 209 if(value->t.integer != -1) 210 /* Get the remote TSAP selector */ 211 dtsap_sel = value->t.integer; 212 else 213 self->errno = -EADDRNOTAVAIL; 214 break; 215 default: 216 self->errno = -EADDRNOTAVAIL; 217 DERROR(IRDA_SR_ERROR, "bad type ! (0x%X)\n", value->type); 218 break; 219 } 220 221 /* Cleanup */ 222 irias_delete_value(value); 223 } 224 else /* value == NULL */ 225 { 226 /* Nothing returned to us - usually result != SUCCESS */ 227 if(!(self->errno)) 228 { 229 DERROR(IRDA_SR_ERROR, 230 "IrDA bug : result == SUCCESS && value == NULL\n"); 231 self->errno = -EHOSTUNREACH; 232 } 233 } 234 DEXIT(IRDA_SR_TRACE, "\n"); 235 236 /* Return the TSAP */ 237 return(dtsap_sel); 238} 239 240/*------------------------------------------------------------------*/ 241/* 242 * Function irnet_find_lsap_sel (self) 243 * 244 * Try to lookup LSAP selector in remote LM-IAS 245 * 246 * Basically, we start a IAP query, and then go to sleep. When the query 247 * return, irnet_getvalue_confirm will wake us up, and we can examine the 248 * result of the query... 249 * Note that in some case, the query fail even before we go to sleep, 250 * creating some races... 251 */ 252static inline int 253irnet_find_lsap_sel(irnet_socket * self) 254{ 255 DENTER(IRDA_SR_TRACE, "(self=0x%p)\n", self); 256 257 /* This should not happen */ 258 DABORT(self->iriap, -EBUSY, IRDA_SR_ERROR, "busy with a previous query.\n"); 259 260 /* Create an IAP instance, will be closed in irnet_getvalue_confirm() */ 261 self->iriap = iriap_open(LSAP_ANY, IAS_CLIENT, self, 262 irnet_getvalue_confirm); 263 264 /* Treat unexpected signals as disconnect */ 265 self->errno = -EHOSTUNREACH; 266 267 /* Query remote LM-IAS */ 268 iriap_getvaluebyclass_request(self->iriap, self->rsaddr, self->daddr, 269 IRNET_SERVICE_NAME, IRNET_IAS_VALUE); 270 271 /* The above request is non-blocking. 272 * After a while, IrDA will call us back in irnet_getvalue_confirm() 273 * We will then call irnet_ias_to_tsap() and finish the 274 * connection procedure */ 275 276 DEXIT(IRDA_SR_TRACE, "\n"); 277 return 0; 278} 279 280/*------------------------------------------------------------------*/ 281/* 282 * Function irnet_connect_tsap (self) 283 * 284 * Initialise the TTP socket and initiate TTP connection 285 * 286 */ 287static inline int 288irnet_connect_tsap(irnet_socket * self) 289{ 290 int err; 291 292 DENTER(IRDA_SR_TRACE, "(self=0x%p)\n", self); 293 294 /* Open a local TSAP (an IrTTP instance) */ 295 err = irnet_open_tsap(self); 296 if(err != 0) 297 { 298 clear_bit(0, &self->ttp_connect); 299 DERROR(IRDA_SR_ERROR, "connect aborted!\n"); 300 return(err); 301 } 302 303 /* Connect to remote device */ 304 err = irttp_connect_request(self->tsap, self->dtsap_sel, 305 self->rsaddr, self->daddr, NULL, 306 self->max_sdu_size_rx, NULL); 307 if(err != 0) 308 { 309 clear_bit(0, &self->ttp_connect); 310 DERROR(IRDA_SR_ERROR, "connect aborted!\n"); 311 return(err); 312 } 313 314 /* The above call is non-blocking. 315 * After a while, the IrDA stack will either call us back in 316 * irnet_connect_confirm() or irnet_disconnect_indication() 317 * See you there ;-) */ 318 319 DEXIT(IRDA_SR_TRACE, "\n"); 320 return(err); 321} 322 323/*------------------------------------------------------------------*/ 324/* 325 * Function irnet_discover_next_daddr (self) 326 * 327 * Query the IrNET TSAP of the next device in the log. 328 * 329 * Used in the TSAP discovery procedure. 330 */ 331static inline int 332irnet_discover_next_daddr(irnet_socket * self) 333{ 334 /* Close the last instance of IrIAP, and open a new one. 335 * We can't reuse the IrIAP instance in the IrIAP callback */ 336 if(self->iriap) 337 { 338 iriap_close(self->iriap); 339 self->iriap = NULL; 340 } 341 /* Create a new IAP instance */ 342 self->iriap = iriap_open(LSAP_ANY, IAS_CLIENT, self, 343 irnet_discovervalue_confirm); 344 if(self->iriap == NULL) 345 return -ENOMEM; 346 347 /* Next discovery - before the call to avoid races */ 348 self->disco_index++; 349 350 /* Check if we have one more address to try */ 351 if(self->disco_index < self->disco_number) 352 { 353 /* Query remote LM-IAS */ 354 iriap_getvaluebyclass_request(self->iriap, 355 self->discoveries[self->disco_index].saddr, 356 self->discoveries[self->disco_index].daddr, 357 IRNET_SERVICE_NAME, IRNET_IAS_VALUE); 358 /* The above request is non-blocking. 359 * After a while, IrDA will call us back in irnet_discovervalue_confirm() 360 * We will then call irnet_ias_to_tsap() and come back here again... */ 361 return(0); 362 } 363 else 364 return(1); 365} 366 367/*------------------------------------------------------------------*/ 368/* 369 * Function irnet_discover_daddr_and_lsap_sel (self) 370 * 371 * This try to find a device with the requested service. 372 * 373 * Initiate a TSAP discovery procedure. 374 * It basically look into the discovery log. For each address in the list, 375 * it queries the LM-IAS of the device to find if this device offer 376 * the requested service. 377 * If there is more than one node supporting the service, we complain 378 * to the user (it should move devices around). 379 * If we find one node which have the requested TSAP, we connect to it. 380 * 381 * This function just start the whole procedure. It request the discovery 382 * log and submit the first IAS query. 383 * The bulk of the job is handled in irnet_discovervalue_confirm() 384 * 385 * Note : this procedure fails if there is more than one device in range 386 * on the same dongle, because IrLMP doesn't disconnect the LAP when the 387 * last LSAP is closed. Moreover, we would need to wait the LAP 388 * disconnection... 389 */ 390static inline int 391irnet_discover_daddr_and_lsap_sel(irnet_socket * self) 392{ 393 int ret; 394 395 DENTER(IRDA_SR_TRACE, "(self=0x%p)\n", self); 396 397 /* Ask lmp for the current discovery log */ 398 self->discoveries = irlmp_get_discoveries(&self->disco_number, self->mask, 399 DISCOVERY_DEFAULT_SLOTS); 400 401 /* Check if the we got some results */ 402 if(self->discoveries == NULL) 403 { 404 self->disco_number = -1; 405 clear_bit(0, &self->ttp_connect); 406 DRETURN(-ENETUNREACH, IRDA_SR_INFO, "No Cachelog...\n"); 407 } 408 DEBUG(IRDA_SR_INFO, "Got the log (0x%p), size is %d\n", 409 self->discoveries, self->disco_number); 410 411 /* Start with the first discovery */ 412 self->disco_index = -1; 413 self->daddr = DEV_ADDR_ANY; 414 415 /* This will fail if the log is empty - this is non-blocking */ 416 ret = irnet_discover_next_daddr(self); 417 if(ret) 418 { 419 /* Close IAP */ 420 if(self->iriap) 421 iriap_close(self->iriap); 422 self->iriap = NULL; 423 424 /* Cleanup our copy of the discovery log */ 425 kfree(self->discoveries); 426 self->discoveries = NULL; 427 428 clear_bit(0, &self->ttp_connect); 429 DRETURN(-ENETUNREACH, IRDA_SR_INFO, "Cachelog empty...\n"); 430 } 431 432 /* Follow me in irnet_discovervalue_confirm() */ 433 434 DEXIT(IRDA_SR_TRACE, "\n"); 435 return(0); 436} 437 438/*------------------------------------------------------------------*/ 439/* 440 * Function irnet_dname_to_daddr (self) 441 * 442 * Convert an IrDA nickname to a valid IrDA address 443 * 444 * It basically look into the discovery log until there is a match. 445 */ 446static inline int 447irnet_dname_to_daddr(irnet_socket * self) 448{ 449 struct irda_device_info *discoveries; /* Copy of the discovery log */ 450 int number; /* Number of nodes in the log */ 451 int i; 452 453 DENTER(IRDA_SR_TRACE, "(self=0x%p)\n", self); 454 455 /* Ask lmp for the current discovery log */ 456 discoveries = irlmp_get_discoveries(&number, 0xffff, 457 DISCOVERY_DEFAULT_SLOTS); 458 /* Check if the we got some results */ 459 if(discoveries == NULL) 460 DRETURN(-ENETUNREACH, IRDA_SR_INFO, "Cachelog empty...\n"); 461 462 /* 463 * Now, check all discovered devices (if any), and connect 464 * client only about the services that the client is 465 * interested in... 466 */ 467 for(i = 0; i < number; i++) 468 { 469 /* Does the name match ? */ 470 if(!strncmp(discoveries[i].info, self->rname, NICKNAME_MAX_LEN)) 471 { 472 /* Yes !!! Get it.. */ 473 self->daddr = discoveries[i].daddr; 474 DEBUG(IRDA_SR_INFO, "discovered device ``%s'' at address 0x%08x.\n", 475 self->rname, self->daddr); 476 kfree(discoveries); 477 DEXIT(IRDA_SR_TRACE, "\n"); 478 return 0; 479 } 480 } 481 /* No luck ! */ 482 DEBUG(IRDA_SR_INFO, "cannot discover device ``%s'' !!!\n", self->rname); 483 kfree(discoveries); 484 return(-EADDRNOTAVAIL); 485} 486 487 488/************************* SOCKET ROUTINES *************************/ 489/* 490 * This are the main operations on IrNET sockets, basically to create 491 * and destroy IrNET sockets. These are called from the PPP part... 492 */ 493 494/*------------------------------------------------------------------*/ 495/* 496 * Create a IrNET instance : just initialise some parameters... 497 */ 498int 499irda_irnet_create(irnet_socket * self) 500{ 501 DENTER(IRDA_SOCK_TRACE, "(self=0x%p)\n", self); 502 503 self->magic = IRNET_MAGIC; /* Paranoia */ 504 505 self->ttp_open = 0; /* Prevent higher layer from accessing IrTTP */ 506 self->ttp_connect = 0; /* Not connecting yet */ 507 self->rname[0] = '\0'; /* May be set via control channel */ 508 self->rdaddr = DEV_ADDR_ANY; /* May be set via control channel */ 509 self->rsaddr = DEV_ADDR_ANY; /* May be set via control channel */ 510 self->daddr = DEV_ADDR_ANY; /* Until we get connected */ 511 self->saddr = DEV_ADDR_ANY; /* Until we get connected */ 512 self->max_sdu_size_rx = TTP_SAR_UNBOUND; 513 514 /* Register as a client with IrLMP */ 515 self->ckey = irlmp_register_client(0, NULL, NULL, NULL); 516#ifdef DISCOVERY_NOMASK 517 self->mask = 0xffff; /* For W2k compatibility */ 518#else /* DISCOVERY_NOMASK */ 519 self->mask = irlmp_service_to_hint(S_LAN); 520#endif /* DISCOVERY_NOMASK */ 521 self->tx_flow = FLOW_START; /* Flow control from IrTTP */ 522 523 INIT_WORK(&self->disconnect_work, irnet_ppp_disconnect); 524 525 DEXIT(IRDA_SOCK_TRACE, "\n"); 526 return(0); 527} 528 529/*------------------------------------------------------------------*/ 530/* 531 * Connect to the other side : 532 * o convert device name to an address 533 * o find the socket number (dlsap) 534 * o Establish the connection 535 * 536 * Note : We no longer mimic af_irda. The IAS query for finding the TSAP 537 * is done asynchronously, like the TTP connection. This allow us to 538 * call this function from any context (not only process). 539 * The downside is that following what's happening in there is tricky 540 * because it involve various functions all over the place... 541 */ 542int 543irda_irnet_connect(irnet_socket * self) 544{ 545 int err; 546 547 DENTER(IRDA_SOCK_TRACE, "(self=0x%p)\n", self); 548 549 /* Check if we are already trying to connect. 550 * Because irda_irnet_connect() can be called directly by pppd plus 551 * packet retries in ppp_generic and connect may take time, plus we may 552 * race with irnet_connect_indication(), we need to be careful there... */ 553 if(test_and_set_bit(0, &self->ttp_connect)) 554 DRETURN(-EBUSY, IRDA_SOCK_INFO, "Already connecting...\n"); 555 if((self->iriap != NULL) || (self->tsap != NULL)) 556 DERROR(IRDA_SOCK_ERROR, "Socket not cleaned up...\n"); 557 558 /* Insert ourselves in the hashbin so that the IrNET server can find us. 559 * Notes : 4th arg is string of 32 char max and must be null terminated 560 * When 4th arg is used (string), 3rd arg isn't (int) 561 * Can't re-insert (MUST remove first) so check for that... */ 562 if((irnet_server.running) && (self->q.q_next == NULL)) 563 { 564 spin_lock_bh(&irnet_server.spinlock); 565 hashbin_insert(irnet_server.list, (irda_queue_t *) self, 0, self->rname); 566 spin_unlock_bh(&irnet_server.spinlock); 567 DEBUG(IRDA_SOCK_INFO, "Inserted ``%s'' in hashbin...\n", self->rname); 568 } 569 570 /* If we don't have anything (no address, no name) */ 571 if((self->rdaddr == DEV_ADDR_ANY) && (self->rname[0] == '\0')) 572 { 573 /* Try to find a suitable address */ 574 if((err = irnet_discover_daddr_and_lsap_sel(self)) != 0) 575 DRETURN(err, IRDA_SOCK_INFO, "auto-connect failed!\n"); 576 /* In most cases, the call above is non-blocking */ 577 } 578 else 579 { 580 /* If we have only the name (no address), try to get an address */ 581 if(self->rdaddr == DEV_ADDR_ANY) 582 { 583 if((err = irnet_dname_to_daddr(self)) != 0) 584 DRETURN(err, IRDA_SOCK_INFO, "name connect failed!\n"); 585 } 586 else 587 /* Use the requested destination address */ 588 self->daddr = self->rdaddr; 589 590 /* Query remote LM-IAS to find LSAP selector */ 591 irnet_find_lsap_sel(self); 592 /* The above call is non blocking */ 593 } 594 595 /* At this point, we are waiting for the IrDA stack to call us back, 596 * or we have already failed. 597 * We will finish the connection procedure in irnet_connect_tsap(). 598 */ 599 DEXIT(IRDA_SOCK_TRACE, "\n"); 600 return(0); 601} 602 603/*------------------------------------------------------------------*/ 604/* 605 * Function irda_irnet_destroy(self) 606 * 607 * Destroy irnet instance 608 * 609 * Note : this need to be called from a process context. 610 */ 611void 612irda_irnet_destroy(irnet_socket * self) 613{ 614 DENTER(IRDA_SOCK_TRACE, "(self=0x%p)\n", self); 615 if(self == NULL) 616 return; 617 618 /* Remove ourselves from hashbin (if we are queued in hashbin) 619 * Note : `irnet_server.running' protect us from calls in hashbin_delete() */ 620 if((irnet_server.running) && (self->q.q_next != NULL)) 621 { 622 struct irnet_socket * entry; 623 DEBUG(IRDA_SOCK_INFO, "Removing from hash..\n"); 624 spin_lock_bh(&irnet_server.spinlock); 625 entry = hashbin_remove_this(irnet_server.list, (irda_queue_t *) self); 626 self->q.q_next = NULL; 627 spin_unlock_bh(&irnet_server.spinlock); 628 DASSERT(entry == self, , IRDA_SOCK_ERROR, "Can't remove from hash.\n"); 629 } 630 631 /* If we were connected, post a message */ 632 if(test_bit(0, &self->ttp_open)) 633 { 634 /* Note : as the disconnect comes from ppp_generic, the unit number 635 * doesn't exist anymore when we post the event, so we need to pass 636 * NULL as the first arg... */ 637 irnet_post_event(NULL, IRNET_DISCONNECT_TO, 638 self->saddr, self->daddr, self->rname, 0); 639 } 640 641 /* Prevent various IrDA callbacks from messing up things 642 * Need to be first */ 643 clear_bit(0, &self->ttp_connect); 644 645 /* Prevent higher layer from accessing IrTTP */ 646 clear_bit(0, &self->ttp_open); 647 648 /* Unregister with IrLMP */ 649 irlmp_unregister_client(self->ckey); 650 651 /* Unregister with LM-IAS */ 652 if(self->iriap) 653 { 654 iriap_close(self->iriap); 655 self->iriap = NULL; 656 } 657 658 /* Cleanup eventual discoveries from connection attempt or control channel */ 659 if(self->discoveries != NULL) 660 { 661 /* Cleanup our copy of the discovery log */ 662 kfree(self->discoveries); 663 self->discoveries = NULL; 664 } 665 666 /* Close our IrTTP connection */ 667 if(self->tsap) 668 { 669 DEBUG(IRDA_SOCK_INFO, "Closing our TTP connection.\n"); 670 irttp_disconnect_request(self->tsap, NULL, P_NORMAL); 671 irttp_close_tsap(self->tsap); 672 self->tsap = NULL; 673 } 674 self->stsap_sel = 0; 675 676 DEXIT(IRDA_SOCK_TRACE, "\n"); 677 return; 678} 679 680 681/************************** SERVER SOCKET **************************/ 682/* 683 * The IrNET service is composed of one server socket and a variable 684 * number of regular IrNET sockets. The server socket is supposed to 685 * handle incoming connections and redirect them to one IrNET sockets. 686 * It's a superset of the regular IrNET socket, but has a very distinct 687 * behaviour... 688 */ 689 690/*------------------------------------------------------------------*/ 691/* 692 * Function irnet_daddr_to_dname (self) 693 * 694 * Convert an IrDA address to a IrDA nickname 695 * 696 * It basically look into the discovery log until there is a match. 697 */ 698static inline int 699irnet_daddr_to_dname(irnet_socket * self) 700{ 701 struct irda_device_info *discoveries; /* Copy of the discovery log */ 702 int number; /* Number of nodes in the log */ 703 int i; 704 705 DENTER(IRDA_SERV_TRACE, "(self=0x%p)\n", self); 706 707 /* Ask lmp for the current discovery log */ 708 discoveries = irlmp_get_discoveries(&number, 0xffff, 709 DISCOVERY_DEFAULT_SLOTS); 710 /* Check if the we got some results */ 711 if (discoveries == NULL) 712 DRETURN(-ENETUNREACH, IRDA_SERV_INFO, "Cachelog empty...\n"); 713 714 /* Now, check all discovered devices (if any) */ 715 for(i = 0; i < number; i++) 716 { 717 /* Does the name match ? */ 718 if(discoveries[i].daddr == self->daddr) 719 { 720 /* Yes !!! Get it.. */ 721 strlcpy(self->rname, discoveries[i].info, sizeof(self->rname)); 722 self->rname[sizeof(self->rname) - 1] = '\0'; 723 DEBUG(IRDA_SERV_INFO, "Device 0x%08x is in fact ``%s''.\n", 724 self->daddr, self->rname); 725 kfree(discoveries); 726 DEXIT(IRDA_SERV_TRACE, "\n"); 727 return 0; 728 } 729 } 730 /* No luck ! */ 731 DEXIT(IRDA_SERV_INFO, ": cannot discover device 0x%08x !!!\n", self->daddr); 732 kfree(discoveries); 733 return(-EADDRNOTAVAIL); 734} 735 736/*------------------------------------------------------------------*/ 737/* 738 * Function irda_find_socket (self) 739 * 740 * Find the correct IrNET socket 741 * 742 * Look into the list of IrNET sockets and finds one with the right 743 * properties... 744 */ 745static inline irnet_socket * 746irnet_find_socket(irnet_socket * self) 747{ 748 irnet_socket * new = (irnet_socket *) NULL; 749 int err; 750 751 DENTER(IRDA_SERV_TRACE, "(self=0x%p)\n", self); 752 753 /* Get the addresses of the requester */ 754 self->daddr = irttp_get_daddr(self->tsap); 755 self->saddr = irttp_get_saddr(self->tsap); 756 757 /* Try to get the IrDA nickname of the requester */ 758 err = irnet_daddr_to_dname(self); 759 760 /* Protect access to the instance list */ 761 spin_lock_bh(&irnet_server.spinlock); 762 763 /* So now, try to get an socket having specifically 764 * requested that nickname */ 765 if(err == 0) 766 { 767 new = (irnet_socket *) hashbin_find(irnet_server.list, 768 0, self->rname); 769 if(new) 770 DEBUG(IRDA_SERV_INFO, "Socket 0x%p matches rname ``%s''.\n", 771 new, new->rname); 772 } 773 774 /* If no name matches, try to find an socket by the destination address */ 775 /* It can be either the requested destination address (set via the 776 * control channel), or the current destination address if the 777 * socket is in the middle of a connection request */ 778 if(new == (irnet_socket *) NULL) 779 { 780 new = (irnet_socket *) hashbin_get_first(irnet_server.list); 781 while(new !=(irnet_socket *) NULL) 782 { 783 /* Does it have the same address ? */ 784 if((new->rdaddr == self->daddr) || (new->daddr == self->daddr)) 785 { 786 /* Yes !!! Get it.. */ 787 DEBUG(IRDA_SERV_INFO, "Socket 0x%p matches daddr %#08x.\n", 788 new, self->daddr); 789 break; 790 } 791 new = (irnet_socket *) hashbin_get_next(irnet_server.list); 792 } 793 } 794 795 /* If we don't have any socket, get the first unconnected socket */ 796 if(new == (irnet_socket *) NULL) 797 { 798 new = (irnet_socket *) hashbin_get_first(irnet_server.list); 799 while(new !=(irnet_socket *) NULL) 800 { 801 /* Is it available ? */ 802 if(!(test_bit(0, &new->ttp_open)) && (new->rdaddr == DEV_ADDR_ANY) && 803 (new->rname[0] == '\0') && (new->ppp_open)) 804 { 805 /* Yes !!! Get it.. */ 806 DEBUG(IRDA_SERV_INFO, "Socket 0x%p is free.\n", 807 new); 808 break; 809 } 810 new = (irnet_socket *) hashbin_get_next(irnet_server.list); 811 } 812 } 813 814 /* Spin lock end */ 815 spin_unlock_bh(&irnet_server.spinlock); 816 817 DEXIT(IRDA_SERV_TRACE, " - new = 0x%p\n", new); 818 return new; 819} 820 821/*------------------------------------------------------------------*/ 822/* 823 * Function irda_connect_socket (self) 824 * 825 * Connect an incoming connection to the socket 826 * 827 */ 828static inline int 829irnet_connect_socket(irnet_socket * server, 830 irnet_socket * new, 831 struct qos_info * qos, 832 __u32 max_sdu_size, 833 __u8 max_header_size) 834{ 835 DENTER(IRDA_SERV_TRACE, "(server=0x%p, new=0x%p)\n", 836 server, new); 837 838 /* Now attach up the new socket */ 839 new->tsap = irttp_dup(server->tsap, new); 840 DABORT(new->tsap == NULL, -1, IRDA_SERV_ERROR, "dup failed!\n"); 841 842 /* Set up all the relevant parameters on the new socket */ 843 new->stsap_sel = new->tsap->stsap_sel; 844 new->dtsap_sel = new->tsap->dtsap_sel; 845 new->saddr = irttp_get_saddr(new->tsap); 846 new->daddr = irttp_get_daddr(new->tsap); 847 848 new->max_header_size = max_header_size; 849 new->max_sdu_size_tx = max_sdu_size; 850 new->max_data_size = max_sdu_size; 851#ifdef STREAM_COMPAT 852 /* If we want to receive "stream sockets" */ 853 if(max_sdu_size == 0) 854 new->max_data_size = irttp_get_max_seg_size(new->tsap); 855#endif /* STREAM_COMPAT */ 856 857 /* Clean up the original one to keep it in listen state */ 858 irttp_listen(server->tsap); 859 860 /* Send a connection response on the new socket */ 861 irttp_connect_response(new->tsap, new->max_sdu_size_rx, NULL); 862 863 /* Allow PPP to send its junk over the new socket... */ 864 set_bit(0, &new->ttp_open); 865 866 /* Not connecting anymore, and clean up last possible remains 867 * of connection attempts on the socket */ 868 clear_bit(0, &new->ttp_connect); 869 if(new->iriap) 870 { 871 iriap_close(new->iriap); 872 new->iriap = NULL; 873 } 874 if(new->discoveries != NULL) 875 { 876 kfree(new->discoveries); 877 new->discoveries = NULL; 878 } 879 880#ifdef CONNECT_INDIC_KICK 881 /* As currently we don't block packets in ppp_irnet_send() while passive, 882 * this is not really needed... 883 * Also, not doing it give IrDA a chance to finish the setup properly 884 * before being swamped with packets... */ 885 ppp_output_wakeup(&new->chan); 886#endif /* CONNECT_INDIC_KICK */ 887 888 /* Notify the control channel */ 889 irnet_post_event(new, IRNET_CONNECT_FROM, 890 new->saddr, new->daddr, server->rname, 0); 891 892 DEXIT(IRDA_SERV_TRACE, "\n"); 893 return 0; 894} 895 896/*------------------------------------------------------------------*/ 897/* 898 * Function irda_disconnect_server (self) 899 * 900 * Cleanup the server socket when the incoming connection abort 901 * 902 */ 903static inline void 904irnet_disconnect_server(irnet_socket * self, 905 struct sk_buff *skb) 906{ 907 DENTER(IRDA_SERV_TRACE, "(self=0x%p)\n", self); 908 909 /* Put the received packet in the black hole */ 910 kfree_skb(skb); 911 912#ifdef FAIL_SEND_DISCONNECT 913 /* Tell the other party we don't want to be connected */ 914 /* Hum... Is it the right thing to do ? And do we need to send 915 * a connect response before ? It looks ok without this... */ 916 irttp_disconnect_request(self->tsap, NULL, P_NORMAL); 917#endif /* FAIL_SEND_DISCONNECT */ 918 919 /* Notify the control channel (see irnet_find_socket()) */ 920 irnet_post_event(NULL, IRNET_REQUEST_FROM, 921 self->saddr, self->daddr, self->rname, 0); 922 923 /* Clean up the server to keep it in listen state */ 924 irttp_listen(self->tsap); 925 926 DEXIT(IRDA_SERV_TRACE, "\n"); 927 return; 928} 929 930/*------------------------------------------------------------------*/ 931/* 932 * Function irda_setup_server (self) 933 * 934 * Create a IrTTP server and set it up... 935 * 936 * Register the IrLAN hint bit, create a IrTTP instance for us, 937 * set all the IrTTP callbacks and create an IrIAS entry... 938 */ 939static inline int 940irnet_setup_server(void) 941{ 942 __u16 hints; 943 944 DENTER(IRDA_SERV_TRACE, "()\n"); 945 946 /* Initialise the regular socket part of the server */ 947 irda_irnet_create(&irnet_server.s); 948 949 /* Open a local TSAP (an IrTTP instance) for the server */ 950 irnet_open_tsap(&irnet_server.s); 951 952 /* PPP part setup */ 953 irnet_server.s.ppp_open = 0; 954 irnet_server.s.chan.private = NULL; 955 irnet_server.s.file = NULL; 956 957 /* Get the hint bit corresponding to IrLAN */ 958 /* Note : we overload the IrLAN hint bit. As it is only a "hint", and as 959 * we provide roughly the same functionality as IrLAN, this is ok. 960 * In fact, the situation is similar as JetSend overloading the Obex hint 961 */ 962 hints = irlmp_service_to_hint(S_LAN); 963 964#ifdef ADVERTISE_HINT 965 /* Register with IrLMP as a service (advertise our hint bit) */ 966 irnet_server.skey = irlmp_register_service(hints); 967#endif /* ADVERTISE_HINT */ 968 969 /* Register with LM-IAS (so that people can connect to us) */ 970 irnet_server.ias_obj = irias_new_object(IRNET_SERVICE_NAME, jiffies); 971 irias_add_integer_attrib(irnet_server.ias_obj, IRNET_IAS_VALUE, 972 irnet_server.s.stsap_sel, IAS_KERNEL_ATTR); 973 irias_insert_object(irnet_server.ias_obj); 974 975#ifdef DISCOVERY_EVENTS 976 /* Tell IrLMP we want to be notified of newly discovered nodes */ 977 irlmp_update_client(irnet_server.s.ckey, hints, 978 irnet_discovery_indication, irnet_expiry_indication, 979 (void *) &irnet_server.s); 980#endif 981 982 DEXIT(IRDA_SERV_TRACE, " - self=0x%p\n", &irnet_server.s); 983 return 0; 984} 985 986/*------------------------------------------------------------------*/ 987/* 988 * Function irda_destroy_server (self) 989 * 990 * Destroy the IrTTP server... 991 * 992 * Reverse of the previous function... 993 */ 994static inline void 995irnet_destroy_server(void) 996{ 997 DENTER(IRDA_SERV_TRACE, "()\n"); 998 999#ifdef ADVERTISE_HINT 1000 /* Unregister with IrLMP */ 1001 irlmp_unregister_service(irnet_server.skey); 1002#endif /* ADVERTISE_HINT */ 1003 1004 /* Unregister with LM-IAS */ 1005 if(irnet_server.ias_obj) 1006 irias_delete_object(irnet_server.ias_obj); 1007 1008 /* Cleanup the socket part */ 1009 irda_irnet_destroy(&irnet_server.s); 1010 1011 DEXIT(IRDA_SERV_TRACE, "\n"); 1012 return; 1013} 1014 1015 1016/************************ IRDA-TTP CALLBACKS ************************/ 1017/* 1018 * When we create a IrTTP instance, we pass to it a set of callbacks 1019 * that IrTTP will call in case of various events. 1020 * We take care of those events here. 1021 */ 1022 1023/*------------------------------------------------------------------*/ 1024/* 1025 * Function irnet_data_indication (instance, sap, skb) 1026 * 1027 * Received some data from TinyTP. Just queue it on the receive queue 1028 * 1029 */ 1030static int 1031irnet_data_indication(void * instance, 1032 void * sap, 1033 struct sk_buff *skb) 1034{ 1035 irnet_socket * ap = (irnet_socket *) instance; 1036 unsigned char * p; 1037 int code = 0; 1038 1039 DENTER(IRDA_TCB_TRACE, "(self/ap=0x%p, skb=0x%p)\n", 1040 ap, skb); 1041 DASSERT(skb != NULL, 0, IRDA_CB_ERROR, "skb is NULL !!!\n"); 1042 1043 /* Check is ppp is ready to receive our packet */ 1044 if(!ap->ppp_open) 1045 { 1046 DERROR(IRDA_CB_ERROR, "PPP not ready, dropping packet...\n"); 1047 /* When we return error, TTP will need to requeue the skb and 1048 * will stop the sender. IrTTP will stall until we send it a 1049 * flow control request... */ 1050 return -ENOMEM; 1051 } 1052 1053 /* strip address/control field if present */ 1054 p = skb->data; 1055 if((p[0] == PPP_ALLSTATIONS) && (p[1] == PPP_UI)) 1056 { 1057 /* chop off address/control */ 1058 if(skb->len < 3) 1059 goto err_exit; 1060 p = skb_pull(skb, 2); 1061 } 1062 1063 /* decompress protocol field if compressed */ 1064 if(p[0] & 1) 1065 { 1066 /* protocol is compressed */ 1067 skb_push(skb, 1)[0] = 0; 1068 } 1069 else 1070 if(skb->len < 2) 1071 goto err_exit; 1072 1073 /* pass to generic ppp layer */ 1074 /* Note : how do I know if ppp can accept or not the packet ? This is 1075 * essential if I want to manage flow control smoothly... */ 1076 ppp_input(&ap->chan, skb); 1077 1078 DEXIT(IRDA_TCB_TRACE, "\n"); 1079 return 0; 1080 1081 err_exit: 1082 DERROR(IRDA_CB_ERROR, "Packet too small, dropping...\n"); 1083 kfree_skb(skb); 1084 ppp_input_error(&ap->chan, code); 1085 return 0; /* Don't return an error code, only for flow control... */ 1086} 1087 1088/*------------------------------------------------------------------*/ 1089/* 1090 * Function irnet_disconnect_indication (instance, sap, reason, skb) 1091 * 1092 * Connection has been closed. Chech reason to find out why 1093 * 1094 * Note : there are many cases where we come here : 1095 * o attempted to connect, timeout 1096 * o connected, link is broken, LAP has timeout 1097 * o connected, other side close the link 1098 * o connection request on the server not handled 1099 */ 1100static void 1101irnet_disconnect_indication(void * instance, 1102 void * sap, 1103 LM_REASON reason, 1104 struct sk_buff *skb) 1105{ 1106 irnet_socket * self = (irnet_socket *) instance; 1107 int test_open; 1108 int test_connect; 1109 1110 DENTER(IRDA_TCB_TRACE, "(self=0x%p)\n", self); 1111 DASSERT(self != NULL, , IRDA_CB_ERROR, "Self is NULL !!!\n"); 1112 1113 /* Don't care about it, but let's not leak it */ 1114 if(skb) 1115 dev_kfree_skb(skb); 1116 1117 /* Prevent higher layer from accessing IrTTP */ 1118 test_open = test_and_clear_bit(0, &self->ttp_open); 1119 /* Not connecting anymore... 1120 * (note : TSAP is open, so IAP callbacks are no longer pending...) */ 1121 test_connect = test_and_clear_bit(0, &self->ttp_connect); 1122 1123 /* If both self->ttp_open and self->ttp_connect are NULL, it mean that we 1124 * have a race condition with irda_irnet_destroy() or 1125 * irnet_connect_indication(), so don't mess up tsap... 1126 */ 1127 if(!(test_open || test_connect)) 1128 { 1129 DERROR(IRDA_CB_ERROR, "Race condition detected...\n"); 1130 return; 1131 } 1132 1133 /* If we were active, notify the control channel */ 1134 if(test_open) 1135 irnet_post_event(self, IRNET_DISCONNECT_FROM, 1136 self->saddr, self->daddr, self->rname, 0); 1137 else 1138 /* If we were trying to connect, notify the control channel */ 1139 if((self->tsap) && (self != &irnet_server.s)) 1140 irnet_post_event(self, IRNET_NOANSWER_FROM, 1141 self->saddr, self->daddr, self->rname, 0); 1142 1143 /* Close our IrTTP connection, cleanup tsap */ 1144 if((self->tsap) && (self != &irnet_server.s)) 1145 { 1146 DEBUG(IRDA_CB_INFO, "Closing our TTP connection.\n"); 1147 irttp_close_tsap(self->tsap); 1148 self->tsap = NULL; 1149 } 1150 /* Cleanup the socket in case we want to reconnect in ppp_output_wakeup() */ 1151 self->stsap_sel = 0; 1152 self->daddr = DEV_ADDR_ANY; 1153 self->tx_flow = FLOW_START; 1154 1155 /* Deal with the ppp instance if it's still alive */ 1156 if(self->ppp_open) 1157 { 1158 if(test_open) 1159 { 1160 /* ppp_unregister_channel() wants a user context. */ 1161 schedule_work(&self->disconnect_work); 1162 } 1163 else 1164 { 1165 /* If we were trying to connect, flush (drain) ppp_generic 1166 * Tx queue (most often we have blocked it), which will 1167 * trigger an other attempt to connect. If we are passive, 1168 * this will empty the Tx queue after last try. */ 1169 ppp_output_wakeup(&self->chan); 1170 } 1171 } 1172 1173 DEXIT(IRDA_TCB_TRACE, "\n"); 1174} 1175 1176/*------------------------------------------------------------------*/ 1177/* 1178 * Function irnet_connect_confirm (instance, sap, qos, max_sdu_size, skb) 1179 * 1180 * Connections has been confirmed by the remote device 1181 * 1182 */ 1183static void 1184irnet_connect_confirm(void * instance, 1185 void * sap, 1186 struct qos_info *qos, 1187 __u32 max_sdu_size, 1188 __u8 max_header_size, 1189 struct sk_buff *skb) 1190{ 1191 irnet_socket * self = (irnet_socket *) instance; 1192 1193 DENTER(IRDA_TCB_TRACE, "(self=0x%p)\n", self); 1194 1195 /* Check if socket is closing down (via irda_irnet_destroy()) */ 1196 if(! test_bit(0, &self->ttp_connect)) 1197 { 1198 DERROR(IRDA_CB_ERROR, "Socket no longer connecting. Ouch !\n"); 1199 return; 1200 } 1201 1202 /* How much header space do we need to reserve */ 1203 self->max_header_size = max_header_size; 1204 1205 /* IrTTP max SDU size in transmit direction */ 1206 self->max_sdu_size_tx = max_sdu_size; 1207 self->max_data_size = max_sdu_size; 1208#ifdef STREAM_COMPAT 1209 if(max_sdu_size == 0) 1210 self->max_data_size = irttp_get_max_seg_size(self->tsap); 1211#endif /* STREAM_COMPAT */ 1212 1213 /* At this point, IrLMP has assigned our source address */ 1214 self->saddr = irttp_get_saddr(self->tsap); 1215 1216 /* Allow higher layer to access IrTTP */ 1217 set_bit(0, &self->ttp_open); 1218 clear_bit(0, &self->ttp_connect); /* Not racy, IrDA traffic is serial */ 1219 /* Give a kick in the ass of ppp_generic so that he sends us some data */ 1220 ppp_output_wakeup(&self->chan); 1221 1222 /* Check size of received packet */ 1223 if(skb->len > 0) 1224 { 1225#ifdef PASS_CONNECT_PACKETS 1226 DEBUG(IRDA_CB_INFO, "Passing connect packet to PPP.\n"); 1227 /* Try to pass it to PPP */ 1228 irnet_data_indication(instance, sap, skb); 1229#else /* PASS_CONNECT_PACKETS */ 1230 DERROR(IRDA_CB_ERROR, "Dropping non empty packet.\n"); 1231 kfree_skb(skb); /* Note : will be optimised with other kfree... */ 1232#endif /* PASS_CONNECT_PACKETS */ 1233 } 1234 else 1235 kfree_skb(skb); 1236 1237 /* Notify the control channel */ 1238 irnet_post_event(self, IRNET_CONNECT_TO, 1239 self->saddr, self->daddr, self->rname, 0); 1240 1241 DEXIT(IRDA_TCB_TRACE, "\n"); 1242} 1243 1244/*------------------------------------------------------------------*/ 1245/* 1246 * Function irnet_flow_indication (instance, sap, flow) 1247 * 1248 * Used by TinyTP to tell us if it can accept more data or not 1249 * 1250 */ 1251static void 1252irnet_flow_indication(void * instance, 1253 void * sap, 1254 LOCAL_FLOW flow) 1255{ 1256 irnet_socket * self = (irnet_socket *) instance; 1257 LOCAL_FLOW oldflow = self->tx_flow; 1258 1259 DENTER(IRDA_TCB_TRACE, "(self=0x%p, flow=%d)\n", self, flow); 1260 1261 /* Update our state */ 1262 self->tx_flow = flow; 1263 1264 /* Check what IrTTP want us to do... */ 1265 switch(flow) 1266 { 1267 case FLOW_START: 1268 DEBUG(IRDA_CB_INFO, "IrTTP wants us to start again\n"); 1269 /* Check if we really need to wake up PPP */ 1270 if(oldflow == FLOW_STOP) 1271 ppp_output_wakeup(&self->chan); 1272 else 1273 DEBUG(IRDA_CB_INFO, "But we were already transmitting !!!\n"); 1274 break; 1275 case FLOW_STOP: 1276 DEBUG(IRDA_CB_INFO, "IrTTP wants us to slow down\n"); 1277 break; 1278 default: 1279 DEBUG(IRDA_CB_INFO, "Unknown flow command!\n"); 1280 break; 1281 } 1282 1283 DEXIT(IRDA_TCB_TRACE, "\n"); 1284} 1285 1286/*------------------------------------------------------------------*/ 1287/* 1288 * Function irnet_status_indication (instance, sap, reason, skb) 1289 * 1290 * Link (IrLAP) status report. 1291 * 1292 */ 1293static void 1294irnet_status_indication(void * instance, 1295 LINK_STATUS link, 1296 LOCK_STATUS lock) 1297{ 1298 irnet_socket * self = (irnet_socket *) instance; 1299 1300 DENTER(IRDA_TCB_TRACE, "(self=0x%p)\n", self); 1301 DASSERT(self != NULL, , IRDA_CB_ERROR, "Self is NULL !!!\n"); 1302 1303 /* We can only get this event if we are connected */ 1304 switch(link) 1305 { 1306 case STATUS_NO_ACTIVITY: 1307 irnet_post_event(self, IRNET_BLOCKED_LINK, 1308 self->saddr, self->daddr, self->rname, 0); 1309 break; 1310 default: 1311 DEBUG(IRDA_CB_INFO, "Unknown status...\n"); 1312 } 1313 1314 DEXIT(IRDA_TCB_TRACE, "\n"); 1315} 1316 1317/*------------------------------------------------------------------*/ 1318/* 1319 * Function irnet_connect_indication(instance, sap, qos, max_sdu_size, userdata) 1320 * 1321 * Incoming connection 1322 * 1323 * In theory, this function is called only on the server socket. 1324 * Some other node is attempting to connect to the IrNET service, and has 1325 * sent a connection request on our server socket. 1326 * We just redirect the connection to the relevant IrNET socket. 1327 * 1328 * Note : we also make sure that between 2 irnet nodes, there can 1329 * exist only one irnet connection. 1330 */ 1331static void 1332irnet_connect_indication(void * instance, 1333 void * sap, 1334 struct qos_info *qos, 1335 __u32 max_sdu_size, 1336 __u8 max_header_size, 1337 struct sk_buff *skb) 1338{ 1339 irnet_socket * server = &irnet_server.s; 1340 irnet_socket * new = (irnet_socket *) NULL; 1341 1342 DENTER(IRDA_TCB_TRACE, "(server=0x%p)\n", server); 1343 DASSERT(instance == &irnet_server, , IRDA_CB_ERROR, 1344 "Invalid instance (0x%p) !!!\n", instance); 1345 DASSERT(sap == irnet_server.s.tsap, , IRDA_CB_ERROR, "Invalid sap !!!\n"); 1346 1347 /* Try to find the most appropriate IrNET socket */ 1348 new = irnet_find_socket(server); 1349 1350 /* After all this hard work, do we have an socket ? */ 1351 if(new == (irnet_socket *) NULL) 1352 { 1353 DEXIT(IRDA_CB_INFO, ": No socket waiting for this connection.\n"); 1354 irnet_disconnect_server(server, skb); 1355 return; 1356 } 1357 1358 /* Is the socket already busy ? */ 1359 if(test_bit(0, &new->ttp_open)) 1360 { 1361 DEXIT(IRDA_CB_INFO, ": Socket already connected.\n"); 1362 irnet_disconnect_server(server, skb); 1363 return; 1364 } 1365 1366 /* The following code is a bit tricky, so need comments ;-) 1367 */ 1368 /* Now, let's look at the way I wrote the test... 1369 * We need to clear up the ttp_connect flag atomically to prevent 1370 * irnet_disconnect_indication() to mess up the tsap we are going to close. 1371 * We want to clear the ttp_connect flag only if we close the tsap, 1372 * otherwise we will never close it, so we need to check for primary 1373 * *before* doing the test on the flag. 1374 * And of course, ALLOW_SIMULT_CONNECT can disable this entirely... 1375 * Jean II 1376 */ 1377 1378 /* Socket already connecting ? On primary ? */ 1379 if(0 1380#ifdef ALLOW_SIMULT_CONNECT 1381 || ((irttp_is_primary(server->tsap) == 1) /* primary */ 1382 && (test_and_clear_bit(0, &new->ttp_connect))) 1383#endif /* ALLOW_SIMULT_CONNECT */ 1384 ) 1385 { 1386 DERROR(IRDA_CB_ERROR, "Socket already connecting, but going to reuse it !\n"); 1387 1388 /* Cleanup the old TSAP if necessary - IrIAP will be cleaned up later */ 1389 if(new->tsap != NULL) 1390 { 1391 /* Close the old connection the new socket was attempting, 1392 * so that we can hook it up to the new connection. 1393 * It's now safe to do it... */ 1394 irttp_close_tsap(new->tsap); 1395 new->tsap = NULL; 1396 } 1397 } 1398 else 1399 { 1400 /* Three options : 1401 * 1) socket was not connecting or connected : ttp_connect should be 0. 1402 * 2) we don't want to connect the socket because we are secondary or 1403 * ALLOW_SIMULT_CONNECT is undefined. ttp_connect should be 1. 1404 * 3) we are half way in irnet_disconnect_indication(), and it's a 1405 * nice race condition... Fortunately, we can detect that by checking 1406 * if tsap is still alive. On the other hand, we can't be in 1407 * irda_irnet_destroy() otherwise we would not have found this 1408 * socket in the hashbin. 1409 * Jean II */ 1410 if((test_bit(0, &new->ttp_connect)) || (new->tsap != NULL)) 1411 { 1412 /* Don't mess this socket, somebody else in in charge... */ 1413 DERROR(IRDA_CB_ERROR, "Race condition detected, socket in use, abort connect...\n"); 1414 irnet_disconnect_server(server, skb); 1415 return; 1416 } 1417 } 1418 1419 /* So : at this point, we have a socket, and it is idle. Good ! */ 1420 irnet_connect_socket(server, new, qos, max_sdu_size, max_header_size); 1421 1422 /* Check size of received packet */ 1423 if(skb->len > 0) 1424 { 1425#ifdef PASS_CONNECT_PACKETS 1426 DEBUG(IRDA_CB_INFO, "Passing connect packet to PPP.\n"); 1427 /* Try to pass it to PPP */ 1428 irnet_data_indication(new, new->tsap, skb); 1429#else /* PASS_CONNECT_PACKETS */ 1430 DERROR(IRDA_CB_ERROR, "Dropping non empty packet.\n"); 1431 kfree_skb(skb); /* Note : will be optimised with other kfree... */ 1432#endif /* PASS_CONNECT_PACKETS */ 1433 } 1434 else 1435 kfree_skb(skb); 1436 1437 DEXIT(IRDA_TCB_TRACE, "\n"); 1438} 1439 1440 1441/********************** IRDA-IAS/LMP CALLBACKS **********************/ 1442/* 1443 * These are the callbacks called by other layers of the IrDA stack, 1444 * mainly LMP for discovery and IAS for name queries. 1445 */ 1446 1447/*------------------------------------------------------------------*/ 1448/* 1449 * Function irnet_getvalue_confirm (result, obj_id, value, priv) 1450 * 1451 * Got answer from remote LM-IAS, just connect 1452 * 1453 * This is the reply to a IAS query we were doing to find the TSAP of 1454 * the device we want to connect to. 1455 * If we have found a valid TSAP, just initiate the TTP connection 1456 * on this TSAP. 1457 */ 1458static void 1459irnet_getvalue_confirm(int result, 1460 __u16 obj_id, 1461 struct ias_value *value, 1462 void * priv) 1463{ 1464 irnet_socket * self = (irnet_socket *) priv; 1465 1466 DENTER(IRDA_OCB_TRACE, "(self=0x%p)\n", self); 1467 DASSERT(self != NULL, , IRDA_OCB_ERROR, "Self is NULL !!!\n"); 1468 1469 /* Check if already connected (via irnet_connect_socket()) 1470 * or socket is closing down (via irda_irnet_destroy()) */ 1471 if(! test_bit(0, &self->ttp_connect)) 1472 { 1473 DERROR(IRDA_OCB_ERROR, "Socket no longer connecting. Ouch !\n"); 1474 return; 1475 } 1476 1477 /* We probably don't need to make any more queries */ 1478 iriap_close(self->iriap); 1479 self->iriap = NULL; 1480 1481 /* Post process the IAS reply */ 1482 self->dtsap_sel = irnet_ias_to_tsap(self, result, value); 1483 1484 /* If error, just go out */ 1485 if(self->errno) 1486 { 1487 clear_bit(0, &self->ttp_connect); 1488 DERROR(IRDA_OCB_ERROR, "IAS connect failed ! (0x%X)\n", self->errno); 1489 return; 1490 } 1491 1492 DEBUG(IRDA_OCB_INFO, "daddr = %08x, lsap = %d, starting IrTTP connection\n", 1493 self->daddr, self->dtsap_sel); 1494 1495 /* Start up TTP - non blocking */ 1496 irnet_connect_tsap(self); 1497 1498 DEXIT(IRDA_OCB_TRACE, "\n"); 1499} 1500 1501/*------------------------------------------------------------------*/ 1502/* 1503 * Function irnet_discovervalue_confirm (result, obj_id, value, priv) 1504 * 1505 * Handle the TSAP discovery procedure state machine. 1506 * Got answer from remote LM-IAS, try next device 1507 * 1508 * We are doing a TSAP discovery procedure, and we got an answer to 1509 * a IAS query we were doing to find the TSAP on one of the address 1510 * in the discovery log. 1511 * 1512 * If we have found a valid TSAP for the first time, save it. If it's 1513 * not the first time we found one, complain. 1514 * 1515 * If we have more addresses in the log, just initiate a new query. 1516 * Note that those query may fail (see irnet_discover_daddr_and_lsap_sel()) 1517 * 1518 * Otherwise, wrap up the procedure (cleanup), check if we have found 1519 * any device and connect to it. 1520 */ 1521static void 1522irnet_discovervalue_confirm(int result, 1523 __u16 obj_id, 1524 struct ias_value *value, 1525 void * priv) 1526{ 1527 irnet_socket * self = (irnet_socket *) priv; 1528 __u8 dtsap_sel; /* TSAP we are looking for */ 1529 1530 DENTER(IRDA_OCB_TRACE, "(self=0x%p)\n", self); 1531 DASSERT(self != NULL, , IRDA_OCB_ERROR, "Self is NULL !!!\n"); 1532 1533 /* Check if already connected (via irnet_connect_socket()) 1534 * or socket is closing down (via irda_irnet_destroy()) */ 1535 if(! test_bit(0, &self->ttp_connect)) 1536 { 1537 DERROR(IRDA_OCB_ERROR, "Socket no longer connecting. Ouch !\n"); 1538 return; 1539 } 1540 1541 /* Post process the IAS reply */ 1542 dtsap_sel = irnet_ias_to_tsap(self, result, value); 1543 1544 /* Have we got something ? */ 1545 if(self->errno == 0) 1546 { 1547 /* We found the requested service */ 1548 if(self->daddr != DEV_ADDR_ANY) 1549 { 1550 DERROR(IRDA_OCB_ERROR, "More than one device in range supports IrNET...\n"); 1551 } 1552 else 1553 { 1554 /* First time we found that one, save it ! */ 1555 self->daddr = self->discoveries[self->disco_index].daddr; 1556 self->dtsap_sel = dtsap_sel; 1557 } 1558 } 1559 1560 /* If no failure */ 1561 if((self->errno == -EADDRNOTAVAIL) || (self->errno == 0)) 1562 { 1563 int ret; 1564 1565 /* Search the next node */ 1566 ret = irnet_discover_next_daddr(self); 1567 if(!ret) 1568 { 1569 /* In this case, the above request was non-blocking. 1570 * We will return here after a while... */ 1571 return; 1572 } 1573 /* In this case, we have processed the last discovery item */ 1574 } 1575 1576 /* No more queries to be done (failure or last one) */ 1577 1578 /* We probably don't need to make any more queries */ 1579 iriap_close(self->iriap); 1580 self->iriap = NULL; 1581 1582 /* No more items : remove the log and signal termination */ 1583 DEBUG(IRDA_OCB_INFO, "Cleaning up log (0x%p)\n", 1584 self->discoveries); 1585 if(self->discoveries != NULL) 1586 { 1587 /* Cleanup our copy of the discovery log */ 1588 kfree(self->discoveries); 1589 self->discoveries = NULL; 1590 } 1591 self->disco_number = -1; 1592 1593 /* Check out what we found */ 1594 if(self->daddr == DEV_ADDR_ANY) 1595 { 1596 self->daddr = DEV_ADDR_ANY; 1597 clear_bit(0, &self->ttp_connect); 1598 DEXIT(IRDA_OCB_TRACE, ": cannot discover IrNET in any device !!!\n"); 1599 return; 1600 } 1601 1602 /* We have a valid address - just connect */ 1603 1604 DEBUG(IRDA_OCB_INFO, "daddr = %08x, lsap = %d, starting IrTTP connection\n", 1605 self->daddr, self->dtsap_sel); 1606 1607 /* Start up TTP - non blocking */ 1608 irnet_connect_tsap(self); 1609 1610 DEXIT(IRDA_OCB_TRACE, "\n"); 1611} 1612 1613#ifdef DISCOVERY_EVENTS 1614/*------------------------------------------------------------------*/ 1615/* 1616 * Function irnet_discovery_indication (discovery) 1617 * 1618 * Got a discovery indication from IrLMP, post an event 1619 * 1620 * Note : IrLMP take care of matching the hint mask for us, and also 1621 * check if it is a "new" node for us... 1622 * 1623 * As IrLMP filter on the IrLAN hint bit, we get both IrLAN and IrNET 1624 * nodes, so it's only at connection time that we will know if the 1625 * node support IrNET, IrLAN or both. The other solution is to check 1626 * in IAS the PNP ids and service name. 1627 * Note : even if a node support IrNET (or IrLAN), it's no guarantee 1628 * that we will be able to connect to it, the node might already be 1629 * busy... 1630 * 1631 * One last thing : in some case, this function will trigger duplicate 1632 * discovery events. On the other hand, we should catch all 1633 * discoveries properly (i.e. not miss one). Filtering duplicate here 1634 * is to messy, so we leave that to user space... 1635 */ 1636static void 1637irnet_discovery_indication(discinfo_t * discovery, 1638 DISCOVERY_MODE mode, 1639 void * priv) 1640{ 1641 irnet_socket * self = &irnet_server.s; 1642 1643 DENTER(IRDA_OCB_TRACE, "(self=0x%p)\n", self); 1644 DASSERT(priv == &irnet_server, , IRDA_OCB_ERROR, 1645 "Invalid instance (0x%p) !!!\n", priv); 1646 1647 DEBUG(IRDA_OCB_INFO, "Discovered new IrNET/IrLAN node %s...\n", 1648 discovery->info); 1649 1650 /* Notify the control channel */ 1651 irnet_post_event(NULL, IRNET_DISCOVER, 1652 discovery->saddr, discovery->daddr, discovery->info, 1653 u16ho(discovery->hints)); 1654 1655 DEXIT(IRDA_OCB_TRACE, "\n"); 1656} 1657 1658/*------------------------------------------------------------------*/ 1659/* 1660 * Function irnet_expiry_indication (expiry) 1661 * 1662 * Got a expiry indication from IrLMP, post an event 1663 * 1664 * Note : IrLMP take care of matching the hint mask for us, we only 1665 * check if it is a "new" node... 1666 */ 1667static void 1668irnet_expiry_indication(discinfo_t * expiry, 1669 DISCOVERY_MODE mode, 1670 void * priv) 1671{ 1672 irnet_socket * self = &irnet_server.s; 1673 1674 DENTER(IRDA_OCB_TRACE, "(self=0x%p)\n", self); 1675 DASSERT(priv == &irnet_server, , IRDA_OCB_ERROR, 1676 "Invalid instance (0x%p) !!!\n", priv); 1677 1678 DEBUG(IRDA_OCB_INFO, "IrNET/IrLAN node %s expired...\n", 1679 expiry->info); 1680 1681 /* Notify the control channel */ 1682 irnet_post_event(NULL, IRNET_EXPIRE, 1683 expiry->saddr, expiry->daddr, expiry->info, 1684 u16ho(expiry->hints)); 1685 1686 DEXIT(IRDA_OCB_TRACE, "\n"); 1687} 1688#endif /* DISCOVERY_EVENTS */ 1689 1690 1691/*********************** PROC ENTRY CALLBACKS ***********************/ 1692/* 1693 * We create a instance in the /proc filesystem, and here we take care 1694 * of that... 1695 */ 1696 1697#ifdef CONFIG_PROC_FS 1698/*------------------------------------------------------------------*/ 1699/* 1700 * Function irnet_proc_read (buf, start, offset, len, unused) 1701 * 1702 * Give some info to the /proc file system 1703 */ 1704static int 1705irnet_proc_read(char * buf, 1706 char ** start, 1707 off_t offset, 1708 int len) 1709{ 1710 irnet_socket * self; 1711 char * state; 1712 int i = 0; 1713 1714 len = 0; 1715 1716 /* Get the IrNET server information... */ 1717 len += sprintf(buf+len, "IrNET server - "); 1718 len += sprintf(buf+len, "IrDA state: %s, ", 1719 (irnet_server.running ? "running" : "dead")); 1720 len += sprintf(buf+len, "stsap_sel: %02x, ", irnet_server.s.stsap_sel); 1721 len += sprintf(buf+len, "dtsap_sel: %02x\n", irnet_server.s.dtsap_sel); 1722 1723 /* Do we need to continue ? */ 1724 if(!irnet_server.running) 1725 return len; 1726 1727 /* Protect access to the instance list */ 1728 spin_lock_bh(&irnet_server.spinlock); 1729 1730 /* Get the sockets one by one... */ 1731 self = (irnet_socket *) hashbin_get_first(irnet_server.list); 1732 while(self != NULL) 1733 { 1734 /* Start printing info about the socket. */ 1735 len += sprintf(buf+len, "\nIrNET socket %d - ", i++); 1736 1737 /* First, get the requested configuration */ 1738 len += sprintf(buf+len, "Requested IrDA name: \"%s\", ", self->rname); 1739 len += sprintf(buf+len, "daddr: %08x, ", self->rdaddr); 1740 len += sprintf(buf+len, "saddr: %08x\n", self->rsaddr); 1741 1742 /* Second, get all the PPP info */ 1743 len += sprintf(buf+len, " PPP state: %s", 1744 (self->ppp_open ? "registered" : "unregistered")); 1745 if(self->ppp_open) 1746 { 1747 len += sprintf(buf+len, ", unit: ppp%d", 1748 ppp_unit_number(&self->chan)); 1749 len += sprintf(buf+len, ", channel: %d", 1750 ppp_channel_index(&self->chan)); 1751 len += sprintf(buf+len, ", mru: %d", 1752 self->mru); 1753 /* Maybe add self->flags ? Later... */ 1754 } 1755 1756 /* Then, get all the IrDA specific info... */ 1757 if(self->ttp_open) 1758 state = "connected"; 1759 else 1760 if(self->tsap != NULL) 1761 state = "connecting"; 1762 else 1763 if(self->iriap != NULL) 1764 state = "searching"; 1765 else 1766 if(self->ttp_connect) 1767 state = "weird"; 1768 else 1769 state = "idle"; 1770 len += sprintf(buf+len, "\n IrDA state: %s, ", state); 1771 len += sprintf(buf+len, "daddr: %08x, ", self->daddr); 1772 len += sprintf(buf+len, "stsap_sel: %02x, ", self->stsap_sel); 1773 len += sprintf(buf+len, "dtsap_sel: %02x\n", self->dtsap_sel); 1774 1775 /* Next socket, please... */ 1776 self = (irnet_socket *) hashbin_get_next(irnet_server.list); 1777 } 1778 1779 /* Spin lock end */ 1780 spin_unlock_bh(&irnet_server.spinlock); 1781 1782 return len; 1783} 1784#endif /* PROC_FS */ 1785 1786 1787/********************** CONFIGURATION/CLEANUP **********************/ 1788/* 1789 * Initialisation and teardown of the IrDA part, called at module 1790 * insertion and removal... 1791 */ 1792 1793/*------------------------------------------------------------------*/ 1794/* 1795 * Prepare the IrNET layer for operation... 1796 */ 1797int __init 1798irda_irnet_init(void) 1799{ 1800 int err = 0; 1801 1802 DENTER(MODULE_TRACE, "()\n"); 1803 1804 /* Pure paranoia - should be redundant */ 1805 memset(&irnet_server, 0, sizeof(struct irnet_root)); 1806 1807 /* Setup start of irnet instance list */ 1808 irnet_server.list = hashbin_new(HB_NOLOCK); 1809 DABORT(irnet_server.list == NULL, -ENOMEM, 1810 MODULE_ERROR, "Can't allocate hashbin!\n"); 1811 /* Init spinlock for instance list */ 1812 spin_lock_init(&irnet_server.spinlock); 1813 1814 /* Initialise control channel */ 1815 init_waitqueue_head(&irnet_events.rwait); 1816 irnet_events.index = 0; 1817 /* Init spinlock for event logging */ 1818 spin_lock_init(&irnet_events.spinlock); 1819 1820#ifdef CONFIG_PROC_FS 1821 /* Add a /proc file for irnet infos */ 1822 create_proc_info_entry("irnet", 0, proc_irda, irnet_proc_read); 1823#endif /* CONFIG_PROC_FS */ 1824 1825 /* Setup the IrNET server */ 1826 err = irnet_setup_server(); 1827 1828 if(!err) 1829 /* We are no longer functional... */ 1830 irnet_server.running = 1; 1831 1832 DEXIT(MODULE_TRACE, "\n"); 1833 return err; 1834} 1835 1836/*------------------------------------------------------------------*/ 1837/* 1838 * Cleanup at exit... 1839 */ 1840void __exit 1841irda_irnet_cleanup(void) 1842{ 1843 DENTER(MODULE_TRACE, "()\n"); 1844 1845 /* We are no longer there... */ 1846 irnet_server.running = 0; 1847 1848#ifdef CONFIG_PROC_FS 1849 /* Remove our /proc file */ 1850 remove_proc_entry("irnet", proc_irda); 1851#endif /* CONFIG_PROC_FS */ 1852 1853 /* Remove our IrNET server from existence */ 1854 irnet_destroy_server(); 1855 1856 /* Remove all instances of IrNET socket still present */ 1857 hashbin_delete(irnet_server.list, (FREE_FUNC) irda_irnet_destroy); 1858 1859 DEXIT(MODULE_TRACE, "\n"); 1860} 1861