Changes in uspace/lib/nic/src/nic_driver.c [6d8455d:ea788701] in mainline
- File:
-
- 1 edited
Legend:
- Unmodified
- Added
- Removed
-
uspace/lib/nic/src/nic_driver.c
r6d8455d rea788701 51 51 #include <net_interface.h> 52 52 #include <ops/nic.h> 53 #include <packet_client.h>54 #include <packet_remote.h>55 #include <net/packet_header.h>56 53 #include <errno.h> 57 54 … … 64 61 65 62 /** 66 * Initializes libraries required for NIC framework - logger , packet manager63 * Initializes libraries required for NIC framework - logger 67 64 * 68 65 * @param name Name of the device/driver (used in logging) … … 79 76 snprintf(buffer, 256, "drv/" DEVICE_CATEGORY_NIC "/%s", name); 80 77 81 /* Initialize packet manager */ 82 return pm_init(); 78 return EOK; 83 79 } 84 80 … … 162 158 163 159 /** 164 * Setup write packethandler. This MUST be called in the add_device handler160 * Setup send frame handler. This MUST be called in the add_device handler 165 161 * if the nic_send_message_impl function is used for sending messages (filled 166 162 * as send_message member of the nic_iface_t structure). The function must not … … 270 266 } 271 267 272 /** 273 * Just a wrapper over the packet_get_1_remote function 274 */ 275 packet_t *nic_alloc_packet(nic_t *nic_data, size_t data_size) 276 { 277 return packet_get_1_remote(nic_data->net_session, data_size); 278 } 279 280 281 /** 282 * Just a wrapper over the pq_release_remote function 283 */ 284 void nic_release_packet(nic_t *nic_data, packet_t *packet) 285 { 286 pq_release_remote(nic_data->net_session, packet_get_id(packet)); 287 } 288 289 /** Allocate frame and packet 268 /** Allocate frame 290 269 * 291 270 * @param nic_data The NIC driver data 292 * @param packet_size Size of packet 293 * @param offload_size Size of packet offload 271 * @param size Frame size in bytes 294 272 * @return pointer to allocated frame if success, NULL otherwise 295 273 */ 296 nic_frame_t *nic_alloc_frame(nic_t *nic_data, size_t packet_size)274 nic_frame_t *nic_alloc_frame(nic_t *nic_data, size_t size) 297 275 { 298 276 nic_frame_t *frame; … … 313 291 } 314 292 315 packet_t *packet = nic_alloc_packet(nic_data, packet_size);316 if ( !packet) {293 frame->data = malloc(size); 294 if (frame->data == NULL) { 317 295 free(frame); 318 296 return NULL; 319 297 } 320 298 321 frame-> packet = packet;299 frame->size = size; 322 300 return frame; 323 301 } … … 332 310 if (!frame) 333 311 return; 334 if (frame->packet != NULL) { 335 nic_release_packet(nic_data, frame->packet); 336 } 312 313 if (frame->data != NULL) { 314 free(frame->data); 315 frame->data = NULL; 316 frame->size = 0; 317 } 318 337 319 fibril_mutex_lock(&nic_globals.lock); 338 320 if (nic_globals.frame_cache_size >= NIC_GLOBALS_MAX_CACHE_SIZE) { … … 604 586 605 587 /** 606 * The busy flag can be set to 1 only in the write_packethandler, to 0 it can588 * The busy flag can be set to 1 only in the send_frame handler, to 0 it can 607 589 * be set anywhere. 608 590 * … … 613 595 { 614 596 /* 615 * When the function is called in write_packethandler the main lock is597 * When the function is called in send_frame handler the main lock is 616 598 * locked so no race can happen. 617 599 * Otherwise, when it is unexpectedly set to 0 (even with main lock held … … 622 604 623 605 /** 624 * Provided for correct naming conventions.625 * The packetis checked by filters and then sent up to the NIL layer or626 * discarded , the frame is released.627 * 628 * @param nic_data 629 * @param frame The frame containing received packet606 * This is the function that the driver should call when it receives a frame. 607 * The frame is checked by filters and then sent up to the NIL layer or 608 * discarded. The frame is released. 609 * 610 * @param nic_data 611 * @param frame The received frame 630 612 */ 631 613 void nic_received_frame(nic_t *nic_data, nic_frame_t *frame) 632 614 { 633 nic_received_packet(nic_data, frame->packet);634 frame->packet = NULL;635 nic_release_frame(nic_data, frame);636 }637 638 /**639 * This is the function that the driver should call when it receives a packet.640 * The packet is checked by filters and then sent up to the NIL layer or641 * discarded.642 *643 * @param nic_data644 * @param packet The received packet645 */646 void nic_received_packet(nic_t *nic_data, packet_t *packet)647 {648 615 /* Note: this function must not lock main lock, because loopback driver 649 * calls it inside write_packet handler (with locked main lock) */ 650 packet_id_t pid = packet_get_id(packet); 651 616 * calls it inside send_frame handler (with locked main lock) */ 652 617 fibril_rwlock_read_lock(&nic_data->rxc_lock); 653 618 nic_frame_type_t frame_type; 654 int check = nic_rxc_check(&nic_data->rx_control, packet, &frame_type); 619 int check = nic_rxc_check(&nic_data->rx_control, frame->data, 620 frame->size, &frame_type); 655 621 fibril_rwlock_read_unlock(&nic_data->rxc_lock); 656 622 /* Update statistics */ 657 623 fibril_rwlock_write_lock(&nic_data->stats_lock); 658 /* Both sending message up and releasing packet are atomic IPC calls */ 624 659 625 if (nic_data->state == NIC_STATE_ACTIVE && check) { 660 626 nic_data->stats.receive_packets++; 661 nic_data->stats.receive_bytes += packet_get_data_length(packet);627 nic_data->stats.receive_bytes += frame->size; 662 628 switch (frame_type) { 663 629 case NIC_FRAME_MULTICAST: … … 671 637 } 672 638 fibril_rwlock_write_unlock(&nic_data->stats_lock); 673 nil_received_msg(nic_data->nil_session, nic_data->device_id, pid); 639 nil_received_msg(nic_data->nil_session, nic_data->device_id, 640 frame->data, frame->size); 674 641 } else { 675 642 switch (frame_type) { … … 685 652 } 686 653 fibril_rwlock_write_unlock(&nic_data->stats_lock); 687 nic_release_packet(nic_data, packet);688 }654 } 655 nic_release_frame(nic_data, frame); 689 656 } 690 657 691 658 /** 692 659 * This function is to be used only in the loopback driver. It's workaround 693 * for the situation when the packetdoes not contain ethernet address.660 * for the situation when the frame does not contain ethernet address. 694 661 * The filtering is therefore not applied here. 695 662 * 696 663 * @param nic_data 697 * @param packet 698 */ 699 void nic_received_noneth_packet(nic_t *nic_data, packet_t *packet) 664 * @param data Frame data 665 * @param size Frame size in bytes 666 */ 667 void nic_received_noneth_frame(nic_t *nic_data, void *data, size_t size) 700 668 { 701 669 fibril_rwlock_write_lock(&nic_data->stats_lock); 702 670 nic_data->stats.receive_packets++; 703 nic_data->stats.receive_bytes += packet_get_data_length(packet);671 nic_data->stats.receive_bytes += size; 704 672 fibril_rwlock_write_unlock(&nic_data->stats_lock); 705 673 706 674 nil_received_msg(nic_data->nil_session, nic_data->device_id, 707 packet_get_id(packet));708 } 709 710 /** 711 * Some NICs can receive multiple packets during single interrupt. These can675 data, size); 676 } 677 678 /** 679 * Some NICs can receive multiple frames during single interrupt. These can 712 680 * send them in whole list of frames (actually nic_frame_t structures), then 713 * the list is deallocated and each packetis passed to the681 * the list is deallocated and each frame is passed to the 714 682 * nic_received_packet function. 715 683 * … … 726 694 727 695 list_remove(&frame->link); 728 nic_received_packet(nic_data, frame->packet); 729 frame->packet = NULL; 730 nic_release_frame(nic_data, frame); 696 nic_received_frame(nic_data, frame); 731 697 } 732 698 nic_driver_release_frame_list(frames); … … 1329 1295 } 1330 1296 1331 /** Lock packet for DMA usage1332 *1333 * @param packet1334 * @return physical address of packet1335 */1336 int nic_dma_lock_packet(packet_t *packet, size_t size, void **phys)1337 {1338 return dmamem_map(packet, SIZE2PAGES(size), 0, 0, phys);1339 }1340 1341 /** Unlock packet after DMA usage1342 *1343 * @param packet1344 */1345 int nic_dma_unlock_packet(packet_t *packet, size_t size)1346 {1347 return dmamem_unmap(packet, size);1348 }1349 1350 1297 /** @} 1351 1298 */
Note:
See TracChangeset
for help on using the changeset viewer.