19a5557fdSlucy wang - Sun Microsystems - Beijing China /* 29a5557fdSlucy wang - Sun Microsystems - Beijing China * CDDL HEADER START 39a5557fdSlucy wang - Sun Microsystems - Beijing China * 49a5557fdSlucy wang - Sun Microsystems - Beijing China * The contents of this file are subject to the terms of the 59a5557fdSlucy wang - Sun Microsystems - Beijing China * Common Development and Distribution License (the "License"). 69a5557fdSlucy wang - Sun Microsystems - Beijing China * You may not use this file except in compliance with the License. 79a5557fdSlucy wang - Sun Microsystems - Beijing China * 89a5557fdSlucy wang - Sun Microsystems - Beijing China * You can obtain a copy of the license at usr/src/OPENSOLARIS.LICENSE 99a5557fdSlucy wang - Sun Microsystems - Beijing China * or http://www.opensolaris.org/os/licensing. 109a5557fdSlucy wang - Sun Microsystems - Beijing China * See the License for the specific language governing permissions 119a5557fdSlucy wang - Sun Microsystems - Beijing China * and limitations under the License. 129a5557fdSlucy wang - Sun Microsystems - Beijing China * 139a5557fdSlucy wang - Sun Microsystems - Beijing China * When distributing Covered Code, include this CDDL HEADER in each 149a5557fdSlucy wang - Sun Microsystems - Beijing China * file and include the License file at usr/src/OPENSOLARIS.LICENSE. 159a5557fdSlucy wang - Sun Microsystems - Beijing China * If applicable, add the following below this CDDL HEADER, with the 169a5557fdSlucy wang - Sun Microsystems - Beijing China * fields enclosed by brackets "[]" replaced with your own identifying 179a5557fdSlucy wang - Sun Microsystems - Beijing China * information: Portions Copyright [yyyy] [name of copyright owner] 189a5557fdSlucy wang - Sun Microsystems - Beijing China * 199a5557fdSlucy wang - Sun Microsystems - Beijing China * CDDL HEADER END 209a5557fdSlucy wang - Sun Microsystems - Beijing China */ 219a5557fdSlucy wang - Sun Microsystems - Beijing China /* 229a5557fdSlucy wang - Sun Microsystems - Beijing China * Copyright 2008 NetXen, Inc. All rights reserved. 239a5557fdSlucy wang - Sun Microsystems - Beijing China * Use is subject to license terms. 249a5557fdSlucy wang - Sun Microsystems - Beijing China */ 259a5557fdSlucy wang - Sun Microsystems - Beijing China /* 26*0dc2366fSVenugopal Iyer * Copyright 2010 Sun Microsystems, Inc. All rights reserved. 279a5557fdSlucy wang - Sun Microsystems - Beijing China * Use is subject to license terms. 289a5557fdSlucy wang - Sun Microsystems - Beijing China */ 299a5557fdSlucy wang - Sun Microsystems - Beijing China #include <sys/types.h> 309a5557fdSlucy wang - Sun Microsystems - Beijing China #include <sys/conf.h> 319a5557fdSlucy wang - Sun Microsystems - Beijing China #include <sys/debug.h> 329a5557fdSlucy wang - Sun Microsystems - Beijing China #include <sys/stropts.h> 339a5557fdSlucy wang - Sun Microsystems - Beijing China #include <sys/stream.h> 349a5557fdSlucy wang - Sun Microsystems - Beijing China #include <sys/strlog.h> 359a5557fdSlucy wang - Sun Microsystems - Beijing China #include <sys/kmem.h> 369a5557fdSlucy wang - Sun Microsystems - Beijing China #include <sys/stat.h> 379a5557fdSlucy wang - Sun Microsystems - Beijing China #include <sys/kstat.h> 389a5557fdSlucy wang - Sun Microsystems - Beijing China #include <sys/vtrace.h> 399a5557fdSlucy wang - Sun Microsystems - Beijing China #include <sys/dlpi.h> 409a5557fdSlucy wang - Sun Microsystems - Beijing China #include <sys/strsun.h> 419a5557fdSlucy wang - Sun Microsystems - Beijing China #include <sys/ethernet.h> 429a5557fdSlucy wang - Sun Microsystems - Beijing China #include <sys/modctl.h> 439a5557fdSlucy wang - Sun Microsystems - Beijing China #include <sys/errno.h> 449a5557fdSlucy wang - Sun Microsystems - Beijing China #include <sys/dditypes.h> 459a5557fdSlucy wang - Sun Microsystems - Beijing China #include <sys/ddi.h> 469a5557fdSlucy wang - Sun Microsystems - Beijing China #include <sys/sunddi.h> 479a5557fdSlucy wang - Sun Microsystems - Beijing China #include <sys/sysmacros.h> 489a5557fdSlucy wang - Sun Microsystems - Beijing China #include <sys/pci.h> 499a5557fdSlucy wang - Sun Microsystems - Beijing China 509a5557fdSlucy wang - Sun Microsystems - Beijing China #include <sys/gld.h> 519a5557fdSlucy wang - Sun Microsystems - Beijing China #include <netinet/in.h> 529a5557fdSlucy wang - Sun Microsystems - Beijing China #include <inet/ip.h> 539a5557fdSlucy wang - Sun Microsystems - Beijing China #include <inet/tcp.h> 549a5557fdSlucy wang - Sun Microsystems - Beijing China 559a5557fdSlucy wang - Sun Microsystems - Beijing China #include <sys/rwlock.h> 569a5557fdSlucy wang - Sun Microsystems - Beijing China #include <sys/mutex.h> 579a5557fdSlucy wang - Sun Microsystems - Beijing China #include <sys/pattr.h> 589a5557fdSlucy wang - Sun Microsystems - Beijing China #include <sys/strsubr.h> 599a5557fdSlucy wang - Sun Microsystems - Beijing China #include <sys/ddi_impldefs.h> 609a5557fdSlucy wang - Sun Microsystems - Beijing China #include<sys/task.h> 619a5557fdSlucy wang - Sun Microsystems - Beijing China 629a5557fdSlucy wang - Sun Microsystems - Beijing China #include "unm_nic_hw.h" 639a5557fdSlucy wang - Sun Microsystems - Beijing China #include "unm_nic.h" 649a5557fdSlucy wang - Sun Microsystems - Beijing China 659a5557fdSlucy wang - Sun Microsystems - Beijing China #include "nic_phan_reg.h" 669a5557fdSlucy wang - Sun Microsystems - Beijing China #include "unm_nic_ioctl.h" 679a5557fdSlucy wang - Sun Microsystems - Beijing China #include "nic_cmn.h" 689a5557fdSlucy wang - Sun Microsystems - Beijing China #include "unm_version.h" 699a5557fdSlucy wang - Sun Microsystems - Beijing China #include "unm_brdcfg.h" 709a5557fdSlucy wang - Sun Microsystems - Beijing China 719a5557fdSlucy wang - Sun Microsystems - Beijing China #if defined(lint) 729a5557fdSlucy wang - Sun Microsystems - Beijing China #undef MBLKL 739a5557fdSlucy wang - Sun Microsystems - Beijing China #define MBLKL(_mp_) ((uintptr_t)(_mp_)->b_wptr - (uintptr_t)(_mp_)->b_rptr) 749a5557fdSlucy wang - Sun Microsystems - Beijing China #endif /* lint */ 759a5557fdSlucy wang - Sun Microsystems - Beijing China 769a5557fdSlucy wang - Sun Microsystems - Beijing China #undef UNM_LOOPBACK 779a5557fdSlucy wang - Sun Microsystems - Beijing China #undef SINGLE_DMA_BUF 789a5557fdSlucy wang - Sun Microsystems - Beijing China 799a5557fdSlucy wang - Sun Microsystems - Beijing China #define UNM_ADAPTER_UP_MAGIC 777 809a5557fdSlucy wang - Sun Microsystems - Beijing China #define VLAN_TAGSZ 0x4 819a5557fdSlucy wang - Sun Microsystems - Beijing China 829a5557fdSlucy wang - Sun Microsystems - Beijing China #define index2rxbuf(_rdp_, _idx_) ((_rdp_)->rx_buf_pool + (_idx_)) 839a5557fdSlucy wang - Sun Microsystems - Beijing China #define rxbuf2index(_rdp_, _bufp_) ((_bufp_) - (_rdp_)->rx_buf_pool) 849a5557fdSlucy wang - Sun Microsystems - Beijing China 859a5557fdSlucy wang - Sun Microsystems - Beijing China /* 869a5557fdSlucy wang - Sun Microsystems - Beijing China * Receive ISR processes NX_RX_MAXBUFS incoming packets at most, then posts 879a5557fdSlucy wang - Sun Microsystems - Beijing China * as many buffers as packets processed. This loop repeats as required to 889a5557fdSlucy wang - Sun Microsystems - Beijing China * process all incoming packets delivered in a single interrupt. Higher 899a5557fdSlucy wang - Sun Microsystems - Beijing China * value of NX_RX_MAXBUFS improves performance by posting rx buffers less 909a5557fdSlucy wang - Sun Microsystems - Beijing China * frequently, but at the cost of not posting quickly enough when card is 919a5557fdSlucy wang - Sun Microsystems - Beijing China * running out of rx buffers. 929a5557fdSlucy wang - Sun Microsystems - Beijing China */ 939a5557fdSlucy wang - Sun Microsystems - Beijing China #define NX_RX_THRESHOLD 32 949a5557fdSlucy wang - Sun Microsystems - Beijing China #define NX_RX_MAXBUFS 128 959a5557fdSlucy wang - Sun Microsystems - Beijing China #define NX_MAX_TXCOMPS 256 969a5557fdSlucy wang - Sun Microsystems - Beijing China 97dda0720aSjing xiong ERI-SUN extern int create_rxtx_rings(unm_adapter *adapter); 98dda0720aSjing xiong ERI-SUN extern void destroy_rxtx_rings(unm_adapter *adapter); 999a5557fdSlucy wang - Sun Microsystems - Beijing China 1009a5557fdSlucy wang - Sun Microsystems - Beijing China static void unm_post_rx_buffers_nodb(struct unm_adapter_s *adapter, 1019a5557fdSlucy wang - Sun Microsystems - Beijing China uint32_t ringid); 1029a5557fdSlucy wang - Sun Microsystems - Beijing China static mblk_t *unm_process_rcv(unm_adapter *adapter, statusDesc_t *desc); 1039a5557fdSlucy wang - Sun Microsystems - Beijing China static int unm_process_rcv_ring(unm_adapter *, int); 1049a5557fdSlucy wang - Sun Microsystems - Beijing China static int unm_process_cmd_ring(struct unm_adapter_s *adapter); 1059a5557fdSlucy wang - Sun Microsystems - Beijing China 1069a5557fdSlucy wang - Sun Microsystems - Beijing China static int unm_nic_do_ioctl(unm_adapter *adapter, queue_t *q, mblk_t *mp); 1079a5557fdSlucy wang - Sun Microsystems - Beijing China static void unm_nic_ioctl(struct unm_adapter_s *adapter, int cmd, queue_t *q, 1089a5557fdSlucy wang - Sun Microsystems - Beijing China mblk_t *mp); 1099a5557fdSlucy wang - Sun Microsystems - Beijing China 1109a5557fdSlucy wang - Sun Microsystems - Beijing China /* GLDv3 interface functions */ 1119a5557fdSlucy wang - Sun Microsystems - Beijing China static int ntxn_m_start(void *); 1129a5557fdSlucy wang - Sun Microsystems - Beijing China static void ntxn_m_stop(void *); 1139a5557fdSlucy wang - Sun Microsystems - Beijing China static int ntxn_m_multicst(void *, boolean_t, const uint8_t *); 1149a5557fdSlucy wang - Sun Microsystems - Beijing China static int ntxn_m_promisc(void *, boolean_t); 1159a5557fdSlucy wang - Sun Microsystems - Beijing China static int ntxn_m_stat(void *arg, uint_t stat, uint64_t *val); 1169a5557fdSlucy wang - Sun Microsystems - Beijing China static mblk_t *ntxn_m_tx(void *, mblk_t *); 1179a5557fdSlucy wang - Sun Microsystems - Beijing China static void ntxn_m_ioctl(void *arg, queue_t *wq, mblk_t *mp); 1189a5557fdSlucy wang - Sun Microsystems - Beijing China static boolean_t ntxn_m_getcapab(void *arg, mac_capab_t cap, void *cap_data); 1199a5557fdSlucy wang - Sun Microsystems - Beijing China 1209a5557fdSlucy wang - Sun Microsystems - Beijing China /* 1219a5557fdSlucy wang - Sun Microsystems - Beijing China * Allocates DMA handle, virtual memory and binds them 1229a5557fdSlucy wang - Sun Microsystems - Beijing China * returns size of actual memory binded and the physical address. 1239a5557fdSlucy wang - Sun Microsystems - Beijing China */ 1249a5557fdSlucy wang - Sun Microsystems - Beijing China int 1259a5557fdSlucy wang - Sun Microsystems - Beijing China unm_pci_alloc_consistent(unm_adapter *adapter, 1269a5557fdSlucy wang - Sun Microsystems - Beijing China int size, caddr_t *address, ddi_dma_cookie_t *cookie, 1279a5557fdSlucy wang - Sun Microsystems - Beijing China ddi_dma_handle_t *dma_handle, ddi_acc_handle_t *handlep) 1289a5557fdSlucy wang - Sun Microsystems - Beijing China { 1299a5557fdSlucy wang - Sun Microsystems - Beijing China int err; 1309a5557fdSlucy wang - Sun Microsystems - Beijing China uint32_t ncookies; 1319a5557fdSlucy wang - Sun Microsystems - Beijing China size_t ring_len; 1329a5557fdSlucy wang - Sun Microsystems - Beijing China uint_t dma_flags = DDI_DMA_RDWR | DDI_DMA_CONSISTENT; 1339a5557fdSlucy wang - Sun Microsystems - Beijing China 1349a5557fdSlucy wang - Sun Microsystems - Beijing China *dma_handle = NULL; 1359a5557fdSlucy wang - Sun Microsystems - Beijing China 1369a5557fdSlucy wang - Sun Microsystems - Beijing China if (size <= 0) 1379a5557fdSlucy wang - Sun Microsystems - Beijing China return (DDI_ENOMEM); 1389a5557fdSlucy wang - Sun Microsystems - Beijing China 1399a5557fdSlucy wang - Sun Microsystems - Beijing China err = ddi_dma_alloc_handle(adapter->dip, 1409a5557fdSlucy wang - Sun Microsystems - Beijing China &adapter->gc_dma_attr_desc, 1419a5557fdSlucy wang - Sun Microsystems - Beijing China DDI_DMA_DONTWAIT, NULL, dma_handle); 1429a5557fdSlucy wang - Sun Microsystems - Beijing China if (err != DDI_SUCCESS) { 1439a5557fdSlucy wang - Sun Microsystems - Beijing China cmn_err(CE_WARN, "!%s: %s: ddi_dma_alloc_handle FAILED:" 1449a5557fdSlucy wang - Sun Microsystems - Beijing China " %d", unm_nic_driver_name, __func__, err); 1459a5557fdSlucy wang - Sun Microsystems - Beijing China return (DDI_ENOMEM); 1469a5557fdSlucy wang - Sun Microsystems - Beijing China } 1479a5557fdSlucy wang - Sun Microsystems - Beijing China 1489a5557fdSlucy wang - Sun Microsystems - Beijing China err = ddi_dma_mem_alloc(*dma_handle, 1499a5557fdSlucy wang - Sun Microsystems - Beijing China size, &adapter->gc_attr_desc, 1509a5557fdSlucy wang - Sun Microsystems - Beijing China dma_flags & (DDI_DMA_STREAMING | DDI_DMA_CONSISTENT), 1519a5557fdSlucy wang - Sun Microsystems - Beijing China DDI_DMA_DONTWAIT, NULL, address, &ring_len, 1529a5557fdSlucy wang - Sun Microsystems - Beijing China handlep); 1539a5557fdSlucy wang - Sun Microsystems - Beijing China if (err != DDI_SUCCESS) { 1549a5557fdSlucy wang - Sun Microsystems - Beijing China cmn_err(CE_WARN, "!%s: %s: ddi_dma_mem_alloc failed:" 1559a5557fdSlucy wang - Sun Microsystems - Beijing China "ret %d, request size: %d", 1569a5557fdSlucy wang - Sun Microsystems - Beijing China unm_nic_driver_name, __func__, err, size); 1579a5557fdSlucy wang - Sun Microsystems - Beijing China ddi_dma_free_handle(dma_handle); 1589a5557fdSlucy wang - Sun Microsystems - Beijing China return (DDI_ENOMEM); 1599a5557fdSlucy wang - Sun Microsystems - Beijing China } 1609a5557fdSlucy wang - Sun Microsystems - Beijing China 1619a5557fdSlucy wang - Sun Microsystems - Beijing China if (ring_len < size) { 1629a5557fdSlucy wang - Sun Microsystems - Beijing China cmn_err(CE_WARN, "%s: %s: could not allocate required " 1639a5557fdSlucy wang - Sun Microsystems - Beijing China "memory :%d\n", unm_nic_driver_name, 1649a5557fdSlucy wang - Sun Microsystems - Beijing China __func__, err); 1659a5557fdSlucy wang - Sun Microsystems - Beijing China ddi_dma_mem_free(handlep); 1669a5557fdSlucy wang - Sun Microsystems - Beijing China ddi_dma_free_handle(dma_handle); 1679a5557fdSlucy wang - Sun Microsystems - Beijing China return (DDI_FAILURE); 1689a5557fdSlucy wang - Sun Microsystems - Beijing China } 1699a5557fdSlucy wang - Sun Microsystems - Beijing China 1709a5557fdSlucy wang - Sun Microsystems - Beijing China (void) memset(*address, 0, size); 1719a5557fdSlucy wang - Sun Microsystems - Beijing China 1729a5557fdSlucy wang - Sun Microsystems - Beijing China if (((err = ddi_dma_addr_bind_handle(*dma_handle, 1739a5557fdSlucy wang - Sun Microsystems - Beijing China NULL, *address, ring_len, 1749a5557fdSlucy wang - Sun Microsystems - Beijing China dma_flags, 1759a5557fdSlucy wang - Sun Microsystems - Beijing China DDI_DMA_DONTWAIT, NULL, 1769a5557fdSlucy wang - Sun Microsystems - Beijing China cookie, &ncookies)) != DDI_DMA_MAPPED) || 1779a5557fdSlucy wang - Sun Microsystems - Beijing China (ncookies != 1)) { 1789a5557fdSlucy wang - Sun Microsystems - Beijing China cmn_err(CE_WARN, 1799a5557fdSlucy wang - Sun Microsystems - Beijing China "!%s: %s: ddi_dma_addr_bind_handle FAILED: %d", 1809a5557fdSlucy wang - Sun Microsystems - Beijing China unm_nic_driver_name, __func__, err); 1819a5557fdSlucy wang - Sun Microsystems - Beijing China ddi_dma_mem_free(handlep); 1829a5557fdSlucy wang - Sun Microsystems - Beijing China ddi_dma_free_handle(dma_handle); 1839a5557fdSlucy wang - Sun Microsystems - Beijing China return (DDI_FAILURE); 1849a5557fdSlucy wang - Sun Microsystems - Beijing China } 1859a5557fdSlucy wang - Sun Microsystems - Beijing China 1869a5557fdSlucy wang - Sun Microsystems - Beijing China return (DDI_SUCCESS); 1879a5557fdSlucy wang - Sun Microsystems - Beijing China } 1889a5557fdSlucy wang - Sun Microsystems - Beijing China 1899a5557fdSlucy wang - Sun Microsystems - Beijing China /* 1909a5557fdSlucy wang - Sun Microsystems - Beijing China * Unbinds the memory, frees the DMA handle and at the end, frees the memory 1919a5557fdSlucy wang - Sun Microsystems - Beijing China */ 1929a5557fdSlucy wang - Sun Microsystems - Beijing China void 1939a5557fdSlucy wang - Sun Microsystems - Beijing China unm_pci_free_consistent(ddi_dma_handle_t *dma_handle, 1949a5557fdSlucy wang - Sun Microsystems - Beijing China ddi_acc_handle_t *acc_handle) 1959a5557fdSlucy wang - Sun Microsystems - Beijing China { 1969a5557fdSlucy wang - Sun Microsystems - Beijing China int err; 1979a5557fdSlucy wang - Sun Microsystems - Beijing China 1989a5557fdSlucy wang - Sun Microsystems - Beijing China err = ddi_dma_unbind_handle(*dma_handle); 1999a5557fdSlucy wang - Sun Microsystems - Beijing China if (err != DDI_SUCCESS) { 2009a5557fdSlucy wang - Sun Microsystems - Beijing China cmn_err(CE_WARN, "%s: Error unbinding memory\n", __func__); 2019a5557fdSlucy wang - Sun Microsystems - Beijing China return; 2029a5557fdSlucy wang - Sun Microsystems - Beijing China } 2039a5557fdSlucy wang - Sun Microsystems - Beijing China 2049a5557fdSlucy wang - Sun Microsystems - Beijing China ddi_dma_mem_free(acc_handle); 2059a5557fdSlucy wang - Sun Microsystems - Beijing China ddi_dma_free_handle(dma_handle); 2069a5557fdSlucy wang - Sun Microsystems - Beijing China } 2079a5557fdSlucy wang - Sun Microsystems - Beijing China 2089a5557fdSlucy wang - Sun Microsystems - Beijing China static uint32_t msi_tgt_status[] = { 2099a5557fdSlucy wang - Sun Microsystems - Beijing China ISR_INT_TARGET_STATUS, ISR_INT_TARGET_STATUS_F1, 2109a5557fdSlucy wang - Sun Microsystems - Beijing China ISR_INT_TARGET_STATUS_F2, ISR_INT_TARGET_STATUS_F3, 2119a5557fdSlucy wang - Sun Microsystems - Beijing China ISR_INT_TARGET_STATUS_F4, ISR_INT_TARGET_STATUS_F5, 2129a5557fdSlucy wang - Sun Microsystems - Beijing China ISR_INT_TARGET_STATUS_F6, ISR_INT_TARGET_STATUS_F7 2139a5557fdSlucy wang - Sun Microsystems - Beijing China }; 2149a5557fdSlucy wang - Sun Microsystems - Beijing China 2159a5557fdSlucy wang - Sun Microsystems - Beijing China static void 2169a5557fdSlucy wang - Sun Microsystems - Beijing China unm_nic_disable_int(unm_adapter *adapter) 2179a5557fdSlucy wang - Sun Microsystems - Beijing China { 2189a5557fdSlucy wang - Sun Microsystems - Beijing China __uint32_t temp = 0; 2199a5557fdSlucy wang - Sun Microsystems - Beijing China 2209a5557fdSlucy wang - Sun Microsystems - Beijing China adapter->unm_nic_hw_write_wx(adapter, adapter->interrupt_crb, 2219a5557fdSlucy wang - Sun Microsystems - Beijing China &temp, 4); 2229a5557fdSlucy wang - Sun Microsystems - Beijing China } 2239a5557fdSlucy wang - Sun Microsystems - Beijing China 224dda0720aSjing xiong ERI-SUN static inline int 2259a5557fdSlucy wang - Sun Microsystems - Beijing China unm_nic_clear_int(unm_adapter *adapter) 2269a5557fdSlucy wang - Sun Microsystems - Beijing China { 2279a5557fdSlucy wang - Sun Microsystems - Beijing China uint32_t mask, temp, our_int, status; 2289a5557fdSlucy wang - Sun Microsystems - Beijing China 2299a5557fdSlucy wang - Sun Microsystems - Beijing China UNM_READ_LOCK(&adapter->adapter_lock); 2309a5557fdSlucy wang - Sun Microsystems - Beijing China 2319a5557fdSlucy wang - Sun Microsystems - Beijing China /* check whether it's our interrupt */ 2329a5557fdSlucy wang - Sun Microsystems - Beijing China if (!UNM_IS_MSI_FAMILY(adapter)) { 2339a5557fdSlucy wang - Sun Microsystems - Beijing China 2349a5557fdSlucy wang - Sun Microsystems - Beijing China /* Legacy Interrupt case */ 2359a5557fdSlucy wang - Sun Microsystems - Beijing China adapter->unm_nic_pci_read_immediate(adapter, ISR_INT_VECTOR, 2369a5557fdSlucy wang - Sun Microsystems - Beijing China &status); 2379a5557fdSlucy wang - Sun Microsystems - Beijing China 2389a5557fdSlucy wang - Sun Microsystems - Beijing China if (!(status & adapter->legacy_intr.int_vec_bit)) { 2399a5557fdSlucy wang - Sun Microsystems - Beijing China UNM_READ_UNLOCK(&adapter->adapter_lock); 2409a5557fdSlucy wang - Sun Microsystems - Beijing China return (-1); 2419a5557fdSlucy wang - Sun Microsystems - Beijing China } 2429a5557fdSlucy wang - Sun Microsystems - Beijing China 2439a5557fdSlucy wang - Sun Microsystems - Beijing China if (adapter->ahw.revision_id >= NX_P3_B1) { 2449a5557fdSlucy wang - Sun Microsystems - Beijing China adapter->unm_nic_pci_read_immediate(adapter, 2459a5557fdSlucy wang - Sun Microsystems - Beijing China ISR_INT_STATE_REG, &temp); 2469a5557fdSlucy wang - Sun Microsystems - Beijing China if (!ISR_IS_LEGACY_INTR_TRIGGERED(temp)) { 2479a5557fdSlucy wang - Sun Microsystems - Beijing China UNM_READ_UNLOCK(&adapter->adapter_lock); 2489a5557fdSlucy wang - Sun Microsystems - Beijing China return (-1); 2499a5557fdSlucy wang - Sun Microsystems - Beijing China } 2509a5557fdSlucy wang - Sun Microsystems - Beijing China } else if (NX_IS_REVISION_P2(adapter->ahw.revision_id)) { 2519a5557fdSlucy wang - Sun Microsystems - Beijing China our_int = adapter->unm_nic_pci_read_normalize(adapter, 2529a5557fdSlucy wang - Sun Microsystems - Beijing China CRB_INT_VECTOR); 2539a5557fdSlucy wang - Sun Microsystems - Beijing China 2549a5557fdSlucy wang - Sun Microsystems - Beijing China /* FIXME: Assumes pci_func is same as ctx */ 2559a5557fdSlucy wang - Sun Microsystems - Beijing China if ((our_int & (0x80 << adapter->portnum)) == 0) { 2569a5557fdSlucy wang - Sun Microsystems - Beijing China if (our_int != 0) { 2579a5557fdSlucy wang - Sun Microsystems - Beijing China /* not our interrupt */ 2589a5557fdSlucy wang - Sun Microsystems - Beijing China UNM_READ_UNLOCK(&adapter->adapter_lock); 2599a5557fdSlucy wang - Sun Microsystems - Beijing China return (-1); 2609a5557fdSlucy wang - Sun Microsystems - Beijing China } 2619a5557fdSlucy wang - Sun Microsystems - Beijing China } 2629a5557fdSlucy wang - Sun Microsystems - Beijing China temp = our_int & ~((u32)(0x80 << adapter->portnum)); 2639a5557fdSlucy wang - Sun Microsystems - Beijing China adapter->unm_nic_pci_write_normalize(adapter, 2649a5557fdSlucy wang - Sun Microsystems - Beijing China CRB_INT_VECTOR, temp); 2659a5557fdSlucy wang - Sun Microsystems - Beijing China } 2669a5557fdSlucy wang - Sun Microsystems - Beijing China 2679a5557fdSlucy wang - Sun Microsystems - Beijing China if (adapter->fw_major < 4) 2689a5557fdSlucy wang - Sun Microsystems - Beijing China unm_nic_disable_int(adapter); 2699a5557fdSlucy wang - Sun Microsystems - Beijing China 2709a5557fdSlucy wang - Sun Microsystems - Beijing China /* claim interrupt */ 2719a5557fdSlucy wang - Sun Microsystems - Beijing China temp = 0xffffffff; 2729a5557fdSlucy wang - Sun Microsystems - Beijing China adapter->unm_nic_pci_write_immediate(adapter, 2739a5557fdSlucy wang - Sun Microsystems - Beijing China adapter->legacy_intr.tgt_status_reg, &temp); 2749a5557fdSlucy wang - Sun Microsystems - Beijing China 2759a5557fdSlucy wang - Sun Microsystems - Beijing China adapter->unm_nic_pci_read_immediate(adapter, ISR_INT_VECTOR, 2769a5557fdSlucy wang - Sun Microsystems - Beijing China &mask); 2779a5557fdSlucy wang - Sun Microsystems - Beijing China 2789a5557fdSlucy wang - Sun Microsystems - Beijing China /* 2799a5557fdSlucy wang - Sun Microsystems - Beijing China * Read again to make sure the legacy interrupt message got 2809a5557fdSlucy wang - Sun Microsystems - Beijing China * flushed out 2819a5557fdSlucy wang - Sun Microsystems - Beijing China */ 2829a5557fdSlucy wang - Sun Microsystems - Beijing China adapter->unm_nic_pci_read_immediate(adapter, ISR_INT_VECTOR, 2839a5557fdSlucy wang - Sun Microsystems - Beijing China &mask); 2849a5557fdSlucy wang - Sun Microsystems - Beijing China } else if (adapter->flags & UNM_NIC_MSI_ENABLED) { 2859a5557fdSlucy wang - Sun Microsystems - Beijing China /* clear interrupt */ 2869a5557fdSlucy wang - Sun Microsystems - Beijing China temp = 0xffffffff; 2879a5557fdSlucy wang - Sun Microsystems - Beijing China adapter->unm_nic_pci_write_immediate(adapter, 2889a5557fdSlucy wang - Sun Microsystems - Beijing China msi_tgt_status[adapter->ahw.pci_func], &temp); 2899a5557fdSlucy wang - Sun Microsystems - Beijing China } 2909a5557fdSlucy wang - Sun Microsystems - Beijing China 2919a5557fdSlucy wang - Sun Microsystems - Beijing China UNM_READ_UNLOCK(&adapter->adapter_lock); 2929a5557fdSlucy wang - Sun Microsystems - Beijing China 2939a5557fdSlucy wang - Sun Microsystems - Beijing China return (0); 2949a5557fdSlucy wang - Sun Microsystems - Beijing China } 2959a5557fdSlucy wang - Sun Microsystems - Beijing China 2969a5557fdSlucy wang - Sun Microsystems - Beijing China static void 2979a5557fdSlucy wang - Sun Microsystems - Beijing China unm_nic_enable_int(unm_adapter *adapter) 2989a5557fdSlucy wang - Sun Microsystems - Beijing China { 2999a5557fdSlucy wang - Sun Microsystems - Beijing China u32 temp = 1; 3009a5557fdSlucy wang - Sun Microsystems - Beijing China 3019a5557fdSlucy wang - Sun Microsystems - Beijing China adapter->unm_nic_hw_write_wx(adapter, adapter->interrupt_crb, 3029a5557fdSlucy wang - Sun Microsystems - Beijing China &temp, 4); 3039a5557fdSlucy wang - Sun Microsystems - Beijing China 3049a5557fdSlucy wang - Sun Microsystems - Beijing China if (!UNM_IS_MSI_FAMILY(adapter)) { 3059a5557fdSlucy wang - Sun Microsystems - Beijing China u32 mask = 0xfbff; 3069a5557fdSlucy wang - Sun Microsystems - Beijing China 3079a5557fdSlucy wang - Sun Microsystems - Beijing China adapter->unm_nic_pci_write_immediate(adapter, 3089a5557fdSlucy wang - Sun Microsystems - Beijing China adapter->legacy_intr.tgt_mask_reg, &mask); 3099a5557fdSlucy wang - Sun Microsystems - Beijing China } 3109a5557fdSlucy wang - Sun Microsystems - Beijing China } 3119a5557fdSlucy wang - Sun Microsystems - Beijing China 3129a5557fdSlucy wang - Sun Microsystems - Beijing China static void 3139a5557fdSlucy wang - Sun Microsystems - Beijing China unm_free_hw_resources(unm_adapter *adapter) 3149a5557fdSlucy wang - Sun Microsystems - Beijing China { 3159a5557fdSlucy wang - Sun Microsystems - Beijing China unm_recv_context_t *recv_ctx; 3169a5557fdSlucy wang - Sun Microsystems - Beijing China unm_rcv_desc_ctx_t *rcv_desc; 3179a5557fdSlucy wang - Sun Microsystems - Beijing China int ctx, ring; 3189a5557fdSlucy wang - Sun Microsystems - Beijing China 3199a5557fdSlucy wang - Sun Microsystems - Beijing China if (adapter->context_alloced == 1) { 3209a5557fdSlucy wang - Sun Microsystems - Beijing China netxen_destroy_rxtx(adapter); 3219a5557fdSlucy wang - Sun Microsystems - Beijing China adapter->context_alloced = 0; 3229a5557fdSlucy wang - Sun Microsystems - Beijing China } 3239a5557fdSlucy wang - Sun Microsystems - Beijing China 3249a5557fdSlucy wang - Sun Microsystems - Beijing China if (adapter->ctxDesc != NULL) { 3259a5557fdSlucy wang - Sun Microsystems - Beijing China unm_pci_free_consistent(&adapter->ctxDesc_dma_handle, 3269a5557fdSlucy wang - Sun Microsystems - Beijing China &adapter->ctxDesc_acc_handle); 3279a5557fdSlucy wang - Sun Microsystems - Beijing China adapter->ctxDesc = NULL; 3289a5557fdSlucy wang - Sun Microsystems - Beijing China } 3299a5557fdSlucy wang - Sun Microsystems - Beijing China 3309a5557fdSlucy wang - Sun Microsystems - Beijing China if (adapter->ahw.cmdDescHead != NULL) { 3319a5557fdSlucy wang - Sun Microsystems - Beijing China unm_pci_free_consistent(&adapter->ahw.cmd_desc_dma_handle, 3329a5557fdSlucy wang - Sun Microsystems - Beijing China &adapter->ahw.cmd_desc_acc_handle); 3339a5557fdSlucy wang - Sun Microsystems - Beijing China adapter->ahw.cmdDesc_physAddr = NULL; 3349a5557fdSlucy wang - Sun Microsystems - Beijing China adapter->ahw.cmdDescHead = NULL; 3359a5557fdSlucy wang - Sun Microsystems - Beijing China } 3369a5557fdSlucy wang - Sun Microsystems - Beijing China 3379a5557fdSlucy wang - Sun Microsystems - Beijing China for (ctx = 0; ctx < MAX_RCV_CTX; ++ctx) { 3389a5557fdSlucy wang - Sun Microsystems - Beijing China recv_ctx = &adapter->recv_ctx[ctx]; 3399a5557fdSlucy wang - Sun Microsystems - Beijing China for (ring = 0; ring < adapter->max_rds_rings; ring++) { 3409a5557fdSlucy wang - Sun Microsystems - Beijing China rcv_desc = &recv_ctx->rcv_desc[ring]; 3419a5557fdSlucy wang - Sun Microsystems - Beijing China 3429a5557fdSlucy wang - Sun Microsystems - Beijing China if (rcv_desc->desc_head != NULL) { 3439a5557fdSlucy wang - Sun Microsystems - Beijing China unm_pci_free_consistent( 3449a5557fdSlucy wang - Sun Microsystems - Beijing China &rcv_desc->rx_desc_dma_handle, 3459a5557fdSlucy wang - Sun Microsystems - Beijing China &rcv_desc->rx_desc_acc_handle); 3469a5557fdSlucy wang - Sun Microsystems - Beijing China rcv_desc->desc_head = NULL; 3479a5557fdSlucy wang - Sun Microsystems - Beijing China rcv_desc->phys_addr = NULL; 3489a5557fdSlucy wang - Sun Microsystems - Beijing China } 3499a5557fdSlucy wang - Sun Microsystems - Beijing China } 3509a5557fdSlucy wang - Sun Microsystems - Beijing China 3519a5557fdSlucy wang - Sun Microsystems - Beijing China if (recv_ctx->rcvStatusDescHead != NULL) { 3529a5557fdSlucy wang - Sun Microsystems - Beijing China unm_pci_free_consistent( 3539a5557fdSlucy wang - Sun Microsystems - Beijing China &recv_ctx->status_desc_dma_handle, 3549a5557fdSlucy wang - Sun Microsystems - Beijing China &recv_ctx->status_desc_acc_handle); 3559a5557fdSlucy wang - Sun Microsystems - Beijing China recv_ctx->rcvStatusDesc_physAddr = NULL; 3569a5557fdSlucy wang - Sun Microsystems - Beijing China recv_ctx->rcvStatusDescHead = NULL; 3579a5557fdSlucy wang - Sun Microsystems - Beijing China } 3589a5557fdSlucy wang - Sun Microsystems - Beijing China } 3599a5557fdSlucy wang - Sun Microsystems - Beijing China } 3609a5557fdSlucy wang - Sun Microsystems - Beijing China 3619a5557fdSlucy wang - Sun Microsystems - Beijing China static void 3629a5557fdSlucy wang - Sun Microsystems - Beijing China cleanup_adapter(struct unm_adapter_s *adapter) 3639a5557fdSlucy wang - Sun Microsystems - Beijing China { 3649a5557fdSlucy wang - Sun Microsystems - Beijing China ddi_regs_map_free(&(adapter->regs_handle)); 3659a5557fdSlucy wang - Sun Microsystems - Beijing China ddi_regs_map_free(&(adapter->db_handle)); 3669a5557fdSlucy wang - Sun Microsystems - Beijing China kmem_free(adapter, sizeof (unm_adapter)); 3679a5557fdSlucy wang - Sun Microsystems - Beijing China } 3689a5557fdSlucy wang - Sun Microsystems - Beijing China 3699a5557fdSlucy wang - Sun Microsystems - Beijing China void 3709a5557fdSlucy wang - Sun Microsystems - Beijing China unm_nic_remove(unm_adapter *adapter) 3719a5557fdSlucy wang - Sun Microsystems - Beijing China { 3729a5557fdSlucy wang - Sun Microsystems - Beijing China mac_link_update(adapter->mach, LINK_STATE_DOWN); 3739a5557fdSlucy wang - Sun Microsystems - Beijing China unm_nic_stop_port(adapter); 3749a5557fdSlucy wang - Sun Microsystems - Beijing China 3759a5557fdSlucy wang - Sun Microsystems - Beijing China if (adapter->interrupt_crb) { 3769a5557fdSlucy wang - Sun Microsystems - Beijing China UNM_READ_LOCK(&adapter->adapter_lock); 3779a5557fdSlucy wang - Sun Microsystems - Beijing China unm_nic_disable_int(adapter); 3789a5557fdSlucy wang - Sun Microsystems - Beijing China UNM_READ_UNLOCK(&adapter->adapter_lock); 3799a5557fdSlucy wang - Sun Microsystems - Beijing China } 3809a5557fdSlucy wang - Sun Microsystems - Beijing China (void) untimeout(adapter->watchdog_timer); 3819a5557fdSlucy wang - Sun Microsystems - Beijing China 3829a5557fdSlucy wang - Sun Microsystems - Beijing China unm_free_hw_resources(adapter); 3839a5557fdSlucy wang - Sun Microsystems - Beijing China 384dda0720aSjing xiong ERI-SUN if (adapter->is_up == UNM_ADAPTER_UP_MAGIC) 385dda0720aSjing xiong ERI-SUN destroy_rxtx_rings(adapter); 3869a5557fdSlucy wang - Sun Microsystems - Beijing China 3879a5557fdSlucy wang - Sun Microsystems - Beijing China if (adapter->portnum == 0) 3889a5557fdSlucy wang - Sun Microsystems - Beijing China unm_free_dummy_dma(adapter); 3899a5557fdSlucy wang - Sun Microsystems - Beijing China 3909a5557fdSlucy wang - Sun Microsystems - Beijing China unm_destroy_intr(adapter); 3919a5557fdSlucy wang - Sun Microsystems - Beijing China 3929a5557fdSlucy wang - Sun Microsystems - Beijing China ddi_set_driver_private(adapter->dip, NULL); 3939a5557fdSlucy wang - Sun Microsystems - Beijing China cleanup_adapter(adapter); 3949a5557fdSlucy wang - Sun Microsystems - Beijing China } 3959a5557fdSlucy wang - Sun Microsystems - Beijing China 3969a5557fdSlucy wang - Sun Microsystems - Beijing China static int 3979a5557fdSlucy wang - Sun Microsystems - Beijing China init_firmware(unm_adapter *adapter) 3989a5557fdSlucy wang - Sun Microsystems - Beijing China { 3999a5557fdSlucy wang - Sun Microsystems - Beijing China uint32_t state = 0, loops = 0, tempout; 4009a5557fdSlucy wang - Sun Microsystems - Beijing China 4019a5557fdSlucy wang - Sun Microsystems - Beijing China /* Window 1 call */ 4029a5557fdSlucy wang - Sun Microsystems - Beijing China UNM_READ_LOCK(&adapter->adapter_lock); 4039a5557fdSlucy wang - Sun Microsystems - Beijing China state = adapter->unm_nic_pci_read_normalize(adapter, CRB_CMDPEG_STATE); 4049a5557fdSlucy wang - Sun Microsystems - Beijing China UNM_READ_UNLOCK(&adapter->adapter_lock); 4059a5557fdSlucy wang - Sun Microsystems - Beijing China 4069a5557fdSlucy wang - Sun Microsystems - Beijing China if (state == PHAN_INITIALIZE_ACK) 4079a5557fdSlucy wang - Sun Microsystems - Beijing China return (0); 4089a5557fdSlucy wang - Sun Microsystems - Beijing China 4099a5557fdSlucy wang - Sun Microsystems - Beijing China while (state != PHAN_INITIALIZE_COMPLETE && loops < 200000) { 4109a5557fdSlucy wang - Sun Microsystems - Beijing China drv_usecwait(100); 4119a5557fdSlucy wang - Sun Microsystems - Beijing China /* Window 1 call */ 4129a5557fdSlucy wang - Sun Microsystems - Beijing China UNM_READ_LOCK(&adapter->adapter_lock); 4139a5557fdSlucy wang - Sun Microsystems - Beijing China state = adapter->unm_nic_pci_read_normalize(adapter, 4149a5557fdSlucy wang - Sun Microsystems - Beijing China CRB_CMDPEG_STATE); 4159a5557fdSlucy wang - Sun Microsystems - Beijing China UNM_READ_UNLOCK(&adapter->adapter_lock); 4169a5557fdSlucy wang - Sun Microsystems - Beijing China loops++; 4179a5557fdSlucy wang - Sun Microsystems - Beijing China } 4189a5557fdSlucy wang - Sun Microsystems - Beijing China 4199a5557fdSlucy wang - Sun Microsystems - Beijing China if (loops >= 200000) { 4209a5557fdSlucy wang - Sun Microsystems - Beijing China cmn_err(CE_WARN, "%s%d: CmdPeg init incomplete:%x\n", 4219a5557fdSlucy wang - Sun Microsystems - Beijing China adapter->name, adapter->instance, state); 4229a5557fdSlucy wang - Sun Microsystems - Beijing China return (-EIO); 4239a5557fdSlucy wang - Sun Microsystems - Beijing China } 4249a5557fdSlucy wang - Sun Microsystems - Beijing China 4259a5557fdSlucy wang - Sun Microsystems - Beijing China /* Window 1 call */ 4269a5557fdSlucy wang - Sun Microsystems - Beijing China UNM_READ_LOCK(&adapter->adapter_lock); 4279a5557fdSlucy wang - Sun Microsystems - Beijing China tempout = INTR_SCHEME_PERPORT; 4289a5557fdSlucy wang - Sun Microsystems - Beijing China adapter->unm_nic_hw_write_wx(adapter, CRB_NIC_CAPABILITIES_HOST, 4299a5557fdSlucy wang - Sun Microsystems - Beijing China &tempout, 4); 4309a5557fdSlucy wang - Sun Microsystems - Beijing China tempout = MSI_MODE_MULTIFUNC; 4319a5557fdSlucy wang - Sun Microsystems - Beijing China adapter->unm_nic_hw_write_wx(adapter, CRB_NIC_MSI_MODE_HOST, 4329a5557fdSlucy wang - Sun Microsystems - Beijing China &tempout, 4); 4339a5557fdSlucy wang - Sun Microsystems - Beijing China tempout = MPORT_MULTI_FUNCTION_MODE; 4349a5557fdSlucy wang - Sun Microsystems - Beijing China adapter->unm_nic_hw_write_wx(adapter, CRB_MPORT_MODE, &tempout, 4); 4359a5557fdSlucy wang - Sun Microsystems - Beijing China tempout = PHAN_INITIALIZE_ACK; 4369a5557fdSlucy wang - Sun Microsystems - Beijing China adapter->unm_nic_hw_write_wx(adapter, CRB_CMDPEG_STATE, &tempout, 4); 4379a5557fdSlucy wang - Sun Microsystems - Beijing China UNM_READ_UNLOCK(&adapter->adapter_lock); 4389a5557fdSlucy wang - Sun Microsystems - Beijing China 4399a5557fdSlucy wang - Sun Microsystems - Beijing China return (0); 4409a5557fdSlucy wang - Sun Microsystems - Beijing China } 4419a5557fdSlucy wang - Sun Microsystems - Beijing China 4429a5557fdSlucy wang - Sun Microsystems - Beijing China /* 4439a5557fdSlucy wang - Sun Microsystems - Beijing China * Utility to synchronize with receive peg. 4449a5557fdSlucy wang - Sun Microsystems - Beijing China * Returns 0 on sucess 4459a5557fdSlucy wang - Sun Microsystems - Beijing China * -EIO on error 4469a5557fdSlucy wang - Sun Microsystems - Beijing China */ 4479a5557fdSlucy wang - Sun Microsystems - Beijing China int 4489a5557fdSlucy wang - Sun Microsystems - Beijing China receive_peg_ready(struct unm_adapter_s *adapter) 4499a5557fdSlucy wang - Sun Microsystems - Beijing China { 4509a5557fdSlucy wang - Sun Microsystems - Beijing China uint32_t state = 0; 4519a5557fdSlucy wang - Sun Microsystems - Beijing China int loops = 0, err = 0; 4529a5557fdSlucy wang - Sun Microsystems - Beijing China 4539a5557fdSlucy wang - Sun Microsystems - Beijing China /* Window 1 call */ 4549a5557fdSlucy wang - Sun Microsystems - Beijing China UNM_READ_LOCK(&adapter->adapter_lock); 4559a5557fdSlucy wang - Sun Microsystems - Beijing China state = adapter->unm_nic_pci_read_normalize(adapter, CRB_RCVPEG_STATE); 4569a5557fdSlucy wang - Sun Microsystems - Beijing China UNM_READ_UNLOCK(&adapter->adapter_lock); 4579a5557fdSlucy wang - Sun Microsystems - Beijing China 4589a5557fdSlucy wang - Sun Microsystems - Beijing China while ((state != PHAN_PEG_RCV_INITIALIZED) && (loops < 20000)) { 4599a5557fdSlucy wang - Sun Microsystems - Beijing China drv_usecwait(100); 4609a5557fdSlucy wang - Sun Microsystems - Beijing China /* Window 1 call */ 4619a5557fdSlucy wang - Sun Microsystems - Beijing China 4629a5557fdSlucy wang - Sun Microsystems - Beijing China UNM_READ_LOCK(&adapter->adapter_lock); 4639a5557fdSlucy wang - Sun Microsystems - Beijing China state = adapter->unm_nic_pci_read_normalize(adapter, 4649a5557fdSlucy wang - Sun Microsystems - Beijing China CRB_RCVPEG_STATE); 4659a5557fdSlucy wang - Sun Microsystems - Beijing China UNM_READ_UNLOCK(&adapter->adapter_lock); 4669a5557fdSlucy wang - Sun Microsystems - Beijing China 4679a5557fdSlucy wang - Sun Microsystems - Beijing China loops++; 4689a5557fdSlucy wang - Sun Microsystems - Beijing China } 4699a5557fdSlucy wang - Sun Microsystems - Beijing China 4709a5557fdSlucy wang - Sun Microsystems - Beijing China if (loops >= 20000) { 4719a5557fdSlucy wang - Sun Microsystems - Beijing China cmn_err(CE_WARN, "Receive Peg initialization incomplete 0x%x\n", 4729a5557fdSlucy wang - Sun Microsystems - Beijing China state); 4739a5557fdSlucy wang - Sun Microsystems - Beijing China err = -EIO; 4749a5557fdSlucy wang - Sun Microsystems - Beijing China } 4759a5557fdSlucy wang - Sun Microsystems - Beijing China 4769a5557fdSlucy wang - Sun Microsystems - Beijing China return (err); 4779a5557fdSlucy wang - Sun Microsystems - Beijing China } 4789a5557fdSlucy wang - Sun Microsystems - Beijing China 4799a5557fdSlucy wang - Sun Microsystems - Beijing China /* 4809a5557fdSlucy wang - Sun Microsystems - Beijing China * check if the firmware has been downloaded and ready to run and 4819a5557fdSlucy wang - Sun Microsystems - Beijing China * setup the address for the descriptors in the adapter 4829a5557fdSlucy wang - Sun Microsystems - Beijing China */ 4839a5557fdSlucy wang - Sun Microsystems - Beijing China static int 4849a5557fdSlucy wang - Sun Microsystems - Beijing China unm_nic_hw_resources(unm_adapter *adapter) 4859a5557fdSlucy wang - Sun Microsystems - Beijing China { 4869a5557fdSlucy wang - Sun Microsystems - Beijing China hardware_context *hw = &adapter->ahw; 4879a5557fdSlucy wang - Sun Microsystems - Beijing China void *addr; 4889a5557fdSlucy wang - Sun Microsystems - Beijing China int err; 4899a5557fdSlucy wang - Sun Microsystems - Beijing China int ctx, ring; 4909a5557fdSlucy wang - Sun Microsystems - Beijing China unm_recv_context_t *recv_ctx; 4919a5557fdSlucy wang - Sun Microsystems - Beijing China unm_rcv_desc_ctx_t *rcv_desc; 4929a5557fdSlucy wang - Sun Microsystems - Beijing China ddi_dma_cookie_t cookie; 4939a5557fdSlucy wang - Sun Microsystems - Beijing China int size; 4949a5557fdSlucy wang - Sun Microsystems - Beijing China 4959a5557fdSlucy wang - Sun Microsystems - Beijing China if (err = receive_peg_ready(adapter)) 4969a5557fdSlucy wang - Sun Microsystems - Beijing China return (err); 4979a5557fdSlucy wang - Sun Microsystems - Beijing China 4989a5557fdSlucy wang - Sun Microsystems - Beijing China size = (sizeof (RingContext) + sizeof (uint32_t)); 4999a5557fdSlucy wang - Sun Microsystems - Beijing China 5009a5557fdSlucy wang - Sun Microsystems - Beijing China err = unm_pci_alloc_consistent(adapter, 5019a5557fdSlucy wang - Sun Microsystems - Beijing China size, (caddr_t *)&addr, &cookie, 5029a5557fdSlucy wang - Sun Microsystems - Beijing China &adapter->ctxDesc_dma_handle, 5039a5557fdSlucy wang - Sun Microsystems - Beijing China &adapter->ctxDesc_acc_handle); 5049a5557fdSlucy wang - Sun Microsystems - Beijing China if (err != DDI_SUCCESS) { 5059a5557fdSlucy wang - Sun Microsystems - Beijing China cmn_err(CE_WARN, "Failed to allocate HW context\n"); 5069a5557fdSlucy wang - Sun Microsystems - Beijing China return (err); 5079a5557fdSlucy wang - Sun Microsystems - Beijing China } 5089a5557fdSlucy wang - Sun Microsystems - Beijing China 5099a5557fdSlucy wang - Sun Microsystems - Beijing China adapter->ctxDesc_physAddr = cookie.dmac_laddress; 5109a5557fdSlucy wang - Sun Microsystems - Beijing China 5119a5557fdSlucy wang - Sun Microsystems - Beijing China (void) memset(addr, 0, sizeof (RingContext)); 5129a5557fdSlucy wang - Sun Microsystems - Beijing China 5139a5557fdSlucy wang - Sun Microsystems - Beijing China adapter->ctxDesc = (RingContext *) addr; 5149a5557fdSlucy wang - Sun Microsystems - Beijing China adapter->ctxDesc->CtxId = adapter->portnum; 5159a5557fdSlucy wang - Sun Microsystems - Beijing China adapter->ctxDesc->CMD_CONSUMER_OFFSET = 5169a5557fdSlucy wang - Sun Microsystems - Beijing China adapter->ctxDesc_physAddr + sizeof (RingContext); 5179a5557fdSlucy wang - Sun Microsystems - Beijing China adapter->cmdConsumer = 5189a5557fdSlucy wang - Sun Microsystems - Beijing China (uint32_t *)(uintptr_t)(((char *)addr) + sizeof (RingContext)); 5199a5557fdSlucy wang - Sun Microsystems - Beijing China 5209a5557fdSlucy wang - Sun Microsystems - Beijing China ASSERT(!((unsigned long)adapter->ctxDesc_physAddr & 0x3f)); 5219a5557fdSlucy wang - Sun Microsystems - Beijing China 5229a5557fdSlucy wang - Sun Microsystems - Beijing China /* 5239a5557fdSlucy wang - Sun Microsystems - Beijing China * Allocate command descriptor ring. 5249a5557fdSlucy wang - Sun Microsystems - Beijing China */ 5259a5557fdSlucy wang - Sun Microsystems - Beijing China size = (sizeof (cmdDescType0_t) * adapter->MaxTxDescCount); 5269a5557fdSlucy wang - Sun Microsystems - Beijing China err = unm_pci_alloc_consistent(adapter, 5279a5557fdSlucy wang - Sun Microsystems - Beijing China size, (caddr_t *)&addr, &cookie, 5289a5557fdSlucy wang - Sun Microsystems - Beijing China &hw->cmd_desc_dma_handle, 5299a5557fdSlucy wang - Sun Microsystems - Beijing China &hw->cmd_desc_acc_handle); 5309a5557fdSlucy wang - Sun Microsystems - Beijing China if (err != DDI_SUCCESS) { 5319a5557fdSlucy wang - Sun Microsystems - Beijing China cmn_err(CE_WARN, "Failed to allocate cmd desc ring\n"); 5329a5557fdSlucy wang - Sun Microsystems - Beijing China return (err); 5339a5557fdSlucy wang - Sun Microsystems - Beijing China } 5349a5557fdSlucy wang - Sun Microsystems - Beijing China 5359a5557fdSlucy wang - Sun Microsystems - Beijing China hw->cmdDesc_physAddr = cookie.dmac_laddress; 5369a5557fdSlucy wang - Sun Microsystems - Beijing China hw->cmdDescHead = (cmdDescType0_t *)addr; 5379a5557fdSlucy wang - Sun Microsystems - Beijing China 5389a5557fdSlucy wang - Sun Microsystems - Beijing China for (ctx = 0; ctx < MAX_RCV_CTX; ++ctx) { 5399a5557fdSlucy wang - Sun Microsystems - Beijing China recv_ctx = &adapter->recv_ctx[ctx]; 5409a5557fdSlucy wang - Sun Microsystems - Beijing China 5419a5557fdSlucy wang - Sun Microsystems - Beijing China size = (sizeof (statusDesc_t)* adapter->MaxRxDescCount); 5429a5557fdSlucy wang - Sun Microsystems - Beijing China err = unm_pci_alloc_consistent(adapter, 5439a5557fdSlucy wang - Sun Microsystems - Beijing China size, (caddr_t *)&addr, 5449a5557fdSlucy wang - Sun Microsystems - Beijing China &recv_ctx->status_desc_dma_cookie, 5459a5557fdSlucy wang - Sun Microsystems - Beijing China &recv_ctx->status_desc_dma_handle, 5469a5557fdSlucy wang - Sun Microsystems - Beijing China &recv_ctx->status_desc_acc_handle); 5479a5557fdSlucy wang - Sun Microsystems - Beijing China if (err != DDI_SUCCESS) { 5489a5557fdSlucy wang - Sun Microsystems - Beijing China cmn_err(CE_WARN, "Failed to allocate sts desc ring\n"); 5499a5557fdSlucy wang - Sun Microsystems - Beijing China goto free_cmd_desc; 5509a5557fdSlucy wang - Sun Microsystems - Beijing China } 5519a5557fdSlucy wang - Sun Microsystems - Beijing China 5529a5557fdSlucy wang - Sun Microsystems - Beijing China (void) memset(addr, 0, size); 5539a5557fdSlucy wang - Sun Microsystems - Beijing China recv_ctx->rcvStatusDesc_physAddr = 5549a5557fdSlucy wang - Sun Microsystems - Beijing China recv_ctx->status_desc_dma_cookie.dmac_laddress; 5559a5557fdSlucy wang - Sun Microsystems - Beijing China recv_ctx->rcvStatusDescHead = (statusDesc_t *)addr; 5569a5557fdSlucy wang - Sun Microsystems - Beijing China 5579a5557fdSlucy wang - Sun Microsystems - Beijing China /* rds rings */ 5589a5557fdSlucy wang - Sun Microsystems - Beijing China for (ring = 0; ring < adapter->max_rds_rings; ring++) { 5599a5557fdSlucy wang - Sun Microsystems - Beijing China rcv_desc = &recv_ctx->rcv_desc[ring]; 5609a5557fdSlucy wang - Sun Microsystems - Beijing China 5619a5557fdSlucy wang - Sun Microsystems - Beijing China size = (sizeof (rcvDesc_t) * adapter->MaxRxDescCount); 5629a5557fdSlucy wang - Sun Microsystems - Beijing China err = unm_pci_alloc_consistent(adapter, 5639a5557fdSlucy wang - Sun Microsystems - Beijing China size, (caddr_t *)&addr, 5649a5557fdSlucy wang - Sun Microsystems - Beijing China &rcv_desc->rx_desc_dma_cookie, 5659a5557fdSlucy wang - Sun Microsystems - Beijing China &rcv_desc->rx_desc_dma_handle, 5669a5557fdSlucy wang - Sun Microsystems - Beijing China &rcv_desc->rx_desc_acc_handle); 5679a5557fdSlucy wang - Sun Microsystems - Beijing China if (err != DDI_SUCCESS) { 5689a5557fdSlucy wang - Sun Microsystems - Beijing China cmn_err(CE_WARN, "Failed to allocate " 5699a5557fdSlucy wang - Sun Microsystems - Beijing China "rx desc ring %d\n", ring); 5709a5557fdSlucy wang - Sun Microsystems - Beijing China goto free_status_desc; 5719a5557fdSlucy wang - Sun Microsystems - Beijing China } 5729a5557fdSlucy wang - Sun Microsystems - Beijing China 5739a5557fdSlucy wang - Sun Microsystems - Beijing China rcv_desc->phys_addr = 5749a5557fdSlucy wang - Sun Microsystems - Beijing China rcv_desc->rx_desc_dma_cookie.dmac_laddress; 5759a5557fdSlucy wang - Sun Microsystems - Beijing China rcv_desc->desc_head = (rcvDesc_t *)addr; 5769a5557fdSlucy wang - Sun Microsystems - Beijing China } 5779a5557fdSlucy wang - Sun Microsystems - Beijing China } 5789a5557fdSlucy wang - Sun Microsystems - Beijing China 5799a5557fdSlucy wang - Sun Microsystems - Beijing China if (err = netxen_create_rxtx(adapter)) 5809a5557fdSlucy wang - Sun Microsystems - Beijing China goto free_statusrx_desc; 5819a5557fdSlucy wang - Sun Microsystems - Beijing China adapter->context_alloced = 1; 5829a5557fdSlucy wang - Sun Microsystems - Beijing China 5839a5557fdSlucy wang - Sun Microsystems - Beijing China return (DDI_SUCCESS); 5849a5557fdSlucy wang - Sun Microsystems - Beijing China 5859a5557fdSlucy wang - Sun Microsystems - Beijing China free_statusrx_desc: 5869a5557fdSlucy wang - Sun Microsystems - Beijing China free_status_desc: 5879a5557fdSlucy wang - Sun Microsystems - Beijing China free_cmd_desc: 5889a5557fdSlucy wang - Sun Microsystems - Beijing China unm_free_hw_resources(adapter); 5899a5557fdSlucy wang - Sun Microsystems - Beijing China 5909a5557fdSlucy wang - Sun Microsystems - Beijing China return (err); 5919a5557fdSlucy wang - Sun Microsystems - Beijing China } 5929a5557fdSlucy wang - Sun Microsystems - Beijing China 5939a5557fdSlucy wang - Sun Microsystems - Beijing China void unm_desc_dma_sync(ddi_dma_handle_t handle, uint_t start, uint_t count, 5949a5557fdSlucy wang - Sun Microsystems - Beijing China uint_t range, uint_t unit_size, uint_t direction) 5959a5557fdSlucy wang - Sun Microsystems - Beijing China { 5969a5557fdSlucy wang - Sun Microsystems - Beijing China if ((start + count) < range) { 5979a5557fdSlucy wang - Sun Microsystems - Beijing China (void) ddi_dma_sync(handle, start * unit_size, 5989a5557fdSlucy wang - Sun Microsystems - Beijing China count * unit_size, direction); 5999a5557fdSlucy wang - Sun Microsystems - Beijing China } else { 6009a5557fdSlucy wang - Sun Microsystems - Beijing China (void) ddi_dma_sync(handle, start * unit_size, 0, direction); 6019a5557fdSlucy wang - Sun Microsystems - Beijing China (void) ddi_dma_sync(handle, 0, 6029a5557fdSlucy wang - Sun Microsystems - Beijing China (start + count - range) * unit_size, DDI_DMA_SYNC_FORCPU); 6039a5557fdSlucy wang - Sun Microsystems - Beijing China } 6049a5557fdSlucy wang - Sun Microsystems - Beijing China } 6059a5557fdSlucy wang - Sun Microsystems - Beijing China 6069a5557fdSlucy wang - Sun Microsystems - Beijing China static uint32_t crb_cmd_producer[4] = { CRB_CMD_PRODUCER_OFFSET, 6079a5557fdSlucy wang - Sun Microsystems - Beijing China CRB_CMD_PRODUCER_OFFSET_1, CRB_CMD_PRODUCER_OFFSET_2, 6089a5557fdSlucy wang - Sun Microsystems - Beijing China CRB_CMD_PRODUCER_OFFSET_3 }; 6099a5557fdSlucy wang - Sun Microsystems - Beijing China 6109a5557fdSlucy wang - Sun Microsystems - Beijing China static uint32_t crb_cmd_consumer[4] = { CRB_CMD_CONSUMER_OFFSET, 6119a5557fdSlucy wang - Sun Microsystems - Beijing China CRB_CMD_CONSUMER_OFFSET_1, CRB_CMD_CONSUMER_OFFSET_2, 6129a5557fdSlucy wang - Sun Microsystems - Beijing China CRB_CMD_CONSUMER_OFFSET_3 }; 6139a5557fdSlucy wang - Sun Microsystems - Beijing China 6149a5557fdSlucy wang - Sun Microsystems - Beijing China void 6159a5557fdSlucy wang - Sun Microsystems - Beijing China unm_nic_update_cmd_producer(struct unm_adapter_s *adapter, 6169a5557fdSlucy wang - Sun Microsystems - Beijing China uint32_t crb_producer) 6179a5557fdSlucy wang - Sun Microsystems - Beijing China { 6189a5557fdSlucy wang - Sun Microsystems - Beijing China int data = crb_producer; 6199a5557fdSlucy wang - Sun Microsystems - Beijing China 6209a5557fdSlucy wang - Sun Microsystems - Beijing China if (adapter->crb_addr_cmd_producer) { 6219a5557fdSlucy wang - Sun Microsystems - Beijing China UNM_READ_LOCK(&adapter->adapter_lock); 6229a5557fdSlucy wang - Sun Microsystems - Beijing China adapter->unm_nic_hw_write_wx(adapter, 6239a5557fdSlucy wang - Sun Microsystems - Beijing China adapter->crb_addr_cmd_producer, &data, 4); 6249a5557fdSlucy wang - Sun Microsystems - Beijing China UNM_READ_UNLOCK(&adapter->adapter_lock); 6259a5557fdSlucy wang - Sun Microsystems - Beijing China } 6269a5557fdSlucy wang - Sun Microsystems - Beijing China } 6279a5557fdSlucy wang - Sun Microsystems - Beijing China 6289a5557fdSlucy wang - Sun Microsystems - Beijing China static void 6299a5557fdSlucy wang - Sun Microsystems - Beijing China unm_nic_update_cmd_consumer(struct unm_adapter_s *adapter, 6309a5557fdSlucy wang - Sun Microsystems - Beijing China uint32_t crb_producer) 6319a5557fdSlucy wang - Sun Microsystems - Beijing China { 6329a5557fdSlucy wang - Sun Microsystems - Beijing China int data = crb_producer; 6339a5557fdSlucy wang - Sun Microsystems - Beijing China 6349a5557fdSlucy wang - Sun Microsystems - Beijing China if (adapter->crb_addr_cmd_consumer) 6359a5557fdSlucy wang - Sun Microsystems - Beijing China adapter->unm_nic_hw_write_wx(adapter, 6369a5557fdSlucy wang - Sun Microsystems - Beijing China adapter->crb_addr_cmd_consumer, &data, 4); 6379a5557fdSlucy wang - Sun Microsystems - Beijing China } 6389a5557fdSlucy wang - Sun Microsystems - Beijing China 6399a5557fdSlucy wang - Sun Microsystems - Beijing China /* 6409a5557fdSlucy wang - Sun Microsystems - Beijing China * Looks for type of packet and sets opcode accordingly 6419a5557fdSlucy wang - Sun Microsystems - Beijing China * so that checksum offload can be used. 6429a5557fdSlucy wang - Sun Microsystems - Beijing China */ 6439a5557fdSlucy wang - Sun Microsystems - Beijing China static void 6449a5557fdSlucy wang - Sun Microsystems - Beijing China unm_tx_csum(cmdDescType0_t *desc, mblk_t *mp, pktinfo_t *pktinfo) 6459a5557fdSlucy wang - Sun Microsystems - Beijing China { 6469a5557fdSlucy wang - Sun Microsystems - Beijing China if (pktinfo->mac_hlen == sizeof (struct ether_vlan_header)) 6479a5557fdSlucy wang - Sun Microsystems - Beijing China desc->u1.s1.flags = FLAGS_VLAN_TAGGED; 6489a5557fdSlucy wang - Sun Microsystems - Beijing China 6499a5557fdSlucy wang - Sun Microsystems - Beijing China if (pktinfo->etype == htons(ETHERTYPE_IP)) { 6509a5557fdSlucy wang - Sun Microsystems - Beijing China uint32_t start, flags; 6519a5557fdSlucy wang - Sun Microsystems - Beijing China 652*0dc2366fSVenugopal Iyer mac_hcksum_get(mp, &start, NULL, NULL, NULL, &flags); 6539a5557fdSlucy wang - Sun Microsystems - Beijing China if ((flags & (HCK_FULLCKSUM | HCK_IPV4_HDRCKSUM)) == 0) 6549a5557fdSlucy wang - Sun Microsystems - Beijing China return; 6559a5557fdSlucy wang - Sun Microsystems - Beijing China 6569a5557fdSlucy wang - Sun Microsystems - Beijing China /* 6579a5557fdSlucy wang - Sun Microsystems - Beijing China * For TCP/UDP, ask hardware to do both IP header and 6589a5557fdSlucy wang - Sun Microsystems - Beijing China * full checksum, even if stack has already done one or 6599a5557fdSlucy wang - Sun Microsystems - Beijing China * the other. Hardware will always get it correct even 6609a5557fdSlucy wang - Sun Microsystems - Beijing China * if stack has already done it. 6619a5557fdSlucy wang - Sun Microsystems - Beijing China */ 6629a5557fdSlucy wang - Sun Microsystems - Beijing China switch (pktinfo->l4_proto) { 6639a5557fdSlucy wang - Sun Microsystems - Beijing China case IPPROTO_TCP: 6649a5557fdSlucy wang - Sun Microsystems - Beijing China desc->u1.s1.opcode = TX_TCP_PKT; 6659a5557fdSlucy wang - Sun Microsystems - Beijing China break; 6669a5557fdSlucy wang - Sun Microsystems - Beijing China case IPPROTO_UDP: 6679a5557fdSlucy wang - Sun Microsystems - Beijing China desc->u1.s1.opcode = TX_UDP_PKT; 6689a5557fdSlucy wang - Sun Microsystems - Beijing China break; 6699a5557fdSlucy wang - Sun Microsystems - Beijing China default: 6709a5557fdSlucy wang - Sun Microsystems - Beijing China /* Must be here with HCK_IPV4_HDRCKSUM */ 6719a5557fdSlucy wang - Sun Microsystems - Beijing China desc->u1.s1.opcode = TX_IP_PKT; 6729a5557fdSlucy wang - Sun Microsystems - Beijing China return; 6739a5557fdSlucy wang - Sun Microsystems - Beijing China } 6749a5557fdSlucy wang - Sun Microsystems - Beijing China 6759a5557fdSlucy wang - Sun Microsystems - Beijing China desc->u1.s1.ipHdrOffset = pktinfo->mac_hlen; 6769a5557fdSlucy wang - Sun Microsystems - Beijing China desc->u1.s1.tcpHdrOffset = pktinfo->mac_hlen + pktinfo->ip_hlen; 6779a5557fdSlucy wang - Sun Microsystems - Beijing China } 6789a5557fdSlucy wang - Sun Microsystems - Beijing China } 6799a5557fdSlucy wang - Sun Microsystems - Beijing China 6809a5557fdSlucy wang - Sun Microsystems - Beijing China /* 6819a5557fdSlucy wang - Sun Microsystems - Beijing China * For IP/UDP/TCP checksum offload, this checks for MAC+IP header in one 6829a5557fdSlucy wang - Sun Microsystems - Beijing China * contiguous block ending at 8 byte aligned address as required by hardware. 6839a5557fdSlucy wang - Sun Microsystems - Beijing China * Caller assumes pktinfo->total_len will be updated by this function and 6849a5557fdSlucy wang - Sun Microsystems - Beijing China * if pktinfo->etype is set to 0, it will need to linearize the mblk and 6859a5557fdSlucy wang - Sun Microsystems - Beijing China * invoke unm_update_pkt_info() to determine ethertype, IP header len and 6869a5557fdSlucy wang - Sun Microsystems - Beijing China * protocol. 6879a5557fdSlucy wang - Sun Microsystems - Beijing China */ 6889a5557fdSlucy wang - Sun Microsystems - Beijing China static boolean_t 6899a5557fdSlucy wang - Sun Microsystems - Beijing China unm_get_pkt_info(mblk_t *mp, pktinfo_t *pktinfo) 6909a5557fdSlucy wang - Sun Microsystems - Beijing China { 6919a5557fdSlucy wang - Sun Microsystems - Beijing China mblk_t *bp; 6929a5557fdSlucy wang - Sun Microsystems - Beijing China ushort_t type; 6939a5557fdSlucy wang - Sun Microsystems - Beijing China 6949a5557fdSlucy wang - Sun Microsystems - Beijing China (void) memset(pktinfo, 0, sizeof (pktinfo_t)); 6959a5557fdSlucy wang - Sun Microsystems - Beijing China 6969a5557fdSlucy wang - Sun Microsystems - Beijing China for (bp = mp; bp != NULL; bp = bp->b_cont) { 6979a5557fdSlucy wang - Sun Microsystems - Beijing China if (MBLKL(bp) == 0) 6989a5557fdSlucy wang - Sun Microsystems - Beijing China continue; 6999a5557fdSlucy wang - Sun Microsystems - Beijing China pktinfo->mblk_no++; 7009a5557fdSlucy wang - Sun Microsystems - Beijing China pktinfo->total_len += MBLKL(bp); 7019a5557fdSlucy wang - Sun Microsystems - Beijing China } 7029a5557fdSlucy wang - Sun Microsystems - Beijing China 7039a5557fdSlucy wang - Sun Microsystems - Beijing China if (MBLKL(mp) < (sizeof (struct ether_header) + sizeof (ipha_t))) 7049a5557fdSlucy wang - Sun Microsystems - Beijing China return (B_FALSE); 7059a5557fdSlucy wang - Sun Microsystems - Beijing China 7069a5557fdSlucy wang - Sun Microsystems - Beijing China /* 7079a5557fdSlucy wang - Sun Microsystems - Beijing China * We just need non 1 byte aligned address, since ether_type is 7089a5557fdSlucy wang - Sun Microsystems - Beijing China * ushort. 7099a5557fdSlucy wang - Sun Microsystems - Beijing China */ 7109a5557fdSlucy wang - Sun Microsystems - Beijing China if ((uintptr_t)mp->b_rptr & 1) 7119a5557fdSlucy wang - Sun Microsystems - Beijing China return (B_FALSE); 7129a5557fdSlucy wang - Sun Microsystems - Beijing China 7139a5557fdSlucy wang - Sun Microsystems - Beijing China type = ((struct ether_header *)(uintptr_t)mp->b_rptr)->ether_type; 7149a5557fdSlucy wang - Sun Microsystems - Beijing China if (type == htons(ETHERTYPE_VLAN)) { 7159a5557fdSlucy wang - Sun Microsystems - Beijing China if (MBLKL(mp) < (sizeof (struct ether_vlan_header) + 7169a5557fdSlucy wang - Sun Microsystems - Beijing China sizeof (ipha_t))) 7179a5557fdSlucy wang - Sun Microsystems - Beijing China return (B_FALSE); 7189a5557fdSlucy wang - Sun Microsystems - Beijing China type = ((struct ether_vlan_header *) \ 7199a5557fdSlucy wang - Sun Microsystems - Beijing China (uintptr_t)mp->b_rptr)->ether_type; 7209a5557fdSlucy wang - Sun Microsystems - Beijing China pktinfo->mac_hlen = sizeof (struct ether_vlan_header); 7219a5557fdSlucy wang - Sun Microsystems - Beijing China } else { 7229a5557fdSlucy wang - Sun Microsystems - Beijing China pktinfo->mac_hlen = sizeof (struct ether_header); 7239a5557fdSlucy wang - Sun Microsystems - Beijing China } 7249a5557fdSlucy wang - Sun Microsystems - Beijing China pktinfo->etype = type; 7259a5557fdSlucy wang - Sun Microsystems - Beijing China 7269a5557fdSlucy wang - Sun Microsystems - Beijing China if (pktinfo->etype == htons(ETHERTYPE_IP)) { 7279a5557fdSlucy wang - Sun Microsystems - Beijing China uchar_t *ip_off = mp->b_rptr + pktinfo->mac_hlen; 7289a5557fdSlucy wang - Sun Microsystems - Beijing China 7299a5557fdSlucy wang - Sun Microsystems - Beijing China pktinfo->ip_hlen = IPH_HDR_LENGTH((uintptr_t)ip_off); 7309a5557fdSlucy wang - Sun Microsystems - Beijing China pktinfo->l4_proto = 7319a5557fdSlucy wang - Sun Microsystems - Beijing China ((ipha_t *)(uintptr_t)ip_off)->ipha_protocol; 7329a5557fdSlucy wang - Sun Microsystems - Beijing China 7339a5557fdSlucy wang - Sun Microsystems - Beijing China /* IP header not aligned to quadward boundary? */ 7349a5557fdSlucy wang - Sun Microsystems - Beijing China if ((unsigned long)(ip_off + pktinfo->ip_hlen) % 8 != 0) 7359a5557fdSlucy wang - Sun Microsystems - Beijing China return (B_FALSE); 7369a5557fdSlucy wang - Sun Microsystems - Beijing China } 7379a5557fdSlucy wang - Sun Microsystems - Beijing China 7389a5557fdSlucy wang - Sun Microsystems - Beijing China return (B_TRUE); 7399a5557fdSlucy wang - Sun Microsystems - Beijing China } 7409a5557fdSlucy wang - Sun Microsystems - Beijing China 7419a5557fdSlucy wang - Sun Microsystems - Beijing China static void 7429a5557fdSlucy wang - Sun Microsystems - Beijing China unm_update_pkt_info(char *ptr, pktinfo_t *pktinfo) 7439a5557fdSlucy wang - Sun Microsystems - Beijing China { 7449a5557fdSlucy wang - Sun Microsystems - Beijing China ushort_t type; 7459a5557fdSlucy wang - Sun Microsystems - Beijing China 7469a5557fdSlucy wang - Sun Microsystems - Beijing China type = ((struct ether_header *)(uintptr_t)ptr)->ether_type; 7479a5557fdSlucy wang - Sun Microsystems - Beijing China if (type == htons(ETHERTYPE_VLAN)) { 7489a5557fdSlucy wang - Sun Microsystems - Beijing China type = ((struct ether_vlan_header *)(uintptr_t)ptr)->ether_type; 7499a5557fdSlucy wang - Sun Microsystems - Beijing China pktinfo->mac_hlen = sizeof (struct ether_vlan_header); 7509a5557fdSlucy wang - Sun Microsystems - Beijing China } else { 7519a5557fdSlucy wang - Sun Microsystems - Beijing China pktinfo->mac_hlen = sizeof (struct ether_header); 7529a5557fdSlucy wang - Sun Microsystems - Beijing China } 7539a5557fdSlucy wang - Sun Microsystems - Beijing China pktinfo->etype = type; 7549a5557fdSlucy wang - Sun Microsystems - Beijing China 7559a5557fdSlucy wang - Sun Microsystems - Beijing China if (pktinfo->etype == htons(ETHERTYPE_IP)) { 7569a5557fdSlucy wang - Sun Microsystems - Beijing China char *ipp = ptr + pktinfo->mac_hlen; 7579a5557fdSlucy wang - Sun Microsystems - Beijing China 7589a5557fdSlucy wang - Sun Microsystems - Beijing China pktinfo->ip_hlen = IPH_HDR_LENGTH((uintptr_t)ipp); 7599a5557fdSlucy wang - Sun Microsystems - Beijing China pktinfo->l4_proto = ((ipha_t *)(uintptr_t)ipp)->ipha_protocol; 7609a5557fdSlucy wang - Sun Microsystems - Beijing China } 7619a5557fdSlucy wang - Sun Microsystems - Beijing China } 7629a5557fdSlucy wang - Sun Microsystems - Beijing China 7639a5557fdSlucy wang - Sun Microsystems - Beijing China static boolean_t 7649a5557fdSlucy wang - Sun Microsystems - Beijing China unm_send_copy(struct unm_adapter_s *adapter, mblk_t *mp, pktinfo_t *pktinfo) 7659a5557fdSlucy wang - Sun Microsystems - Beijing China { 7669a5557fdSlucy wang - Sun Microsystems - Beijing China hardware_context *hw; 7679a5557fdSlucy wang - Sun Microsystems - Beijing China u32 producer = 0; 7689a5557fdSlucy wang - Sun Microsystems - Beijing China cmdDescType0_t *hwdesc; 7699a5557fdSlucy wang - Sun Microsystems - Beijing China struct unm_cmd_buffer *pbuf = NULL; 7709a5557fdSlucy wang - Sun Microsystems - Beijing China u32 mblen; 7719a5557fdSlucy wang - Sun Microsystems - Beijing China int no_of_desc = 1; 7729a5557fdSlucy wang - Sun Microsystems - Beijing China int MaxTxDescCount; 7739a5557fdSlucy wang - Sun Microsystems - Beijing China mblk_t *bp; 7749a5557fdSlucy wang - Sun Microsystems - Beijing China char *txb; 7759a5557fdSlucy wang - Sun Microsystems - Beijing China 7769a5557fdSlucy wang - Sun Microsystems - Beijing China hw = &adapter->ahw; 7779a5557fdSlucy wang - Sun Microsystems - Beijing China MaxTxDescCount = adapter->MaxTxDescCount; 7789a5557fdSlucy wang - Sun Microsystems - Beijing China 7799a5557fdSlucy wang - Sun Microsystems - Beijing China UNM_SPIN_LOCK(&adapter->tx_lock); 7809a5557fdSlucy wang - Sun Microsystems - Beijing China membar_enter(); 7819a5557fdSlucy wang - Sun Microsystems - Beijing China 7829a5557fdSlucy wang - Sun Microsystems - Beijing China if (find_diff_among(adapter->cmdProducer, adapter->lastCmdConsumer, 7839a5557fdSlucy wang - Sun Microsystems - Beijing China MaxTxDescCount) <= 2) { 7849a5557fdSlucy wang - Sun Microsystems - Beijing China adapter->stats.outofcmddesc++; 7859a5557fdSlucy wang - Sun Microsystems - Beijing China adapter->resched_needed = 1; 7869a5557fdSlucy wang - Sun Microsystems - Beijing China membar_exit(); 7879a5557fdSlucy wang - Sun Microsystems - Beijing China UNM_SPIN_UNLOCK(&adapter->tx_lock); 7889a5557fdSlucy wang - Sun Microsystems - Beijing China return (B_FALSE); 7899a5557fdSlucy wang - Sun Microsystems - Beijing China } 7909a5557fdSlucy wang - Sun Microsystems - Beijing China adapter->freecmds -= no_of_desc; 7919a5557fdSlucy wang - Sun Microsystems - Beijing China 7929a5557fdSlucy wang - Sun Microsystems - Beijing China producer = adapter->cmdProducer; 7939a5557fdSlucy wang - Sun Microsystems - Beijing China 7949a5557fdSlucy wang - Sun Microsystems - Beijing China adapter->cmdProducer = get_index_range(adapter->cmdProducer, 7959a5557fdSlucy wang - Sun Microsystems - Beijing China MaxTxDescCount, no_of_desc); 7969a5557fdSlucy wang - Sun Microsystems - Beijing China 7979a5557fdSlucy wang - Sun Microsystems - Beijing China hwdesc = &hw->cmdDescHead[producer]; 7989a5557fdSlucy wang - Sun Microsystems - Beijing China (void) memset(hwdesc, 0, sizeof (cmdDescType0_t)); 7999a5557fdSlucy wang - Sun Microsystems - Beijing China pbuf = &adapter->cmd_buf_arr[producer]; 8009a5557fdSlucy wang - Sun Microsystems - Beijing China 8019a5557fdSlucy wang - Sun Microsystems - Beijing China pbuf->msg = NULL; 8029a5557fdSlucy wang - Sun Microsystems - Beijing China pbuf->head = NULL; 8039a5557fdSlucy wang - Sun Microsystems - Beijing China pbuf->tail = NULL; 8049a5557fdSlucy wang - Sun Microsystems - Beijing China 8059a5557fdSlucy wang - Sun Microsystems - Beijing China txb = pbuf->dma_area.vaddr; 8069a5557fdSlucy wang - Sun Microsystems - Beijing China 8079a5557fdSlucy wang - Sun Microsystems - Beijing China for (bp = mp; bp != NULL; bp = bp->b_cont) { 8089a5557fdSlucy wang - Sun Microsystems - Beijing China if ((mblen = MBLKL(bp)) == 0) 8099a5557fdSlucy wang - Sun Microsystems - Beijing China continue; 8109a5557fdSlucy wang - Sun Microsystems - Beijing China bcopy(bp->b_rptr, txb, mblen); 8119a5557fdSlucy wang - Sun Microsystems - Beijing China txb += mblen; 8129a5557fdSlucy wang - Sun Microsystems - Beijing China } 8139a5557fdSlucy wang - Sun Microsystems - Beijing China 8149a5557fdSlucy wang - Sun Microsystems - Beijing China /* 8159a5557fdSlucy wang - Sun Microsystems - Beijing China * Determine metadata if not previously done due to fragmented mblk. 8169a5557fdSlucy wang - Sun Microsystems - Beijing China */ 8179a5557fdSlucy wang - Sun Microsystems - Beijing China if (pktinfo->etype == 0) 8189a5557fdSlucy wang - Sun Microsystems - Beijing China unm_update_pkt_info(pbuf->dma_area.vaddr, pktinfo); 8199a5557fdSlucy wang - Sun Microsystems - Beijing China 8209a5557fdSlucy wang - Sun Microsystems - Beijing China (void) ddi_dma_sync(pbuf->dma_area.dma_hdl, 8219a5557fdSlucy wang - Sun Microsystems - Beijing China 0, pktinfo->total_len, DDI_DMA_SYNC_FORDEV); 8229a5557fdSlucy wang - Sun Microsystems - Beijing China 8239a5557fdSlucy wang - Sun Microsystems - Beijing China /* hwdesc->u1.s1.tcpHdrOffset = 0; */ 8249a5557fdSlucy wang - Sun Microsystems - Beijing China /* hwdesc->mss = 0; */ 8259a5557fdSlucy wang - Sun Microsystems - Beijing China hwdesc->u1.s1.opcode = TX_ETHER_PKT; 8269a5557fdSlucy wang - Sun Microsystems - Beijing China hwdesc->u3.s1.port = adapter->portnum; 8279a5557fdSlucy wang - Sun Microsystems - Beijing China hwdesc->u3.s1.ctx_id = adapter->portnum; 8289a5557fdSlucy wang - Sun Microsystems - Beijing China 8299a5557fdSlucy wang - Sun Microsystems - Beijing China hwdesc->u6.s1.buffer1Length = pktinfo->total_len; 8309a5557fdSlucy wang - Sun Microsystems - Beijing China hwdesc->u5.AddrBuffer1 = pbuf->dma_area.dma_addr; 8319a5557fdSlucy wang - Sun Microsystems - Beijing China hwdesc->u1.s1.numOfBuffers = 1; 8329a5557fdSlucy wang - Sun Microsystems - Beijing China hwdesc->u1.s1.totalLength = pktinfo->total_len; 8339a5557fdSlucy wang - Sun Microsystems - Beijing China 8349a5557fdSlucy wang - Sun Microsystems - Beijing China unm_tx_csum(hwdesc, mp, pktinfo); 8359a5557fdSlucy wang - Sun Microsystems - Beijing China 8369a5557fdSlucy wang - Sun Microsystems - Beijing China unm_desc_dma_sync(hw->cmd_desc_dma_handle, 8379a5557fdSlucy wang - Sun Microsystems - Beijing China producer, 8389a5557fdSlucy wang - Sun Microsystems - Beijing China no_of_desc, 8399a5557fdSlucy wang - Sun Microsystems - Beijing China MaxTxDescCount, 8409a5557fdSlucy wang - Sun Microsystems - Beijing China sizeof (cmdDescType0_t), 8419a5557fdSlucy wang - Sun Microsystems - Beijing China DDI_DMA_SYNC_FORDEV); 8429a5557fdSlucy wang - Sun Microsystems - Beijing China 8439a5557fdSlucy wang - Sun Microsystems - Beijing China hw->cmdProducer = adapter->cmdProducer; 8449a5557fdSlucy wang - Sun Microsystems - Beijing China unm_nic_update_cmd_producer(adapter, adapter->cmdProducer); 8459a5557fdSlucy wang - Sun Microsystems - Beijing China 8469a5557fdSlucy wang - Sun Microsystems - Beijing China adapter->stats.txbytes += pktinfo->total_len; 8479a5557fdSlucy wang - Sun Microsystems - Beijing China adapter->stats.xmitfinished++; 8489a5557fdSlucy wang - Sun Microsystems - Beijing China adapter->stats.txcopyed++; 8499a5557fdSlucy wang - Sun Microsystems - Beijing China UNM_SPIN_UNLOCK(&adapter->tx_lock); 8509a5557fdSlucy wang - Sun Microsystems - Beijing China 8519a5557fdSlucy wang - Sun Microsystems - Beijing China freemsg(mp); 8529a5557fdSlucy wang - Sun Microsystems - Beijing China return (B_TRUE); 8539a5557fdSlucy wang - Sun Microsystems - Beijing China } 8549a5557fdSlucy wang - Sun Microsystems - Beijing China 8559a5557fdSlucy wang - Sun Microsystems - Beijing China /* Should be called with adapter->tx_lock held. */ 8569a5557fdSlucy wang - Sun Microsystems - Beijing China static void 8579a5557fdSlucy wang - Sun Microsystems - Beijing China unm_return_dma_handle(unm_adapter *adapter, unm_dmah_node_t *head, 8589a5557fdSlucy wang - Sun Microsystems - Beijing China unm_dmah_node_t *tail, uint32_t num) 8599a5557fdSlucy wang - Sun Microsystems - Beijing China { 8609a5557fdSlucy wang - Sun Microsystems - Beijing China ASSERT(tail != NULL); 8619a5557fdSlucy wang - Sun Microsystems - Beijing China tail->next = adapter->dmahdl_pool; 8629a5557fdSlucy wang - Sun Microsystems - Beijing China adapter->dmahdl_pool = head; 8639a5557fdSlucy wang - Sun Microsystems - Beijing China adapter->freehdls += num; 8649a5557fdSlucy wang - Sun Microsystems - Beijing China } 8659a5557fdSlucy wang - Sun Microsystems - Beijing China 8669a5557fdSlucy wang - Sun Microsystems - Beijing China static unm_dmah_node_t * 8679a5557fdSlucy wang - Sun Microsystems - Beijing China unm_reserve_dma_handle(unm_adapter* adapter) 8689a5557fdSlucy wang - Sun Microsystems - Beijing China { 8699a5557fdSlucy wang - Sun Microsystems - Beijing China unm_dmah_node_t *dmah = NULL; 8709a5557fdSlucy wang - Sun Microsystems - Beijing China 8719a5557fdSlucy wang - Sun Microsystems - Beijing China dmah = adapter->dmahdl_pool; 8729a5557fdSlucy wang - Sun Microsystems - Beijing China if (dmah != NULL) { 8739a5557fdSlucy wang - Sun Microsystems - Beijing China adapter->dmahdl_pool = dmah->next; 8749a5557fdSlucy wang - Sun Microsystems - Beijing China dmah->next = NULL; 8759a5557fdSlucy wang - Sun Microsystems - Beijing China adapter->freehdls--; 8769a5557fdSlucy wang - Sun Microsystems - Beijing China membar_exit(); 8779a5557fdSlucy wang - Sun Microsystems - Beijing China } 8789a5557fdSlucy wang - Sun Microsystems - Beijing China 8799a5557fdSlucy wang - Sun Microsystems - Beijing China return (dmah); 8809a5557fdSlucy wang - Sun Microsystems - Beijing China } 8819a5557fdSlucy wang - Sun Microsystems - Beijing China 8829a5557fdSlucy wang - Sun Microsystems - Beijing China static boolean_t 8839a5557fdSlucy wang - Sun Microsystems - Beijing China unm_send_mapped(struct unm_adapter_s *adapter, mblk_t *mp, pktinfo_t *pktinfo) 8849a5557fdSlucy wang - Sun Microsystems - Beijing China { 8859a5557fdSlucy wang - Sun Microsystems - Beijing China hardware_context *hw; 8869a5557fdSlucy wang - Sun Microsystems - Beijing China u32 producer = 0; 8879a5557fdSlucy wang - Sun Microsystems - Beijing China u32 saved_producer = 0; 8889a5557fdSlucy wang - Sun Microsystems - Beijing China cmdDescType0_t *hwdesc; 8899a5557fdSlucy wang - Sun Microsystems - Beijing China struct unm_cmd_buffer *pbuf = NULL; 8909a5557fdSlucy wang - Sun Microsystems - Beijing China int no_of_desc; 8919a5557fdSlucy wang - Sun Microsystems - Beijing China int k; 8929a5557fdSlucy wang - Sun Microsystems - Beijing China int MaxTxDescCount; 8939a5557fdSlucy wang - Sun Microsystems - Beijing China mblk_t *bp; 8949a5557fdSlucy wang - Sun Microsystems - Beijing China 8959a5557fdSlucy wang - Sun Microsystems - Beijing China unm_dmah_node_t *dmah, *head = NULL, *tail = NULL, *hdlp; 8969a5557fdSlucy wang - Sun Microsystems - Beijing China ddi_dma_cookie_t cookie[MAX_COOKIES_PER_CMD + 1]; 8979a5557fdSlucy wang - Sun Microsystems - Beijing China int ret, i; 8989a5557fdSlucy wang - Sun Microsystems - Beijing China uint32_t hdl_reserved = 0; 8999a5557fdSlucy wang - Sun Microsystems - Beijing China uint32_t mblen; 9009a5557fdSlucy wang - Sun Microsystems - Beijing China uint32_t ncookies, index = 0, total_cookies = 0; 9019a5557fdSlucy wang - Sun Microsystems - Beijing China 9029a5557fdSlucy wang - Sun Microsystems - Beijing China MaxTxDescCount = adapter->MaxTxDescCount; 9039a5557fdSlucy wang - Sun Microsystems - Beijing China 9049a5557fdSlucy wang - Sun Microsystems - Beijing China UNM_SPIN_LOCK(&adapter->tx_lock); 9059a5557fdSlucy wang - Sun Microsystems - Beijing China 9069a5557fdSlucy wang - Sun Microsystems - Beijing China /* bind all the mblks of the packet first */ 9079a5557fdSlucy wang - Sun Microsystems - Beijing China for (bp = mp; bp != NULL; bp = bp->b_cont) { 9089a5557fdSlucy wang - Sun Microsystems - Beijing China mblen = MBLKL(bp); 9099a5557fdSlucy wang - Sun Microsystems - Beijing China if (mblen == 0) 9109a5557fdSlucy wang - Sun Microsystems - Beijing China continue; 9119a5557fdSlucy wang - Sun Microsystems - Beijing China 9129a5557fdSlucy wang - Sun Microsystems - Beijing China dmah = unm_reserve_dma_handle(adapter); 9139a5557fdSlucy wang - Sun Microsystems - Beijing China if (dmah == NULL) { 9149a5557fdSlucy wang - Sun Microsystems - Beijing China adapter->stats.outoftxdmahdl++; 9159a5557fdSlucy wang - Sun Microsystems - Beijing China goto err_map; 9169a5557fdSlucy wang - Sun Microsystems - Beijing China } 9179a5557fdSlucy wang - Sun Microsystems - Beijing China 9189a5557fdSlucy wang - Sun Microsystems - Beijing China ret = ddi_dma_addr_bind_handle(dmah->dmahdl, 9199a5557fdSlucy wang - Sun Microsystems - Beijing China NULL, (caddr_t)bp->b_rptr, mblen, 9209a5557fdSlucy wang - Sun Microsystems - Beijing China DDI_DMA_STREAMING | DDI_DMA_WRITE, 9219a5557fdSlucy wang - Sun Microsystems - Beijing China DDI_DMA_DONTWAIT, NULL, &cookie[index], &ncookies); 9229a5557fdSlucy wang - Sun Microsystems - Beijing China 9239a5557fdSlucy wang - Sun Microsystems - Beijing China if (ret != DDI_DMA_MAPPED) 9249a5557fdSlucy wang - Sun Microsystems - Beijing China goto err_map; 9259a5557fdSlucy wang - Sun Microsystems - Beijing China 9269a5557fdSlucy wang - Sun Microsystems - Beijing China if (tail == NULL) { 9279a5557fdSlucy wang - Sun Microsystems - Beijing China head = tail = dmah; 9289a5557fdSlucy wang - Sun Microsystems - Beijing China } else { 9299a5557fdSlucy wang - Sun Microsystems - Beijing China tail->next = dmah; 9309a5557fdSlucy wang - Sun Microsystems - Beijing China tail = dmah; 9319a5557fdSlucy wang - Sun Microsystems - Beijing China } 9329a5557fdSlucy wang - Sun Microsystems - Beijing China hdl_reserved++; 9339a5557fdSlucy wang - Sun Microsystems - Beijing China 9349a5557fdSlucy wang - Sun Microsystems - Beijing China total_cookies += ncookies; 9359a5557fdSlucy wang - Sun Microsystems - Beijing China if (total_cookies > MAX_COOKIES_PER_CMD) { 9369a5557fdSlucy wang - Sun Microsystems - Beijing China dmah = NULL; 9379a5557fdSlucy wang - Sun Microsystems - Beijing China goto err_map; 9389a5557fdSlucy wang - Sun Microsystems - Beijing China } 9399a5557fdSlucy wang - Sun Microsystems - Beijing China 9409a5557fdSlucy wang - Sun Microsystems - Beijing China if (index == 0) { 9419a5557fdSlucy wang - Sun Microsystems - Beijing China size_t hsize = cookie[0].dmac_size; 9429a5557fdSlucy wang - Sun Microsystems - Beijing China 9439a5557fdSlucy wang - Sun Microsystems - Beijing China /* 9449a5557fdSlucy wang - Sun Microsystems - Beijing China * For TCP/UDP packets with checksum offload, 9459a5557fdSlucy wang - Sun Microsystems - Beijing China * MAC/IP headers need to be contiguous. Otherwise, 9469a5557fdSlucy wang - Sun Microsystems - Beijing China * there must be at least 16 bytes in the first 9479a5557fdSlucy wang - Sun Microsystems - Beijing China * descriptor. 9489a5557fdSlucy wang - Sun Microsystems - Beijing China */ 9499a5557fdSlucy wang - Sun Microsystems - Beijing China if ((pktinfo->l4_proto == IPPROTO_TCP) || 9509a5557fdSlucy wang - Sun Microsystems - Beijing China (pktinfo->l4_proto == IPPROTO_UDP)) { 9519a5557fdSlucy wang - Sun Microsystems - Beijing China if (hsize < (pktinfo->mac_hlen + 9529a5557fdSlucy wang - Sun Microsystems - Beijing China pktinfo->ip_hlen)) { 9539a5557fdSlucy wang - Sun Microsystems - Beijing China dmah = NULL; 9549a5557fdSlucy wang - Sun Microsystems - Beijing China goto err_map; 9559a5557fdSlucy wang - Sun Microsystems - Beijing China } 9569a5557fdSlucy wang - Sun Microsystems - Beijing China } else { 9579a5557fdSlucy wang - Sun Microsystems - Beijing China if (hsize < 16) { 9589a5557fdSlucy wang - Sun Microsystems - Beijing China dmah = NULL; 9599a5557fdSlucy wang - Sun Microsystems - Beijing China goto err_map; 9609a5557fdSlucy wang - Sun Microsystems - Beijing China } 9619a5557fdSlucy wang - Sun Microsystems - Beijing China } 9629a5557fdSlucy wang - Sun Microsystems - Beijing China } 9639a5557fdSlucy wang - Sun Microsystems - Beijing China 9649a5557fdSlucy wang - Sun Microsystems - Beijing China index++; 9659a5557fdSlucy wang - Sun Microsystems - Beijing China ncookies--; 9669a5557fdSlucy wang - Sun Microsystems - Beijing China for (i = 0; i < ncookies; i++, index++) 9679a5557fdSlucy wang - Sun Microsystems - Beijing China ddi_dma_nextcookie(dmah->dmahdl, &cookie[index]); 9689a5557fdSlucy wang - Sun Microsystems - Beijing China } 9699a5557fdSlucy wang - Sun Microsystems - Beijing China 9709a5557fdSlucy wang - Sun Microsystems - Beijing China dmah = NULL; 9719a5557fdSlucy wang - Sun Microsystems - Beijing China hw = &adapter->ahw; 9729a5557fdSlucy wang - Sun Microsystems - Beijing China no_of_desc = (total_cookies + 3) >> 2; 9739a5557fdSlucy wang - Sun Microsystems - Beijing China 9749a5557fdSlucy wang - Sun Microsystems - Beijing China membar_enter(); 9759a5557fdSlucy wang - Sun Microsystems - Beijing China if (find_diff_among(adapter->cmdProducer, adapter->lastCmdConsumer, 9769a5557fdSlucy wang - Sun Microsystems - Beijing China MaxTxDescCount) < no_of_desc+2) { 9779a5557fdSlucy wang - Sun Microsystems - Beijing China /* 9789a5557fdSlucy wang - Sun Microsystems - Beijing China * If we are going to be trying the copy path, no point 9799a5557fdSlucy wang - Sun Microsystems - Beijing China * scheduling an upcall when Tx resources are freed. 9809a5557fdSlucy wang - Sun Microsystems - Beijing China */ 9819a5557fdSlucy wang - Sun Microsystems - Beijing China if (pktinfo->total_len > adapter->maxmtu) { 9829a5557fdSlucy wang - Sun Microsystems - Beijing China adapter->stats.outofcmddesc++; 9839a5557fdSlucy wang - Sun Microsystems - Beijing China adapter->resched_needed = 1; 9849a5557fdSlucy wang - Sun Microsystems - Beijing China } 9859a5557fdSlucy wang - Sun Microsystems - Beijing China membar_exit(); 9869a5557fdSlucy wang - Sun Microsystems - Beijing China goto err_alloc_desc; 9879a5557fdSlucy wang - Sun Microsystems - Beijing China } 9889a5557fdSlucy wang - Sun Microsystems - Beijing China adapter->freecmds -= no_of_desc; 9899a5557fdSlucy wang - Sun Microsystems - Beijing China 9909a5557fdSlucy wang - Sun Microsystems - Beijing China /* Copy the descriptors into the hardware */ 9919a5557fdSlucy wang - Sun Microsystems - Beijing China producer = adapter->cmdProducer; 9929a5557fdSlucy wang - Sun Microsystems - Beijing China saved_producer = producer; 9939a5557fdSlucy wang - Sun Microsystems - Beijing China hwdesc = &hw->cmdDescHead[producer]; 9949a5557fdSlucy wang - Sun Microsystems - Beijing China (void) memset(hwdesc, 0, sizeof (cmdDescType0_t)); 9959a5557fdSlucy wang - Sun Microsystems - Beijing China pbuf = &adapter->cmd_buf_arr[producer]; 9969a5557fdSlucy wang - Sun Microsystems - Beijing China 9979a5557fdSlucy wang - Sun Microsystems - Beijing China pbuf->msg = mp; 9989a5557fdSlucy wang - Sun Microsystems - Beijing China pbuf->head = head; 9999a5557fdSlucy wang - Sun Microsystems - Beijing China pbuf->tail = tail; 10009a5557fdSlucy wang - Sun Microsystems - Beijing China 10019a5557fdSlucy wang - Sun Microsystems - Beijing China hwdesc->u1.s1.numOfBuffers = total_cookies; 10029a5557fdSlucy wang - Sun Microsystems - Beijing China hwdesc->u1.s1.opcode = TX_ETHER_PKT; 10039a5557fdSlucy wang - Sun Microsystems - Beijing China hwdesc->u3.s1.port = adapter->portnum; 10049a5557fdSlucy wang - Sun Microsystems - Beijing China /* hwdesc->u1.s1.tcpHdrOffset = 0; */ 10059a5557fdSlucy wang - Sun Microsystems - Beijing China /* hwdesc->mss = 0; */ 10069a5557fdSlucy wang - Sun Microsystems - Beijing China hwdesc->u3.s1.ctx_id = adapter->portnum; 10079a5557fdSlucy wang - Sun Microsystems - Beijing China hwdesc->u1.s1.totalLength = pktinfo->total_len; 10089a5557fdSlucy wang - Sun Microsystems - Beijing China unm_tx_csum(hwdesc, mp, pktinfo); 10099a5557fdSlucy wang - Sun Microsystems - Beijing China 10109a5557fdSlucy wang - Sun Microsystems - Beijing China for (i = k = 0; i < total_cookies; i++) { 10119a5557fdSlucy wang - Sun Microsystems - Beijing China if (k == 4) { 10129a5557fdSlucy wang - Sun Microsystems - Beijing China /* Move to the next descriptor */ 10139a5557fdSlucy wang - Sun Microsystems - Beijing China k = 0; 10149a5557fdSlucy wang - Sun Microsystems - Beijing China producer = get_next_index(producer, MaxTxDescCount); 10159a5557fdSlucy wang - Sun Microsystems - Beijing China hwdesc = &hw->cmdDescHead[producer]; 10169a5557fdSlucy wang - Sun Microsystems - Beijing China (void) memset(hwdesc, 0, sizeof (cmdDescType0_t)); 10179a5557fdSlucy wang - Sun Microsystems - Beijing China } 10189a5557fdSlucy wang - Sun Microsystems - Beijing China 10199a5557fdSlucy wang - Sun Microsystems - Beijing China switch (k) { 10209a5557fdSlucy wang - Sun Microsystems - Beijing China case 0: 10219a5557fdSlucy wang - Sun Microsystems - Beijing China hwdesc->u6.s1.buffer1Length = cookie[i].dmac_size; 10229a5557fdSlucy wang - Sun Microsystems - Beijing China hwdesc->u5.AddrBuffer1 = cookie[i].dmac_laddress; 10239a5557fdSlucy wang - Sun Microsystems - Beijing China break; 10249a5557fdSlucy wang - Sun Microsystems - Beijing China case 1: 10259a5557fdSlucy wang - Sun Microsystems - Beijing China hwdesc->u6.s1.buffer2Length = cookie[i].dmac_size; 10269a5557fdSlucy wang - Sun Microsystems - Beijing China hwdesc->u2.AddrBuffer2 = cookie[i].dmac_laddress; 10279a5557fdSlucy wang - Sun Microsystems - Beijing China break; 10289a5557fdSlucy wang - Sun Microsystems - Beijing China case 2: 10299a5557fdSlucy wang - Sun Microsystems - Beijing China hwdesc->u6.s1.buffer3Length = cookie[i].dmac_size; 10309a5557fdSlucy wang - Sun Microsystems - Beijing China hwdesc->u4.AddrBuffer3 = cookie[i].dmac_laddress; 10319a5557fdSlucy wang - Sun Microsystems - Beijing China break; 10329a5557fdSlucy wang - Sun Microsystems - Beijing China case 3: 10339a5557fdSlucy wang - Sun Microsystems - Beijing China hwdesc->u6.s1.buffer4Length = cookie[i].dmac_size; 10349a5557fdSlucy wang - Sun Microsystems - Beijing China hwdesc->u7.AddrBuffer4 = cookie[i].dmac_laddress; 10359a5557fdSlucy wang - Sun Microsystems - Beijing China break; 10369a5557fdSlucy wang - Sun Microsystems - Beijing China } 10379a5557fdSlucy wang - Sun Microsystems - Beijing China k++; 10389a5557fdSlucy wang - Sun Microsystems - Beijing China } 10399a5557fdSlucy wang - Sun Microsystems - Beijing China 10409a5557fdSlucy wang - Sun Microsystems - Beijing China unm_desc_dma_sync(hw->cmd_desc_dma_handle, saved_producer, no_of_desc, 10419a5557fdSlucy wang - Sun Microsystems - Beijing China MaxTxDescCount, sizeof (cmdDescType0_t), DDI_DMA_SYNC_FORDEV); 10429a5557fdSlucy wang - Sun Microsystems - Beijing China 10439a5557fdSlucy wang - Sun Microsystems - Beijing China adapter->cmdProducer = get_next_index(producer, MaxTxDescCount); 10449a5557fdSlucy wang - Sun Microsystems - Beijing China hw->cmdProducer = adapter->cmdProducer; 10459a5557fdSlucy wang - Sun Microsystems - Beijing China unm_nic_update_cmd_producer(adapter, adapter->cmdProducer); 10469a5557fdSlucy wang - Sun Microsystems - Beijing China 10479a5557fdSlucy wang - Sun Microsystems - Beijing China adapter->stats.txbytes += pktinfo->total_len; 10489a5557fdSlucy wang - Sun Microsystems - Beijing China adapter->stats.xmitfinished++; 10499a5557fdSlucy wang - Sun Microsystems - Beijing China adapter->stats.txmapped++; 10509a5557fdSlucy wang - Sun Microsystems - Beijing China UNM_SPIN_UNLOCK(&adapter->tx_lock); 10519a5557fdSlucy wang - Sun Microsystems - Beijing China return (B_TRUE); 10529a5557fdSlucy wang - Sun Microsystems - Beijing China 10539a5557fdSlucy wang - Sun Microsystems - Beijing China err_alloc_desc: 10549a5557fdSlucy wang - Sun Microsystems - Beijing China err_map: 10559a5557fdSlucy wang - Sun Microsystems - Beijing China 10569a5557fdSlucy wang - Sun Microsystems - Beijing China hdlp = head; 10579a5557fdSlucy wang - Sun Microsystems - Beijing China while (hdlp != NULL) { 10589a5557fdSlucy wang - Sun Microsystems - Beijing China (void) ddi_dma_unbind_handle(hdlp->dmahdl); 10599a5557fdSlucy wang - Sun Microsystems - Beijing China hdlp = hdlp->next; 10609a5557fdSlucy wang - Sun Microsystems - Beijing China } 10619a5557fdSlucy wang - Sun Microsystems - Beijing China 10629a5557fdSlucy wang - Sun Microsystems - Beijing China /* 10639a5557fdSlucy wang - Sun Microsystems - Beijing China * add the reserved but bind failed one to the list to be returned 10649a5557fdSlucy wang - Sun Microsystems - Beijing China */ 10659a5557fdSlucy wang - Sun Microsystems - Beijing China if (dmah != NULL) { 10669a5557fdSlucy wang - Sun Microsystems - Beijing China if (tail == NULL) 10679a5557fdSlucy wang - Sun Microsystems - Beijing China head = tail = dmah; 10689a5557fdSlucy wang - Sun Microsystems - Beijing China else { 10699a5557fdSlucy wang - Sun Microsystems - Beijing China tail->next = dmah; 10709a5557fdSlucy wang - Sun Microsystems - Beijing China tail = dmah; 10719a5557fdSlucy wang - Sun Microsystems - Beijing China } 10729a5557fdSlucy wang - Sun Microsystems - Beijing China hdl_reserved++; 10739a5557fdSlucy wang - Sun Microsystems - Beijing China } 10749a5557fdSlucy wang - Sun Microsystems - Beijing China 10759a5557fdSlucy wang - Sun Microsystems - Beijing China if (head != NULL) 10769a5557fdSlucy wang - Sun Microsystems - Beijing China unm_return_dma_handle(adapter, head, tail, hdl_reserved); 10779a5557fdSlucy wang - Sun Microsystems - Beijing China 10789a5557fdSlucy wang - Sun Microsystems - Beijing China UNM_SPIN_UNLOCK(&adapter->tx_lock); 10799a5557fdSlucy wang - Sun Microsystems - Beijing China return (B_FALSE); 10809a5557fdSlucy wang - Sun Microsystems - Beijing China } 10819a5557fdSlucy wang - Sun Microsystems - Beijing China 10829a5557fdSlucy wang - Sun Microsystems - Beijing China static boolean_t 10839a5557fdSlucy wang - Sun Microsystems - Beijing China unm_nic_xmit_frame(unm_adapter *adapter, mblk_t *mp) 10849a5557fdSlucy wang - Sun Microsystems - Beijing China { 10859a5557fdSlucy wang - Sun Microsystems - Beijing China pktinfo_t pktinfo; 10869a5557fdSlucy wang - Sun Microsystems - Beijing China boolean_t status = B_FALSE, send_mapped; 10879a5557fdSlucy wang - Sun Microsystems - Beijing China 10889a5557fdSlucy wang - Sun Microsystems - Beijing China adapter->stats.xmitcalled++; 10899a5557fdSlucy wang - Sun Microsystems - Beijing China 10909a5557fdSlucy wang - Sun Microsystems - Beijing China send_mapped = unm_get_pkt_info(mp, &pktinfo); 10919a5557fdSlucy wang - Sun Microsystems - Beijing China 10929a5557fdSlucy wang - Sun Microsystems - Beijing China if (pktinfo.total_len <= adapter->tx_bcopy_threshold || 1093dda0720aSjing xiong ERI-SUN pktinfo.mblk_no >= MAX_COOKIES_PER_CMD) 10949a5557fdSlucy wang - Sun Microsystems - Beijing China send_mapped = B_FALSE; 10959a5557fdSlucy wang - Sun Microsystems - Beijing China 10969a5557fdSlucy wang - Sun Microsystems - Beijing China if (send_mapped == B_TRUE) 10979a5557fdSlucy wang - Sun Microsystems - Beijing China status = unm_send_mapped(adapter, mp, &pktinfo); 10989a5557fdSlucy wang - Sun Microsystems - Beijing China 10999a5557fdSlucy wang - Sun Microsystems - Beijing China if (status != B_TRUE) { 11009a5557fdSlucy wang - Sun Microsystems - Beijing China if (pktinfo.total_len <= adapter->maxmtu) 11019a5557fdSlucy wang - Sun Microsystems - Beijing China return (unm_send_copy(adapter, mp, &pktinfo)); 11029a5557fdSlucy wang - Sun Microsystems - Beijing China 11039a5557fdSlucy wang - Sun Microsystems - Beijing China /* message too large */ 11049a5557fdSlucy wang - Sun Microsystems - Beijing China freemsg(mp); 11059a5557fdSlucy wang - Sun Microsystems - Beijing China adapter->stats.txdropped++; 11069a5557fdSlucy wang - Sun Microsystems - Beijing China status = B_TRUE; 11079a5557fdSlucy wang - Sun Microsystems - Beijing China } 11089a5557fdSlucy wang - Sun Microsystems - Beijing China 11099a5557fdSlucy wang - Sun Microsystems - Beijing China return (status); 11109a5557fdSlucy wang - Sun Microsystems - Beijing China } 11119a5557fdSlucy wang - Sun Microsystems - Beijing China 11129a5557fdSlucy wang - Sun Microsystems - Beijing China static int 11139a5557fdSlucy wang - Sun Microsystems - Beijing China unm_nic_check_temp(struct unm_adapter_s *adapter) 11149a5557fdSlucy wang - Sun Microsystems - Beijing China { 11159a5557fdSlucy wang - Sun Microsystems - Beijing China uint32_t temp, temp_state, temp_val; 11169a5557fdSlucy wang - Sun Microsystems - Beijing China int rv = 0; 11179a5557fdSlucy wang - Sun Microsystems - Beijing China 11189a5557fdSlucy wang - Sun Microsystems - Beijing China if ((adapter->ahw.revision_id == NX_P3_A2) || 11199a5557fdSlucy wang - Sun Microsystems - Beijing China (adapter->ahw.revision_id == NX_P3_A0)) 11209a5557fdSlucy wang - Sun Microsystems - Beijing China return (0); 11219a5557fdSlucy wang - Sun Microsystems - Beijing China 11229a5557fdSlucy wang - Sun Microsystems - Beijing China temp = adapter->unm_nic_pci_read_normalize(adapter, CRB_TEMP_STATE); 11239a5557fdSlucy wang - Sun Microsystems - Beijing China 11249a5557fdSlucy wang - Sun Microsystems - Beijing China temp_state = nx_get_temp_state(temp); 11259a5557fdSlucy wang - Sun Microsystems - Beijing China temp_val = nx_get_temp_val(temp); 11269a5557fdSlucy wang - Sun Microsystems - Beijing China 11279a5557fdSlucy wang - Sun Microsystems - Beijing China if (temp_state == NX_TEMP_PANIC) { 11289a5557fdSlucy wang - Sun Microsystems - Beijing China cmn_err(CE_WARN, "%s: Device temperature %d C exceeds " 11299a5557fdSlucy wang - Sun Microsystems - Beijing China "maximum allowed, device has been shut down\n", 11309a5557fdSlucy wang - Sun Microsystems - Beijing China unm_nic_driver_name, temp_val); 11319a5557fdSlucy wang - Sun Microsystems - Beijing China rv = 1; 11329a5557fdSlucy wang - Sun Microsystems - Beijing China } else if (temp_state == NX_TEMP_WARN) { 11339a5557fdSlucy wang - Sun Microsystems - Beijing China if (adapter->temp == NX_TEMP_NORMAL) { 11349a5557fdSlucy wang - Sun Microsystems - Beijing China cmn_err(CE_WARN, "%s: Device temperature %d C exceeds" 11359a5557fdSlucy wang - Sun Microsystems - Beijing China "operating range. Immediate action needed.\n", 11369a5557fdSlucy wang - Sun Microsystems - Beijing China unm_nic_driver_name, temp_val); 11379a5557fdSlucy wang - Sun Microsystems - Beijing China } 11389a5557fdSlucy wang - Sun Microsystems - Beijing China } else { 11399a5557fdSlucy wang - Sun Microsystems - Beijing China if (adapter->temp == NX_TEMP_WARN) { 11409a5557fdSlucy wang - Sun Microsystems - Beijing China cmn_err(CE_WARN, "%s: Device temperature is now %d " 11419a5557fdSlucy wang - Sun Microsystems - Beijing China "degrees C in normal range.\n", 11429a5557fdSlucy wang - Sun Microsystems - Beijing China unm_nic_driver_name, temp_val); 11439a5557fdSlucy wang - Sun Microsystems - Beijing China } 11449a5557fdSlucy wang - Sun Microsystems - Beijing China } 11459a5557fdSlucy wang - Sun Microsystems - Beijing China 11469a5557fdSlucy wang - Sun Microsystems - Beijing China adapter->temp = temp_state; 11479a5557fdSlucy wang - Sun Microsystems - Beijing China return (rv); 11489a5557fdSlucy wang - Sun Microsystems - Beijing China } 11499a5557fdSlucy wang - Sun Microsystems - Beijing China 11509a5557fdSlucy wang - Sun Microsystems - Beijing China static void 11519a5557fdSlucy wang - Sun Microsystems - Beijing China unm_watchdog(unsigned long v) 11529a5557fdSlucy wang - Sun Microsystems - Beijing China { 11539a5557fdSlucy wang - Sun Microsystems - Beijing China unm_adapter *adapter = (unm_adapter *)v; 11549a5557fdSlucy wang - Sun Microsystems - Beijing China 11559a5557fdSlucy wang - Sun Microsystems - Beijing China if ((adapter->portnum == 0) && unm_nic_check_temp(adapter)) { 11569a5557fdSlucy wang - Sun Microsystems - Beijing China /* 11579a5557fdSlucy wang - Sun Microsystems - Beijing China * We return without turning on the netdev queue as there 11589a5557fdSlucy wang - Sun Microsystems - Beijing China * was an overheated device 11599a5557fdSlucy wang - Sun Microsystems - Beijing China */ 11609a5557fdSlucy wang - Sun Microsystems - Beijing China return; 11619a5557fdSlucy wang - Sun Microsystems - Beijing China } 11629a5557fdSlucy wang - Sun Microsystems - Beijing China 11639a5557fdSlucy wang - Sun Microsystems - Beijing China unm_nic_handle_phy_intr(adapter); 11649a5557fdSlucy wang - Sun Microsystems - Beijing China 11659a5557fdSlucy wang - Sun Microsystems - Beijing China /* 11669a5557fdSlucy wang - Sun Microsystems - Beijing China * This function schedules a call for itself. 11679a5557fdSlucy wang - Sun Microsystems - Beijing China */ 11689a5557fdSlucy wang - Sun Microsystems - Beijing China adapter->watchdog_timer = timeout((void (*)(void *))&unm_watchdog, 11699a5557fdSlucy wang - Sun Microsystems - Beijing China (void *)adapter, 2 * drv_usectohz(1000000)); 11709a5557fdSlucy wang - Sun Microsystems - Beijing China 11719a5557fdSlucy wang - Sun Microsystems - Beijing China } 11729a5557fdSlucy wang - Sun Microsystems - Beijing China 11739a5557fdSlucy wang - Sun Microsystems - Beijing China static void unm_nic_clear_stats(unm_adapter *adapter) 11749a5557fdSlucy wang - Sun Microsystems - Beijing China { 11759a5557fdSlucy wang - Sun Microsystems - Beijing China (void) memset(&adapter->stats, 0, sizeof (adapter->stats)); 11769a5557fdSlucy wang - Sun Microsystems - Beijing China } 11779a5557fdSlucy wang - Sun Microsystems - Beijing China 11789a5557fdSlucy wang - Sun Microsystems - Beijing China static void 11799a5557fdSlucy wang - Sun Microsystems - Beijing China unm_nic_poll(unm_adapter *adapter) 11809a5557fdSlucy wang - Sun Microsystems - Beijing China { 11819a5557fdSlucy wang - Sun Microsystems - Beijing China int work_done, tx_complete; 11829a5557fdSlucy wang - Sun Microsystems - Beijing China 11839a5557fdSlucy wang - Sun Microsystems - Beijing China adapter->stats.polled++; 11849a5557fdSlucy wang - Sun Microsystems - Beijing China 11859a5557fdSlucy wang - Sun Microsystems - Beijing China loop: 11869a5557fdSlucy wang - Sun Microsystems - Beijing China tx_complete = unm_process_cmd_ring(adapter); 11879a5557fdSlucy wang - Sun Microsystems - Beijing China work_done = unm_process_rcv_ring(adapter, NX_RX_MAXBUFS); 11889a5557fdSlucy wang - Sun Microsystems - Beijing China if ((!tx_complete) || (!(work_done < NX_RX_MAXBUFS))) 11899a5557fdSlucy wang - Sun Microsystems - Beijing China goto loop; 11909a5557fdSlucy wang - Sun Microsystems - Beijing China 11919a5557fdSlucy wang - Sun Microsystems - Beijing China UNM_READ_LOCK(&adapter->adapter_lock); 11929a5557fdSlucy wang - Sun Microsystems - Beijing China unm_nic_enable_int(adapter); 11939a5557fdSlucy wang - Sun Microsystems - Beijing China UNM_READ_UNLOCK(&adapter->adapter_lock); 11949a5557fdSlucy wang - Sun Microsystems - Beijing China } 11959a5557fdSlucy wang - Sun Microsystems - Beijing China 11969a5557fdSlucy wang - Sun Microsystems - Beijing China /* ARGSUSED */ 11979a5557fdSlucy wang - Sun Microsystems - Beijing China uint_t 11989a5557fdSlucy wang - Sun Microsystems - Beijing China unm_intr(caddr_t data, caddr_t arg) 11999a5557fdSlucy wang - Sun Microsystems - Beijing China { 12009a5557fdSlucy wang - Sun Microsystems - Beijing China unm_adapter *adapter = (unm_adapter *)(uintptr_t)data; 12019a5557fdSlucy wang - Sun Microsystems - Beijing China 12029a5557fdSlucy wang - Sun Microsystems - Beijing China if (unm_nic_clear_int(adapter)) 12039a5557fdSlucy wang - Sun Microsystems - Beijing China return (DDI_INTR_UNCLAIMED); 12049a5557fdSlucy wang - Sun Microsystems - Beijing China 12059a5557fdSlucy wang - Sun Microsystems - Beijing China unm_nic_poll(adapter); 12069a5557fdSlucy wang - Sun Microsystems - Beijing China return (DDI_INTR_CLAIMED); 12079a5557fdSlucy wang - Sun Microsystems - Beijing China } 12089a5557fdSlucy wang - Sun Microsystems - Beijing China 12099a5557fdSlucy wang - Sun Microsystems - Beijing China /* 12109a5557fdSlucy wang - Sun Microsystems - Beijing China * This is invoked from receive isr. Due to the single threaded nature 12119a5557fdSlucy wang - Sun Microsystems - Beijing China * of the invocation, pool_lock acquisition is not neccesary to protect 12129a5557fdSlucy wang - Sun Microsystems - Beijing China * pool_list. 12139a5557fdSlucy wang - Sun Microsystems - Beijing China */ 12149a5557fdSlucy wang - Sun Microsystems - Beijing China static void 12159a5557fdSlucy wang - Sun Microsystems - Beijing China unm_free_rx_buffer(unm_rcv_desc_ctx_t *rcv_desc, unm_rx_buffer_t *rx_buffer) 12169a5557fdSlucy wang - Sun Microsystems - Beijing China { 12179a5557fdSlucy wang - Sun Microsystems - Beijing China /* mutex_enter(rcv_desc->pool_lock); */ 12189a5557fdSlucy wang - Sun Microsystems - Beijing China rx_buffer->next = rcv_desc->pool_list; 12199a5557fdSlucy wang - Sun Microsystems - Beijing China rcv_desc->pool_list = rx_buffer; 12209a5557fdSlucy wang - Sun Microsystems - Beijing China rcv_desc->rx_buf_free++; 12219a5557fdSlucy wang - Sun Microsystems - Beijing China /* mutex_exit(rcv_desc->pool_lock); */ 12229a5557fdSlucy wang - Sun Microsystems - Beijing China } 12239a5557fdSlucy wang - Sun Microsystems - Beijing China 12249a5557fdSlucy wang - Sun Microsystems - Beijing China /* 12259a5557fdSlucy wang - Sun Microsystems - Beijing China * unm_process_rcv() send the received packet to the protocol stack. 12269a5557fdSlucy wang - Sun Microsystems - Beijing China */ 12279a5557fdSlucy wang - Sun Microsystems - Beijing China static mblk_t * 12289a5557fdSlucy wang - Sun Microsystems - Beijing China unm_process_rcv(unm_adapter *adapter, statusDesc_t *desc) 12299a5557fdSlucy wang - Sun Microsystems - Beijing China { 12309a5557fdSlucy wang - Sun Microsystems - Beijing China unm_recv_context_t *recv_ctx = &(adapter->recv_ctx[0]); 12319a5557fdSlucy wang - Sun Microsystems - Beijing China unm_rx_buffer_t *rx_buffer; 12329a5557fdSlucy wang - Sun Microsystems - Beijing China mblk_t *mp; 12339a5557fdSlucy wang - Sun Microsystems - Beijing China u32 desc_ctx = desc->u1.s1.type; 12349a5557fdSlucy wang - Sun Microsystems - Beijing China unm_rcv_desc_ctx_t *rcv_desc = &recv_ctx->rcv_desc[desc_ctx]; 12359a5557fdSlucy wang - Sun Microsystems - Beijing China u32 pkt_length = desc->u1.s1.totalLength; 12369a5557fdSlucy wang - Sun Microsystems - Beijing China int poff = desc->u1.s1.pkt_offset; 12379a5557fdSlucy wang - Sun Microsystems - Beijing China int index, cksum_flags, docopy; 12389a5557fdSlucy wang - Sun Microsystems - Beijing China int index_lo = desc->u1.s1.referenceHandle_lo; 12399a5557fdSlucy wang - Sun Microsystems - Beijing China char *vaddr; 12409a5557fdSlucy wang - Sun Microsystems - Beijing China 12419a5557fdSlucy wang - Sun Microsystems - Beijing China index = ((desc->u1.s1.referenceHandle_hi << 4) | index_lo); 12429a5557fdSlucy wang - Sun Microsystems - Beijing China 12439a5557fdSlucy wang - Sun Microsystems - Beijing China rx_buffer = index2rxbuf(rcv_desc, index); 12449a5557fdSlucy wang - Sun Microsystems - Beijing China 12459a5557fdSlucy wang - Sun Microsystems - Beijing China if (rx_buffer == NULL) { 12469a5557fdSlucy wang - Sun Microsystems - Beijing China cmn_err(CE_WARN, "\r\nNULL rx_buffer idx=%d", index); 12479a5557fdSlucy wang - Sun Microsystems - Beijing China return (NULL); 12489a5557fdSlucy wang - Sun Microsystems - Beijing China } 12499a5557fdSlucy wang - Sun Microsystems - Beijing China vaddr = (char *)rx_buffer->dma_info.vaddr; 12509a5557fdSlucy wang - Sun Microsystems - Beijing China if (vaddr == NULL) { 12519a5557fdSlucy wang - Sun Microsystems - Beijing China cmn_err(CE_WARN, "\r\nNULL vaddr"); 12529a5557fdSlucy wang - Sun Microsystems - Beijing China return (NULL); 12539a5557fdSlucy wang - Sun Microsystems - Beijing China } 12549a5557fdSlucy wang - Sun Microsystems - Beijing China rcv_desc->rx_desc_handled++; 12559a5557fdSlucy wang - Sun Microsystems - Beijing China rcv_desc->rx_buf_card--; 12569a5557fdSlucy wang - Sun Microsystems - Beijing China 12579a5557fdSlucy wang - Sun Microsystems - Beijing China (void) ddi_dma_sync(rx_buffer->dma_info.dma_hdl, 0, 12589a5557fdSlucy wang - Sun Microsystems - Beijing China pkt_length + poff + (adapter->ahw.cut_through ? 0 : 12599a5557fdSlucy wang - Sun Microsystems - Beijing China IP_ALIGNMENT_BYTES), DDI_DMA_SYNC_FORCPU); 12609a5557fdSlucy wang - Sun Microsystems - Beijing China 12619a5557fdSlucy wang - Sun Microsystems - Beijing China /* 12629a5557fdSlucy wang - Sun Microsystems - Beijing China * Copy packet into new allocated message buffer, if pkt_length 12639a5557fdSlucy wang - Sun Microsystems - Beijing China * is below copy threshold. 12649a5557fdSlucy wang - Sun Microsystems - Beijing China */ 12659a5557fdSlucy wang - Sun Microsystems - Beijing China docopy = (pkt_length <= adapter->rx_bcopy_threshold) ? 1 : 0; 12669a5557fdSlucy wang - Sun Microsystems - Beijing China 12679a5557fdSlucy wang - Sun Microsystems - Beijing China /* 12689a5557fdSlucy wang - Sun Microsystems - Beijing China * If card is running out of rx buffers, then attempt to allocate 12699a5557fdSlucy wang - Sun Microsystems - Beijing China * new mblk so we can feed this rx buffer back to card (we 12709a5557fdSlucy wang - Sun Microsystems - Beijing China * _could_ look at what's pending on free and recycle lists). 12719a5557fdSlucy wang - Sun Microsystems - Beijing China */ 12729a5557fdSlucy wang - Sun Microsystems - Beijing China if (rcv_desc->rx_buf_card < NX_RX_THRESHOLD) { 12739a5557fdSlucy wang - Sun Microsystems - Beijing China docopy = 1; 12749a5557fdSlucy wang - Sun Microsystems - Beijing China adapter->stats.rxbufshort++; 12759a5557fdSlucy wang - Sun Microsystems - Beijing China } 12769a5557fdSlucy wang - Sun Microsystems - Beijing China 12779a5557fdSlucy wang - Sun Microsystems - Beijing China if (docopy == 1) { 12789a5557fdSlucy wang - Sun Microsystems - Beijing China if ((mp = allocb(pkt_length + IP_ALIGNMENT_BYTES, 0)) == NULL) { 12799a5557fdSlucy wang - Sun Microsystems - Beijing China adapter->stats.allocbfailed++; 12809a5557fdSlucy wang - Sun Microsystems - Beijing China goto freebuf; 12819a5557fdSlucy wang - Sun Microsystems - Beijing China } 12829a5557fdSlucy wang - Sun Microsystems - Beijing China 12839a5557fdSlucy wang - Sun Microsystems - Beijing China mp->b_rptr += IP_ALIGNMENT_BYTES; 12849a5557fdSlucy wang - Sun Microsystems - Beijing China vaddr += poff; 12859a5557fdSlucy wang - Sun Microsystems - Beijing China bcopy(vaddr, mp->b_rptr, pkt_length); 12869a5557fdSlucy wang - Sun Microsystems - Beijing China adapter->stats.rxcopyed++; 12879a5557fdSlucy wang - Sun Microsystems - Beijing China unm_free_rx_buffer(rcv_desc, rx_buffer); 12889a5557fdSlucy wang - Sun Microsystems - Beijing China } else { 12899a5557fdSlucy wang - Sun Microsystems - Beijing China mp = (mblk_t *)rx_buffer->mp; 12909a5557fdSlucy wang - Sun Microsystems - Beijing China if (mp == NULL) { 12919a5557fdSlucy wang - Sun Microsystems - Beijing China mp = desballoc(rx_buffer->dma_info.vaddr, 12929a5557fdSlucy wang - Sun Microsystems - Beijing China rcv_desc->dma_size, 0, &rx_buffer->rx_recycle); 12939a5557fdSlucy wang - Sun Microsystems - Beijing China if (mp == NULL) { 12949a5557fdSlucy wang - Sun Microsystems - Beijing China adapter->stats.desballocfailed++; 12959a5557fdSlucy wang - Sun Microsystems - Beijing China goto freebuf; 12969a5557fdSlucy wang - Sun Microsystems - Beijing China } 12979a5557fdSlucy wang - Sun Microsystems - Beijing China rx_buffer->mp = mp; 12989a5557fdSlucy wang - Sun Microsystems - Beijing China } 12999a5557fdSlucy wang - Sun Microsystems - Beijing China mp->b_rptr += poff; 13009a5557fdSlucy wang - Sun Microsystems - Beijing China adapter->stats.rxmapped++; 13019a5557fdSlucy wang - Sun Microsystems - Beijing China } 13029a5557fdSlucy wang - Sun Microsystems - Beijing China 13039a5557fdSlucy wang - Sun Microsystems - Beijing China mp->b_wptr = (uchar_t *)((unsigned long)mp->b_rptr + pkt_length); 13049a5557fdSlucy wang - Sun Microsystems - Beijing China 13059a5557fdSlucy wang - Sun Microsystems - Beijing China if (desc->u1.s1.status == STATUS_CKSUM_OK) { 13069a5557fdSlucy wang - Sun Microsystems - Beijing China adapter->stats.csummed++; 13079a5557fdSlucy wang - Sun Microsystems - Beijing China cksum_flags = 1308*0dc2366fSVenugopal Iyer HCK_FULLCKSUM_OK | HCK_IPV4_HDRCKSUM_OK; 13099a5557fdSlucy wang - Sun Microsystems - Beijing China } else { 13109a5557fdSlucy wang - Sun Microsystems - Beijing China cksum_flags = 0; 13119a5557fdSlucy wang - Sun Microsystems - Beijing China } 1312*0dc2366fSVenugopal Iyer mac_hcksum_set(mp, 0, 0, 0, 0, cksum_flags); 13139a5557fdSlucy wang - Sun Microsystems - Beijing China 13149a5557fdSlucy wang - Sun Microsystems - Beijing China adapter->stats.no_rcv++; 13159a5557fdSlucy wang - Sun Microsystems - Beijing China adapter->stats.rxbytes += pkt_length; 13169a5557fdSlucy wang - Sun Microsystems - Beijing China adapter->stats.uphappy++; 13179a5557fdSlucy wang - Sun Microsystems - Beijing China 13189a5557fdSlucy wang - Sun Microsystems - Beijing China return (mp); 13199a5557fdSlucy wang - Sun Microsystems - Beijing China 13209a5557fdSlucy wang - Sun Microsystems - Beijing China freebuf: 13219a5557fdSlucy wang - Sun Microsystems - Beijing China unm_free_rx_buffer(rcv_desc, rx_buffer); 13229a5557fdSlucy wang - Sun Microsystems - Beijing China return (NULL); 13239a5557fdSlucy wang - Sun Microsystems - Beijing China } 13249a5557fdSlucy wang - Sun Microsystems - Beijing China 13259a5557fdSlucy wang - Sun Microsystems - Beijing China /* Process Receive status ring */ 13269a5557fdSlucy wang - Sun Microsystems - Beijing China static int 13279a5557fdSlucy wang - Sun Microsystems - Beijing China unm_process_rcv_ring(unm_adapter *adapter, int max) 13289a5557fdSlucy wang - Sun Microsystems - Beijing China { 13299a5557fdSlucy wang - Sun Microsystems - Beijing China unm_recv_context_t *recv_ctx = &(adapter->recv_ctx[0]); 13309a5557fdSlucy wang - Sun Microsystems - Beijing China statusDesc_t *desc_head = recv_ctx->rcvStatusDescHead; 13319a5557fdSlucy wang - Sun Microsystems - Beijing China statusDesc_t *desc = NULL; 13329a5557fdSlucy wang - Sun Microsystems - Beijing China uint32_t consumer, start; 13339a5557fdSlucy wang - Sun Microsystems - Beijing China int count = 0, ring; 13349a5557fdSlucy wang - Sun Microsystems - Beijing China mblk_t *mp; 13359a5557fdSlucy wang - Sun Microsystems - Beijing China 13369a5557fdSlucy wang - Sun Microsystems - Beijing China start = consumer = recv_ctx->statusRxConsumer; 13379a5557fdSlucy wang - Sun Microsystems - Beijing China 13389a5557fdSlucy wang - Sun Microsystems - Beijing China unm_desc_dma_sync(recv_ctx->status_desc_dma_handle, start, max, 13399a5557fdSlucy wang - Sun Microsystems - Beijing China adapter->MaxRxDescCount, sizeof (statusDesc_t), 13409a5557fdSlucy wang - Sun Microsystems - Beijing China DDI_DMA_SYNC_FORCPU); 13419a5557fdSlucy wang - Sun Microsystems - Beijing China 13429a5557fdSlucy wang - Sun Microsystems - Beijing China while (count < max) { 13439a5557fdSlucy wang - Sun Microsystems - Beijing China desc = &desc_head[consumer]; 13449a5557fdSlucy wang - Sun Microsystems - Beijing China if (!(desc->u1.s1.owner & STATUS_OWNER_HOST)) 13459a5557fdSlucy wang - Sun Microsystems - Beijing China break; 13469a5557fdSlucy wang - Sun Microsystems - Beijing China 13479a5557fdSlucy wang - Sun Microsystems - Beijing China mp = unm_process_rcv(adapter, desc); 13489a5557fdSlucy wang - Sun Microsystems - Beijing China desc->u1.s1.owner = STATUS_OWNER_PHANTOM; 13499a5557fdSlucy wang - Sun Microsystems - Beijing China 13509a5557fdSlucy wang - Sun Microsystems - Beijing China consumer = (consumer + 1) % adapter->MaxRxDescCount; 13519a5557fdSlucy wang - Sun Microsystems - Beijing China count++; 13529a5557fdSlucy wang - Sun Microsystems - Beijing China if (mp != NULL) 13539a5557fdSlucy wang - Sun Microsystems - Beijing China mac_rx(adapter->mach, NULL, mp); 13549a5557fdSlucy wang - Sun Microsystems - Beijing China } 13559a5557fdSlucy wang - Sun Microsystems - Beijing China 13569a5557fdSlucy wang - Sun Microsystems - Beijing China for (ring = 0; ring < adapter->max_rds_rings; ring++) { 13579a5557fdSlucy wang - Sun Microsystems - Beijing China if (recv_ctx->rcv_desc[ring].rx_desc_handled > 0) 13589a5557fdSlucy wang - Sun Microsystems - Beijing China unm_post_rx_buffers_nodb(adapter, ring); 13599a5557fdSlucy wang - Sun Microsystems - Beijing China } 13609a5557fdSlucy wang - Sun Microsystems - Beijing China 13619a5557fdSlucy wang - Sun Microsystems - Beijing China if (count) { 13629a5557fdSlucy wang - Sun Microsystems - Beijing China unm_desc_dma_sync(recv_ctx->status_desc_dma_handle, start, 13639a5557fdSlucy wang - Sun Microsystems - Beijing China count, adapter->MaxRxDescCount, sizeof (statusDesc_t), 13649a5557fdSlucy wang - Sun Microsystems - Beijing China DDI_DMA_SYNC_FORDEV); 13659a5557fdSlucy wang - Sun Microsystems - Beijing China 13669a5557fdSlucy wang - Sun Microsystems - Beijing China /* update the consumer index in phantom */ 13679a5557fdSlucy wang - Sun Microsystems - Beijing China recv_ctx->statusRxConsumer = consumer; 13689a5557fdSlucy wang - Sun Microsystems - Beijing China 13699a5557fdSlucy wang - Sun Microsystems - Beijing China UNM_READ_LOCK(&adapter->adapter_lock); 13709a5557fdSlucy wang - Sun Microsystems - Beijing China adapter->unm_nic_hw_write_wx(adapter, 13719a5557fdSlucy wang - Sun Microsystems - Beijing China recv_ctx->host_sds_consumer, &consumer, 4); 13729a5557fdSlucy wang - Sun Microsystems - Beijing China UNM_READ_UNLOCK(&adapter->adapter_lock); 13739a5557fdSlucy wang - Sun Microsystems - Beijing China } 13749a5557fdSlucy wang - Sun Microsystems - Beijing China 13759a5557fdSlucy wang - Sun Microsystems - Beijing China return (count); 13769a5557fdSlucy wang - Sun Microsystems - Beijing China } 13779a5557fdSlucy wang - Sun Microsystems - Beijing China 13789a5557fdSlucy wang - Sun Microsystems - Beijing China /* Process Command status ring */ 13799a5557fdSlucy wang - Sun Microsystems - Beijing China static int 13809a5557fdSlucy wang - Sun Microsystems - Beijing China unm_process_cmd_ring(struct unm_adapter_s *adapter) 13819a5557fdSlucy wang - Sun Microsystems - Beijing China { 13829a5557fdSlucy wang - Sun Microsystems - Beijing China u32 last_consumer; 13839a5557fdSlucy wang - Sun Microsystems - Beijing China u32 consumer; 13849a5557fdSlucy wang - Sun Microsystems - Beijing China int count = 0; 13859a5557fdSlucy wang - Sun Microsystems - Beijing China struct unm_cmd_buffer *buffer; 13869a5557fdSlucy wang - Sun Microsystems - Beijing China int done; 13879a5557fdSlucy wang - Sun Microsystems - Beijing China unm_dmah_node_t *dmah, *head = NULL, *tail = NULL; 13889a5557fdSlucy wang - Sun Microsystems - Beijing China uint32_t free_hdls = 0; 13899a5557fdSlucy wang - Sun Microsystems - Beijing China 13909a5557fdSlucy wang - Sun Microsystems - Beijing China (void) ddi_dma_sync(adapter->ctxDesc_dma_handle, sizeof (RingContext), 13919a5557fdSlucy wang - Sun Microsystems - Beijing China sizeof (uint32_t), DDI_DMA_SYNC_FORCPU); 13929a5557fdSlucy wang - Sun Microsystems - Beijing China 13939a5557fdSlucy wang - Sun Microsystems - Beijing China last_consumer = adapter->lastCmdConsumer; 13949a5557fdSlucy wang - Sun Microsystems - Beijing China consumer = *(adapter->cmdConsumer); 13959a5557fdSlucy wang - Sun Microsystems - Beijing China 13969a5557fdSlucy wang - Sun Microsystems - Beijing China while (last_consumer != consumer) { 13979a5557fdSlucy wang - Sun Microsystems - Beijing China buffer = &adapter->cmd_buf_arr[last_consumer]; 13989a5557fdSlucy wang - Sun Microsystems - Beijing China if (buffer->head != NULL) { 13999a5557fdSlucy wang - Sun Microsystems - Beijing China dmah = buffer->head; 14009a5557fdSlucy wang - Sun Microsystems - Beijing China while (dmah != NULL) { 14019a5557fdSlucy wang - Sun Microsystems - Beijing China (void) ddi_dma_unbind_handle(dmah->dmahdl); 14029a5557fdSlucy wang - Sun Microsystems - Beijing China dmah = dmah->next; 14039a5557fdSlucy wang - Sun Microsystems - Beijing China free_hdls++; 14049a5557fdSlucy wang - Sun Microsystems - Beijing China } 14059a5557fdSlucy wang - Sun Microsystems - Beijing China 14069a5557fdSlucy wang - Sun Microsystems - Beijing China if (head == NULL) { 14079a5557fdSlucy wang - Sun Microsystems - Beijing China head = buffer->head; 14089a5557fdSlucy wang - Sun Microsystems - Beijing China tail = buffer->tail; 14099a5557fdSlucy wang - Sun Microsystems - Beijing China } else { 14109a5557fdSlucy wang - Sun Microsystems - Beijing China tail->next = buffer->head; 14119a5557fdSlucy wang - Sun Microsystems - Beijing China tail = buffer->tail; 14129a5557fdSlucy wang - Sun Microsystems - Beijing China } 14139a5557fdSlucy wang - Sun Microsystems - Beijing China 14149a5557fdSlucy wang - Sun Microsystems - Beijing China buffer->head = NULL; 14159a5557fdSlucy wang - Sun Microsystems - Beijing China buffer->tail = NULL; 14169a5557fdSlucy wang - Sun Microsystems - Beijing China 14179a5557fdSlucy wang - Sun Microsystems - Beijing China if (buffer->msg != NULL) { 14189a5557fdSlucy wang - Sun Microsystems - Beijing China freemsg(buffer->msg); 14199a5557fdSlucy wang - Sun Microsystems - Beijing China buffer->msg = NULL; 14209a5557fdSlucy wang - Sun Microsystems - Beijing China } 14219a5557fdSlucy wang - Sun Microsystems - Beijing China } 14229a5557fdSlucy wang - Sun Microsystems - Beijing China 14239a5557fdSlucy wang - Sun Microsystems - Beijing China last_consumer = get_next_index(last_consumer, 14249a5557fdSlucy wang - Sun Microsystems - Beijing China adapter->MaxTxDescCount); 14259a5557fdSlucy wang - Sun Microsystems - Beijing China if (++count > NX_MAX_TXCOMPS) 14269a5557fdSlucy wang - Sun Microsystems - Beijing China break; 14279a5557fdSlucy wang - Sun Microsystems - Beijing China } 14289a5557fdSlucy wang - Sun Microsystems - Beijing China 14299a5557fdSlucy wang - Sun Microsystems - Beijing China if (count) { 14309a5557fdSlucy wang - Sun Microsystems - Beijing China int doresched; 14319a5557fdSlucy wang - Sun Microsystems - Beijing China 14329a5557fdSlucy wang - Sun Microsystems - Beijing China UNM_SPIN_LOCK(&adapter->tx_lock); 14339a5557fdSlucy wang - Sun Microsystems - Beijing China adapter->lastCmdConsumer = last_consumer; 14349a5557fdSlucy wang - Sun Microsystems - Beijing China adapter->freecmds += count; 14359a5557fdSlucy wang - Sun Microsystems - Beijing China membar_exit(); 14369a5557fdSlucy wang - Sun Microsystems - Beijing China 14379a5557fdSlucy wang - Sun Microsystems - Beijing China doresched = adapter->resched_needed; 14389a5557fdSlucy wang - Sun Microsystems - Beijing China if (doresched) 14399a5557fdSlucy wang - Sun Microsystems - Beijing China adapter->resched_needed = 0; 14409a5557fdSlucy wang - Sun Microsystems - Beijing China 14419a5557fdSlucy wang - Sun Microsystems - Beijing China if (head != NULL) 14429a5557fdSlucy wang - Sun Microsystems - Beijing China unm_return_dma_handle(adapter, head, tail, free_hdls); 14439a5557fdSlucy wang - Sun Microsystems - Beijing China 14449a5557fdSlucy wang - Sun Microsystems - Beijing China UNM_SPIN_UNLOCK(&adapter->tx_lock); 14459a5557fdSlucy wang - Sun Microsystems - Beijing China 14469a5557fdSlucy wang - Sun Microsystems - Beijing China if (doresched) 14479a5557fdSlucy wang - Sun Microsystems - Beijing China mac_tx_update(adapter->mach); 14489a5557fdSlucy wang - Sun Microsystems - Beijing China } 14499a5557fdSlucy wang - Sun Microsystems - Beijing China 14509a5557fdSlucy wang - Sun Microsystems - Beijing China (void) ddi_dma_sync(adapter->ctxDesc_dma_handle, sizeof (RingContext), 14519a5557fdSlucy wang - Sun Microsystems - Beijing China sizeof (uint32_t), DDI_DMA_SYNC_FORCPU); 14529a5557fdSlucy wang - Sun Microsystems - Beijing China 14539a5557fdSlucy wang - Sun Microsystems - Beijing China consumer = *(adapter->cmdConsumer); 14549a5557fdSlucy wang - Sun Microsystems - Beijing China done = (adapter->lastCmdConsumer == consumer); 14559a5557fdSlucy wang - Sun Microsystems - Beijing China 14569a5557fdSlucy wang - Sun Microsystems - Beijing China return (done); 14579a5557fdSlucy wang - Sun Microsystems - Beijing China } 14589a5557fdSlucy wang - Sun Microsystems - Beijing China 14599a5557fdSlucy wang - Sun Microsystems - Beijing China /* 14609a5557fdSlucy wang - Sun Microsystems - Beijing China * This is invoked from receive isr, and at initialization time when no 14619a5557fdSlucy wang - Sun Microsystems - Beijing China * rx buffers have been posted to card. Due to the single threaded nature 14629a5557fdSlucy wang - Sun Microsystems - Beijing China * of the invocation, pool_lock acquisition is not neccesary to protect 14639a5557fdSlucy wang - Sun Microsystems - Beijing China * pool_list. 14649a5557fdSlucy wang - Sun Microsystems - Beijing China */ 14659a5557fdSlucy wang - Sun Microsystems - Beijing China static unm_rx_buffer_t * 14669a5557fdSlucy wang - Sun Microsystems - Beijing China unm_reserve_rx_buffer(unm_rcv_desc_ctx_t *rcv_desc) 14679a5557fdSlucy wang - Sun Microsystems - Beijing China { 14689a5557fdSlucy wang - Sun Microsystems - Beijing China unm_rx_buffer_t *rx_buffer = NULL; 14699a5557fdSlucy wang - Sun Microsystems - Beijing China 14709a5557fdSlucy wang - Sun Microsystems - Beijing China /* mutex_enter(rcv_desc->pool_lock); */ 14719a5557fdSlucy wang - Sun Microsystems - Beijing China if (rcv_desc->rx_buf_free) { 14729a5557fdSlucy wang - Sun Microsystems - Beijing China rx_buffer = rcv_desc->pool_list; 14739a5557fdSlucy wang - Sun Microsystems - Beijing China rcv_desc->pool_list = rx_buffer->next; 14749a5557fdSlucy wang - Sun Microsystems - Beijing China rx_buffer->next = NULL; 14759a5557fdSlucy wang - Sun Microsystems - Beijing China rcv_desc->rx_buf_free--; 14769a5557fdSlucy wang - Sun Microsystems - Beijing China } else { 14779a5557fdSlucy wang - Sun Microsystems - Beijing China mutex_enter(rcv_desc->recycle_lock); 14789a5557fdSlucy wang - Sun Microsystems - Beijing China 14799a5557fdSlucy wang - Sun Microsystems - Beijing China if (rcv_desc->rx_buf_recycle) { 14809a5557fdSlucy wang - Sun Microsystems - Beijing China rcv_desc->pool_list = rcv_desc->recycle_list; 14819a5557fdSlucy wang - Sun Microsystems - Beijing China rcv_desc->recycle_list = NULL; 14829a5557fdSlucy wang - Sun Microsystems - Beijing China rcv_desc->rx_buf_free += rcv_desc->rx_buf_recycle; 14839a5557fdSlucy wang - Sun Microsystems - Beijing China rcv_desc->rx_buf_recycle = 0; 14849a5557fdSlucy wang - Sun Microsystems - Beijing China 14859a5557fdSlucy wang - Sun Microsystems - Beijing China rx_buffer = rcv_desc->pool_list; 14869a5557fdSlucy wang - Sun Microsystems - Beijing China rcv_desc->pool_list = rx_buffer->next; 14879a5557fdSlucy wang - Sun Microsystems - Beijing China rx_buffer->next = NULL; 14889a5557fdSlucy wang - Sun Microsystems - Beijing China rcv_desc->rx_buf_free--; 14899a5557fdSlucy wang - Sun Microsystems - Beijing China } 14909a5557fdSlucy wang - Sun Microsystems - Beijing China 14919a5557fdSlucy wang - Sun Microsystems - Beijing China mutex_exit(rcv_desc->recycle_lock); 14929a5557fdSlucy wang - Sun Microsystems - Beijing China } 14939a5557fdSlucy wang - Sun Microsystems - Beijing China 14949a5557fdSlucy wang - Sun Microsystems - Beijing China /* mutex_exit(rcv_desc->pool_lock); */ 14959a5557fdSlucy wang - Sun Microsystems - Beijing China return (rx_buffer); 14969a5557fdSlucy wang - Sun Microsystems - Beijing China } 14979a5557fdSlucy wang - Sun Microsystems - Beijing China 14989a5557fdSlucy wang - Sun Microsystems - Beijing China static void 14999a5557fdSlucy wang - Sun Microsystems - Beijing China post_rx_doorbell(struct unm_adapter_s *adapter, uint32_t ringid, int count) 15009a5557fdSlucy wang - Sun Microsystems - Beijing China { 15019a5557fdSlucy wang - Sun Microsystems - Beijing China #define UNM_RCV_PEG_DB_ID 2 15029a5557fdSlucy wang - Sun Microsystems - Beijing China #define UNM_RCV_PRODUCER_OFFSET 0 15039a5557fdSlucy wang - Sun Microsystems - Beijing China ctx_msg msg = {0}; 15049a5557fdSlucy wang - Sun Microsystems - Beijing China 15059a5557fdSlucy wang - Sun Microsystems - Beijing China /* 15069a5557fdSlucy wang - Sun Microsystems - Beijing China * Write a doorbell msg to tell phanmon of change in 15079a5557fdSlucy wang - Sun Microsystems - Beijing China * receive ring producer 15089a5557fdSlucy wang - Sun Microsystems - Beijing China */ 15099a5557fdSlucy wang - Sun Microsystems - Beijing China msg.PegId = UNM_RCV_PEG_DB_ID; 15109a5557fdSlucy wang - Sun Microsystems - Beijing China msg.privId = 1; 15119a5557fdSlucy wang - Sun Microsystems - Beijing China msg.Count = count; 15129a5557fdSlucy wang - Sun Microsystems - Beijing China msg.CtxId = adapter->portnum; 15139a5557fdSlucy wang - Sun Microsystems - Beijing China msg.Opcode = UNM_RCV_PRODUCER(ringid); 15149a5557fdSlucy wang - Sun Microsystems - Beijing China dbwritel(*((__uint32_t *)&msg), 15159a5557fdSlucy wang - Sun Microsystems - Beijing China (void *)(DB_NORMALIZE(adapter, UNM_RCV_PRODUCER_OFFSET))); 15169a5557fdSlucy wang - Sun Microsystems - Beijing China } 15179a5557fdSlucy wang - Sun Microsystems - Beijing China 15189a5557fdSlucy wang - Sun Microsystems - Beijing China static int 15199a5557fdSlucy wang - Sun Microsystems - Beijing China unm_post_rx_buffers(struct unm_adapter_s *adapter, uint32_t ringid) 15209a5557fdSlucy wang - Sun Microsystems - Beijing China { 15219a5557fdSlucy wang - Sun Microsystems - Beijing China unm_recv_context_t *recv_ctx = &(adapter->recv_ctx[0]); 15229a5557fdSlucy wang - Sun Microsystems - Beijing China unm_rcv_desc_ctx_t *rcv_desc = &recv_ctx->rcv_desc[ringid]; 15239a5557fdSlucy wang - Sun Microsystems - Beijing China unm_rx_buffer_t *rx_buffer; 15249a5557fdSlucy wang - Sun Microsystems - Beijing China rcvDesc_t *pdesc; 15259a5557fdSlucy wang - Sun Microsystems - Beijing China int count; 15269a5557fdSlucy wang - Sun Microsystems - Beijing China 15279a5557fdSlucy wang - Sun Microsystems - Beijing China for (count = 0; count < rcv_desc->MaxRxDescCount; count++) { 15289a5557fdSlucy wang - Sun Microsystems - Beijing China rx_buffer = unm_reserve_rx_buffer(rcv_desc); 15299a5557fdSlucy wang - Sun Microsystems - Beijing China if (rx_buffer != NULL) { 15309a5557fdSlucy wang - Sun Microsystems - Beijing China pdesc = &rcv_desc->desc_head[count]; 15319a5557fdSlucy wang - Sun Microsystems - Beijing China pdesc->referenceHandle = rxbuf2index(rcv_desc, 15329a5557fdSlucy wang - Sun Microsystems - Beijing China rx_buffer); 15339a5557fdSlucy wang - Sun Microsystems - Beijing China pdesc->flags = ringid; 15349a5557fdSlucy wang - Sun Microsystems - Beijing China pdesc->bufferLength = rcv_desc->dma_size; 15359a5557fdSlucy wang - Sun Microsystems - Beijing China pdesc->AddrBuffer = rx_buffer->dma_info.dma_addr; 15369a5557fdSlucy wang - Sun Microsystems - Beijing China } 15379a5557fdSlucy wang - Sun Microsystems - Beijing China else 15389a5557fdSlucy wang - Sun Microsystems - Beijing China return (DDI_FAILURE); 15399a5557fdSlucy wang - Sun Microsystems - Beijing China } 15409a5557fdSlucy wang - Sun Microsystems - Beijing China 15419a5557fdSlucy wang - Sun Microsystems - Beijing China rcv_desc->producer = count % rcv_desc->MaxRxDescCount; 15429a5557fdSlucy wang - Sun Microsystems - Beijing China count--; 15439a5557fdSlucy wang - Sun Microsystems - Beijing China unm_desc_dma_sync(rcv_desc->rx_desc_dma_handle, 15449a5557fdSlucy wang - Sun Microsystems - Beijing China 0, /* start */ 15459a5557fdSlucy wang - Sun Microsystems - Beijing China count, /* count */ 15469a5557fdSlucy wang - Sun Microsystems - Beijing China count, /* range */ 15479a5557fdSlucy wang - Sun Microsystems - Beijing China sizeof (rcvDesc_t), /* unit_size */ 15489a5557fdSlucy wang - Sun Microsystems - Beijing China DDI_DMA_SYNC_FORDEV); /* direction */ 15499a5557fdSlucy wang - Sun Microsystems - Beijing China 15509a5557fdSlucy wang - Sun Microsystems - Beijing China rcv_desc->rx_buf_card = rcv_desc->MaxRxDescCount; 15519a5557fdSlucy wang - Sun Microsystems - Beijing China UNM_READ_LOCK(&adapter->adapter_lock); 15529a5557fdSlucy wang - Sun Microsystems - Beijing China adapter->unm_nic_hw_write_wx(adapter, rcv_desc->host_rx_producer, 15539a5557fdSlucy wang - Sun Microsystems - Beijing China &count, 4); 15549a5557fdSlucy wang - Sun Microsystems - Beijing China if (adapter->fw_major < 4) 15559a5557fdSlucy wang - Sun Microsystems - Beijing China post_rx_doorbell(adapter, ringid, count); 15569a5557fdSlucy wang - Sun Microsystems - Beijing China UNM_READ_UNLOCK(&adapter->adapter_lock); 15579a5557fdSlucy wang - Sun Microsystems - Beijing China 15589a5557fdSlucy wang - Sun Microsystems - Beijing China return (DDI_SUCCESS); 15599a5557fdSlucy wang - Sun Microsystems - Beijing China } 15609a5557fdSlucy wang - Sun Microsystems - Beijing China 15619a5557fdSlucy wang - Sun Microsystems - Beijing China static void 15629a5557fdSlucy wang - Sun Microsystems - Beijing China unm_post_rx_buffers_nodb(struct unm_adapter_s *adapter, 15639a5557fdSlucy wang - Sun Microsystems - Beijing China uint32_t ringid) 15649a5557fdSlucy wang - Sun Microsystems - Beijing China { 15659a5557fdSlucy wang - Sun Microsystems - Beijing China unm_recv_context_t *recv_ctx = &(adapter->recv_ctx[0]); 15669a5557fdSlucy wang - Sun Microsystems - Beijing China unm_rcv_desc_ctx_t *rcv_desc = &recv_ctx->rcv_desc[ringid]; 15679a5557fdSlucy wang - Sun Microsystems - Beijing China struct unm_rx_buffer *rx_buffer; 15689a5557fdSlucy wang - Sun Microsystems - Beijing China rcvDesc_t *pdesc; 15699a5557fdSlucy wang - Sun Microsystems - Beijing China int count, producer = rcv_desc->producer; 15709a5557fdSlucy wang - Sun Microsystems - Beijing China int last_producer = producer; 15719a5557fdSlucy wang - Sun Microsystems - Beijing China 15729a5557fdSlucy wang - Sun Microsystems - Beijing China for (count = 0; count < rcv_desc->rx_desc_handled; count++) { 15739a5557fdSlucy wang - Sun Microsystems - Beijing China rx_buffer = unm_reserve_rx_buffer(rcv_desc); 15749a5557fdSlucy wang - Sun Microsystems - Beijing China if (rx_buffer != NULL) { 15759a5557fdSlucy wang - Sun Microsystems - Beijing China pdesc = &rcv_desc->desc_head[producer]; 15769a5557fdSlucy wang - Sun Microsystems - Beijing China pdesc->referenceHandle = rxbuf2index(rcv_desc, 15779a5557fdSlucy wang - Sun Microsystems - Beijing China rx_buffer); 15789a5557fdSlucy wang - Sun Microsystems - Beijing China pdesc->flags = ringid; 15799a5557fdSlucy wang - Sun Microsystems - Beijing China pdesc->bufferLength = rcv_desc->dma_size; 15809a5557fdSlucy wang - Sun Microsystems - Beijing China pdesc->AddrBuffer = rx_buffer->dma_info.dma_addr; 15819a5557fdSlucy wang - Sun Microsystems - Beijing China } else { 15829a5557fdSlucy wang - Sun Microsystems - Beijing China adapter->stats.outofrxbuf++; 15839a5557fdSlucy wang - Sun Microsystems - Beijing China break; 15849a5557fdSlucy wang - Sun Microsystems - Beijing China } 15859a5557fdSlucy wang - Sun Microsystems - Beijing China producer = get_next_index(producer, rcv_desc->MaxRxDescCount); 15869a5557fdSlucy wang - Sun Microsystems - Beijing China } 15879a5557fdSlucy wang - Sun Microsystems - Beijing China 15889a5557fdSlucy wang - Sun Microsystems - Beijing China /* if we did allocate buffers, then write the count to Phantom */ 15899a5557fdSlucy wang - Sun Microsystems - Beijing China if (count) { 15909a5557fdSlucy wang - Sun Microsystems - Beijing China /* Sync rx ring, considering case for wrap around */ 15919a5557fdSlucy wang - Sun Microsystems - Beijing China unm_desc_dma_sync(rcv_desc->rx_desc_dma_handle, last_producer, 15929a5557fdSlucy wang - Sun Microsystems - Beijing China count, rcv_desc->MaxRxDescCount, sizeof (rcvDesc_t), 15939a5557fdSlucy wang - Sun Microsystems - Beijing China DDI_DMA_SYNC_FORDEV); 15949a5557fdSlucy wang - Sun Microsystems - Beijing China 15959a5557fdSlucy wang - Sun Microsystems - Beijing China rcv_desc->producer = producer; 15969a5557fdSlucy wang - Sun Microsystems - Beijing China rcv_desc->rx_desc_handled -= count; 15979a5557fdSlucy wang - Sun Microsystems - Beijing China rcv_desc->rx_buf_card += count; 15989a5557fdSlucy wang - Sun Microsystems - Beijing China 15999a5557fdSlucy wang - Sun Microsystems - Beijing China producer = (producer - 1) % rcv_desc->MaxRxDescCount; 16009a5557fdSlucy wang - Sun Microsystems - Beijing China UNM_READ_LOCK(&adapter->adapter_lock); 16019a5557fdSlucy wang - Sun Microsystems - Beijing China adapter->unm_nic_hw_write_wx(adapter, 16029a5557fdSlucy wang - Sun Microsystems - Beijing China rcv_desc->host_rx_producer, &producer, 4); 16039a5557fdSlucy wang - Sun Microsystems - Beijing China UNM_READ_UNLOCK(&adapter->adapter_lock); 16049a5557fdSlucy wang - Sun Microsystems - Beijing China } 16059a5557fdSlucy wang - Sun Microsystems - Beijing China } 16069a5557fdSlucy wang - Sun Microsystems - Beijing China 16079a5557fdSlucy wang - Sun Microsystems - Beijing China int 16089a5557fdSlucy wang - Sun Microsystems - Beijing China unm_nic_fill_statistics_128M(struct unm_adapter_s *adapter, 16099a5557fdSlucy wang - Sun Microsystems - Beijing China struct unm_statistics *unm_stats) 16109a5557fdSlucy wang - Sun Microsystems - Beijing China { 16119a5557fdSlucy wang - Sun Microsystems - Beijing China void *addr; 16129a5557fdSlucy wang - Sun Microsystems - Beijing China if (adapter->ahw.board_type == UNM_NIC_XGBE) { 16139a5557fdSlucy wang - Sun Microsystems - Beijing China UNM_WRITE_LOCK(&adapter->adapter_lock); 16149a5557fdSlucy wang - Sun Microsystems - Beijing China unm_nic_pci_change_crbwindow_128M(adapter, 0); 16159a5557fdSlucy wang - Sun Microsystems - Beijing China 16169a5557fdSlucy wang - Sun Microsystems - Beijing China /* LINTED: E_FALSE_LOGICAL_EXPR */ 16179a5557fdSlucy wang - Sun Microsystems - Beijing China UNM_NIC_LOCKED_READ_REG(UNM_NIU_XGE_TX_BYTE_CNT, 16189a5557fdSlucy wang - Sun Microsystems - Beijing China &(unm_stats->tx_bytes)); 16199a5557fdSlucy wang - Sun Microsystems - Beijing China /* LINTED: E_FALSE_LOGICAL_EXPR */ 16209a5557fdSlucy wang - Sun Microsystems - Beijing China UNM_NIC_LOCKED_READ_REG(UNM_NIU_XGE_TX_FRAME_CNT, 16219a5557fdSlucy wang - Sun Microsystems - Beijing China &(unm_stats->tx_packets)); 16229a5557fdSlucy wang - Sun Microsystems - Beijing China /* LINTED: E_FALSE_LOGICAL_EXPR */ 16239a5557fdSlucy wang - Sun Microsystems - Beijing China UNM_NIC_LOCKED_READ_REG(UNM_NIU_XGE_RX_BYTE_CNT, 16249a5557fdSlucy wang - Sun Microsystems - Beijing China &(unm_stats->rx_bytes)); 16259a5557fdSlucy wang - Sun Microsystems - Beijing China /* LINTED: E_FALSE_LOGICAL_EXPR */ 16269a5557fdSlucy wang - Sun Microsystems - Beijing China UNM_NIC_LOCKED_READ_REG(UNM_NIU_XGE_RX_FRAME_CNT, 16279a5557fdSlucy wang - Sun Microsystems - Beijing China &(unm_stats->rx_packets)); 16289a5557fdSlucy wang - Sun Microsystems - Beijing China /* LINTED: E_FALSE_LOGICAL_EXPR */ 16299a5557fdSlucy wang - Sun Microsystems - Beijing China UNM_NIC_LOCKED_READ_REG(UNM_NIU_XGE_AGGR_ERROR_CNT, 16309a5557fdSlucy wang - Sun Microsystems - Beijing China &(unm_stats->rx_errors)); 16319a5557fdSlucy wang - Sun Microsystems - Beijing China /* LINTED: E_FALSE_LOGICAL_EXPR */ 16329a5557fdSlucy wang - Sun Microsystems - Beijing China UNM_NIC_LOCKED_READ_REG(UNM_NIU_XGE_CRC_ERROR_CNT, 16339a5557fdSlucy wang - Sun Microsystems - Beijing China &(unm_stats->rx_CRC_errors)); 16349a5557fdSlucy wang - Sun Microsystems - Beijing China /* LINTED: E_FALSE_LOGICAL_EXPR */ 16359a5557fdSlucy wang - Sun Microsystems - Beijing China UNM_NIC_LOCKED_READ_REG(UNM_NIU_XGE_OVERSIZE_FRAME_ERR, 16369a5557fdSlucy wang - Sun Microsystems - Beijing China &(unm_stats->rx_long_length_error)); 16379a5557fdSlucy wang - Sun Microsystems - Beijing China /* LINTED: E_FALSE_LOGICAL_EXPR */ 16389a5557fdSlucy wang - Sun Microsystems - Beijing China UNM_NIC_LOCKED_READ_REG(UNM_NIU_XGE_UNDERSIZE_FRAME_ERR, 16399a5557fdSlucy wang - Sun Microsystems - Beijing China &(unm_stats->rx_short_length_error)); 16409a5557fdSlucy wang - Sun Microsystems - Beijing China 16419a5557fdSlucy wang - Sun Microsystems - Beijing China /* 16429a5557fdSlucy wang - Sun Microsystems - Beijing China * For reading rx_MAC_error bit different procedure 16439a5557fdSlucy wang - Sun Microsystems - Beijing China * UNM_NIC_LOCKED_WRITE_REG(UNM_NIU_TEST_MUX_CTL, 0x15); 16449a5557fdSlucy wang - Sun Microsystems - Beijing China * UNM_NIC_LOCKED_READ_REG((UNM_CRB_NIU + 0xC0), &temp); 16459a5557fdSlucy wang - Sun Microsystems - Beijing China * unm_stats->rx_MAC_errors = temp & 0xff; 16469a5557fdSlucy wang - Sun Microsystems - Beijing China */ 16479a5557fdSlucy wang - Sun Microsystems - Beijing China 16489a5557fdSlucy wang - Sun Microsystems - Beijing China unm_nic_pci_change_crbwindow_128M(adapter, 1); 16499a5557fdSlucy wang - Sun Microsystems - Beijing China UNM_WRITE_UNLOCK(&adapter->adapter_lock); 16509a5557fdSlucy wang - Sun Microsystems - Beijing China } else { 16519a5557fdSlucy wang - Sun Microsystems - Beijing China UNM_SPIN_LOCK_ISR(&adapter->tx_lock); 16529a5557fdSlucy wang - Sun Microsystems - Beijing China unm_stats->tx_bytes = adapter->stats.txbytes; 16539a5557fdSlucy wang - Sun Microsystems - Beijing China unm_stats->tx_packets = adapter->stats.xmitedframes + 16549a5557fdSlucy wang - Sun Microsystems - Beijing China adapter->stats.xmitfinished; 16559a5557fdSlucy wang - Sun Microsystems - Beijing China unm_stats->rx_bytes = adapter->stats.rxbytes; 16569a5557fdSlucy wang - Sun Microsystems - Beijing China unm_stats->rx_packets = adapter->stats.no_rcv; 16579a5557fdSlucy wang - Sun Microsystems - Beijing China unm_stats->rx_errors = adapter->stats.rcvdbadmsg; 16589a5557fdSlucy wang - Sun Microsystems - Beijing China unm_stats->tx_errors = adapter->stats.nocmddescriptor; 16599a5557fdSlucy wang - Sun Microsystems - Beijing China unm_stats->rx_short_length_error = adapter->stats.uplcong; 16609a5557fdSlucy wang - Sun Microsystems - Beijing China unm_stats->rx_long_length_error = adapter->stats.uphcong; 16619a5557fdSlucy wang - Sun Microsystems - Beijing China unm_stats->rx_CRC_errors = 0; 16629a5557fdSlucy wang - Sun Microsystems - Beijing China unm_stats->rx_MAC_errors = 0; 16639a5557fdSlucy wang - Sun Microsystems - Beijing China UNM_SPIN_UNLOCK_ISR(&adapter->tx_lock); 16649a5557fdSlucy wang - Sun Microsystems - Beijing China } 16659a5557fdSlucy wang - Sun Microsystems - Beijing China return (0); 16669a5557fdSlucy wang - Sun Microsystems - Beijing China } 16679a5557fdSlucy wang - Sun Microsystems - Beijing China 16689a5557fdSlucy wang - Sun Microsystems - Beijing China int 16699a5557fdSlucy wang - Sun Microsystems - Beijing China unm_nic_fill_statistics_2M(struct unm_adapter_s *adapter, 16709a5557fdSlucy wang - Sun Microsystems - Beijing China struct unm_statistics *unm_stats) 16719a5557fdSlucy wang - Sun Microsystems - Beijing China { 16729a5557fdSlucy wang - Sun Microsystems - Beijing China if (adapter->ahw.board_type == UNM_NIC_XGBE) { 16739a5557fdSlucy wang - Sun Microsystems - Beijing China (void) unm_nic_hw_read_wx_2M(adapter, UNM_NIU_XGE_TX_BYTE_CNT, 16749a5557fdSlucy wang - Sun Microsystems - Beijing China &(unm_stats->tx_bytes), 4); 16759a5557fdSlucy wang - Sun Microsystems - Beijing China (void) unm_nic_hw_read_wx_2M(adapter, UNM_NIU_XGE_TX_FRAME_CNT, 16769a5557fdSlucy wang - Sun Microsystems - Beijing China &(unm_stats->tx_packets), 4); 16779a5557fdSlucy wang - Sun Microsystems - Beijing China (void) unm_nic_hw_read_wx_2M(adapter, UNM_NIU_XGE_RX_BYTE_CNT, 16789a5557fdSlucy wang - Sun Microsystems - Beijing China &(unm_stats->rx_bytes), 4); 16799a5557fdSlucy wang - Sun Microsystems - Beijing China (void) unm_nic_hw_read_wx_2M(adapter, UNM_NIU_XGE_RX_FRAME_CNT, 16809a5557fdSlucy wang - Sun Microsystems - Beijing China &(unm_stats->rx_packets), 4); 16819a5557fdSlucy wang - Sun Microsystems - Beijing China (void) unm_nic_hw_read_wx_2M(adapter, 16829a5557fdSlucy wang - Sun Microsystems - Beijing China UNM_NIU_XGE_AGGR_ERROR_CNT, &(unm_stats->rx_errors), 4); 16839a5557fdSlucy wang - Sun Microsystems - Beijing China (void) unm_nic_hw_read_wx_2M(adapter, UNM_NIU_XGE_CRC_ERROR_CNT, 16849a5557fdSlucy wang - Sun Microsystems - Beijing China &(unm_stats->rx_CRC_errors), 4); 16859a5557fdSlucy wang - Sun Microsystems - Beijing China (void) unm_nic_hw_read_wx_2M(adapter, 16869a5557fdSlucy wang - Sun Microsystems - Beijing China UNM_NIU_XGE_OVERSIZE_FRAME_ERR, 16879a5557fdSlucy wang - Sun Microsystems - Beijing China &(unm_stats->rx_long_length_error), 4); 16889a5557fdSlucy wang - Sun Microsystems - Beijing China (void) unm_nic_hw_read_wx_2M(adapter, 16899a5557fdSlucy wang - Sun Microsystems - Beijing China UNM_NIU_XGE_UNDERSIZE_FRAME_ERR, 16909a5557fdSlucy wang - Sun Microsystems - Beijing China &(unm_stats->rx_short_length_error), 4); 16919a5557fdSlucy wang - Sun Microsystems - Beijing China } else { 16929a5557fdSlucy wang - Sun Microsystems - Beijing China UNM_SPIN_LOCK_ISR(&adapter->tx_lock); 16939a5557fdSlucy wang - Sun Microsystems - Beijing China unm_stats->tx_bytes = adapter->stats.txbytes; 16949a5557fdSlucy wang - Sun Microsystems - Beijing China unm_stats->tx_packets = adapter->stats.xmitedframes + 16959a5557fdSlucy wang - Sun Microsystems - Beijing China adapter->stats.xmitfinished; 16969a5557fdSlucy wang - Sun Microsystems - Beijing China unm_stats->rx_bytes = adapter->stats.rxbytes; 16979a5557fdSlucy wang - Sun Microsystems - Beijing China unm_stats->rx_packets = adapter->stats.no_rcv; 16989a5557fdSlucy wang - Sun Microsystems - Beijing China unm_stats->rx_errors = adapter->stats.rcvdbadmsg; 16999a5557fdSlucy wang - Sun Microsystems - Beijing China unm_stats->tx_errors = adapter->stats.nocmddescriptor; 17009a5557fdSlucy wang - Sun Microsystems - Beijing China unm_stats->rx_short_length_error = adapter->stats.uplcong; 17019a5557fdSlucy wang - Sun Microsystems - Beijing China unm_stats->rx_long_length_error = adapter->stats.uphcong; 17029a5557fdSlucy wang - Sun Microsystems - Beijing China unm_stats->rx_CRC_errors = 0; 17039a5557fdSlucy wang - Sun Microsystems - Beijing China unm_stats->rx_MAC_errors = 0; 17049a5557fdSlucy wang - Sun Microsystems - Beijing China UNM_SPIN_UNLOCK_ISR(&adapter->tx_lock); 17059a5557fdSlucy wang - Sun Microsystems - Beijing China } 17069a5557fdSlucy wang - Sun Microsystems - Beijing China return (0); 17079a5557fdSlucy wang - Sun Microsystems - Beijing China } 17089a5557fdSlucy wang - Sun Microsystems - Beijing China 17099a5557fdSlucy wang - Sun Microsystems - Beijing China int 17109a5557fdSlucy wang - Sun Microsystems - Beijing China unm_nic_clear_statistics_128M(struct unm_adapter_s *adapter) 17119a5557fdSlucy wang - Sun Microsystems - Beijing China { 17129a5557fdSlucy wang - Sun Microsystems - Beijing China void *addr; 17139a5557fdSlucy wang - Sun Microsystems - Beijing China int data = 0; 17149a5557fdSlucy wang - Sun Microsystems - Beijing China 17159a5557fdSlucy wang - Sun Microsystems - Beijing China UNM_WRITE_LOCK(&adapter->adapter_lock); 17169a5557fdSlucy wang - Sun Microsystems - Beijing China unm_nic_pci_change_crbwindow_128M(adapter, 0); 17179a5557fdSlucy wang - Sun Microsystems - Beijing China 17189a5557fdSlucy wang - Sun Microsystems - Beijing China /* LINTED: E_FALSE_LOGICAL_EXPR */ 17199a5557fdSlucy wang - Sun Microsystems - Beijing China UNM_NIC_LOCKED_WRITE_REG(UNM_NIU_XGE_TX_BYTE_CNT, &data); 17209a5557fdSlucy wang - Sun Microsystems - Beijing China /* LINTED: E_FALSE_LOGICAL_EXPR */ 17219a5557fdSlucy wang - Sun Microsystems - Beijing China UNM_NIC_LOCKED_WRITE_REG(UNM_NIU_XGE_TX_FRAME_CNT, &data); 17229a5557fdSlucy wang - Sun Microsystems - Beijing China /* LINTED: E_FALSE_LOGICAL_EXPR */ 17239a5557fdSlucy wang - Sun Microsystems - Beijing China UNM_NIC_LOCKED_WRITE_REG(UNM_NIU_XGE_RX_BYTE_CNT, &data); 17249a5557fdSlucy wang - Sun Microsystems - Beijing China /* LINTED: E_FALSE_LOGICAL_EXPR */ 17259a5557fdSlucy wang - Sun Microsystems - Beijing China UNM_NIC_LOCKED_WRITE_REG(UNM_NIU_XGE_RX_FRAME_CNT, &data); 17269a5557fdSlucy wang - Sun Microsystems - Beijing China /* LINTED: E_FALSE_LOGICAL_EXPR */ 17279a5557fdSlucy wang - Sun Microsystems - Beijing China UNM_NIC_LOCKED_WRITE_REG(UNM_NIU_XGE_AGGR_ERROR_CNT, &data); 17289a5557fdSlucy wang - Sun Microsystems - Beijing China /* LINTED: E_FALSE_LOGICAL_EXPR */ 17299a5557fdSlucy wang - Sun Microsystems - Beijing China UNM_NIC_LOCKED_WRITE_REG(UNM_NIU_XGE_CRC_ERROR_CNT, &data); 17309a5557fdSlucy wang - Sun Microsystems - Beijing China /* LINTED: E_FALSE_LOGICAL_EXPR */ 17319a5557fdSlucy wang - Sun Microsystems - Beijing China UNM_NIC_LOCKED_WRITE_REG(UNM_NIU_XGE_OVERSIZE_FRAME_ERR, &data); 17329a5557fdSlucy wang - Sun Microsystems - Beijing China /* LINTED: E_FALSE_LOGICAL_EXPR */ 17339a5557fdSlucy wang - Sun Microsystems - Beijing China UNM_NIC_LOCKED_WRITE_REG(UNM_NIU_XGE_UNDERSIZE_FRAME_ERR, &data); 17349a5557fdSlucy wang - Sun Microsystems - Beijing China 17359a5557fdSlucy wang - Sun Microsystems - Beijing China unm_nic_pci_change_crbwindow_128M(adapter, 1); 17369a5557fdSlucy wang - Sun Microsystems - Beijing China UNM_WRITE_UNLOCK(&adapter->adapter_lock); 17379a5557fdSlucy wang - Sun Microsystems - Beijing China unm_nic_clear_stats(adapter); 17389a5557fdSlucy wang - Sun Microsystems - Beijing China return (0); 17399a5557fdSlucy wang - Sun Microsystems - Beijing China } 17409a5557fdSlucy wang - Sun Microsystems - Beijing China 17419a5557fdSlucy wang - Sun Microsystems - Beijing China int 17429a5557fdSlucy wang - Sun Microsystems - Beijing China unm_nic_clear_statistics_2M(struct unm_adapter_s *adapter) 17439a5557fdSlucy wang - Sun Microsystems - Beijing China { 17449a5557fdSlucy wang - Sun Microsystems - Beijing China int data = 0; 17459a5557fdSlucy wang - Sun Microsystems - Beijing China 17469a5557fdSlucy wang - Sun Microsystems - Beijing China (void) unm_nic_hw_write_wx_2M(adapter, UNM_NIU_XGE_TX_BYTE_CNT, 17479a5557fdSlucy wang - Sun Microsystems - Beijing China &data, 4); 17489a5557fdSlucy wang - Sun Microsystems - Beijing China (void) unm_nic_hw_write_wx_2M(adapter, UNM_NIU_XGE_TX_FRAME_CNT, 17499a5557fdSlucy wang - Sun Microsystems - Beijing China &data, 4); 17509a5557fdSlucy wang - Sun Microsystems - Beijing China (void) unm_nic_hw_write_wx_2M(adapter, UNM_NIU_XGE_RX_BYTE_CNT, 17519a5557fdSlucy wang - Sun Microsystems - Beijing China &data, 4); 17529a5557fdSlucy wang - Sun Microsystems - Beijing China (void) unm_nic_hw_write_wx_2M(adapter, UNM_NIU_XGE_RX_FRAME_CNT, 17539a5557fdSlucy wang - Sun Microsystems - Beijing China &data, 4); 17549a5557fdSlucy wang - Sun Microsystems - Beijing China (void) unm_nic_hw_write_wx_2M(adapter, UNM_NIU_XGE_AGGR_ERROR_CNT, 17559a5557fdSlucy wang - Sun Microsystems - Beijing China &data, 4); 17569a5557fdSlucy wang - Sun Microsystems - Beijing China (void) unm_nic_hw_write_wx_2M(adapter, UNM_NIU_XGE_CRC_ERROR_CNT, 17579a5557fdSlucy wang - Sun Microsystems - Beijing China &data, 4); 17589a5557fdSlucy wang - Sun Microsystems - Beijing China (void) unm_nic_hw_write_wx_2M(adapter, UNM_NIU_XGE_OVERSIZE_FRAME_ERR, 17599a5557fdSlucy wang - Sun Microsystems - Beijing China &data, 4); 17609a5557fdSlucy wang - Sun Microsystems - Beijing China (void) unm_nic_hw_write_wx_2M(adapter, UNM_NIU_XGE_UNDERSIZE_FRAME_ERR, 17619a5557fdSlucy wang - Sun Microsystems - Beijing China &data, 4); 17629a5557fdSlucy wang - Sun Microsystems - Beijing China unm_nic_clear_stats(adapter); 17639a5557fdSlucy wang - Sun Microsystems - Beijing China return (0); 17649a5557fdSlucy wang - Sun Microsystems - Beijing China } 17659a5557fdSlucy wang - Sun Microsystems - Beijing China 17669a5557fdSlucy wang - Sun Microsystems - Beijing China /* 17679a5557fdSlucy wang - Sun Microsystems - Beijing China * unm_nic_ioctl () We provide the tcl/phanmon support 17689a5557fdSlucy wang - Sun Microsystems - Beijing China * through these ioctls. 17699a5557fdSlucy wang - Sun Microsystems - Beijing China */ 17709a5557fdSlucy wang - Sun Microsystems - Beijing China static void 17719a5557fdSlucy wang - Sun Microsystems - Beijing China unm_nic_ioctl(struct unm_adapter_s *adapter, int cmd, queue_t *q, mblk_t *mp) 17729a5557fdSlucy wang - Sun Microsystems - Beijing China { 17739a5557fdSlucy wang - Sun Microsystems - Beijing China void *ptr; 17749a5557fdSlucy wang - Sun Microsystems - Beijing China 17759a5557fdSlucy wang - Sun Microsystems - Beijing China switch (cmd) { 17769a5557fdSlucy wang - Sun Microsystems - Beijing China case UNM_NIC_CMD: 17779a5557fdSlucy wang - Sun Microsystems - Beijing China (void) unm_nic_do_ioctl(adapter, q, mp); 17789a5557fdSlucy wang - Sun Microsystems - Beijing China break; 17799a5557fdSlucy wang - Sun Microsystems - Beijing China 17809a5557fdSlucy wang - Sun Microsystems - Beijing China case UNM_NIC_NAME: 17819a5557fdSlucy wang - Sun Microsystems - Beijing China ptr = (void *) mp->b_cont->b_rptr; 17829a5557fdSlucy wang - Sun Microsystems - Beijing China 17839a5557fdSlucy wang - Sun Microsystems - Beijing China /* 17849a5557fdSlucy wang - Sun Microsystems - Beijing China * Phanmon checks for "UNM-UNM" string 17859a5557fdSlucy wang - Sun Microsystems - Beijing China * Replace the hardcoded value with appropriate macro 17869a5557fdSlucy wang - Sun Microsystems - Beijing China */ 17879a5557fdSlucy wang - Sun Microsystems - Beijing China DPRINTF(-1, (CE_CONT, "UNM_NIC_NAME ioctl executed %d %d\n", 17889a5557fdSlucy wang - Sun Microsystems - Beijing China cmd, __LINE__)); 17899a5557fdSlucy wang - Sun Microsystems - Beijing China (void) memcpy(ptr, "UNM-UNM", 10); 17909a5557fdSlucy wang - Sun Microsystems - Beijing China miocack(q, mp, 10, 0); 17919a5557fdSlucy wang - Sun Microsystems - Beijing China break; 17929a5557fdSlucy wang - Sun Microsystems - Beijing China 17939a5557fdSlucy wang - Sun Microsystems - Beijing China default: 17949a5557fdSlucy wang - Sun Microsystems - Beijing China cmn_err(CE_WARN, "Netxen ioctl cmd %x not supported\n", cmd); 17959a5557fdSlucy wang - Sun Microsystems - Beijing China 17969a5557fdSlucy wang - Sun Microsystems - Beijing China miocnak(q, mp, 0, EINVAL); 17979a5557fdSlucy wang - Sun Microsystems - Beijing China break; 17989a5557fdSlucy wang - Sun Microsystems - Beijing China } 17999a5557fdSlucy wang - Sun Microsystems - Beijing China } 18009a5557fdSlucy wang - Sun Microsystems - Beijing China 18019a5557fdSlucy wang - Sun Microsystems - Beijing China int 18029a5557fdSlucy wang - Sun Microsystems - Beijing China unm_nic_resume(unm_adapter *adapter) 18039a5557fdSlucy wang - Sun Microsystems - Beijing China { 18049a5557fdSlucy wang - Sun Microsystems - Beijing China 18059a5557fdSlucy wang - Sun Microsystems - Beijing China adapter->watchdog_timer = timeout((void (*)(void *))&unm_watchdog, 18069a5557fdSlucy wang - Sun Microsystems - Beijing China (void *) adapter, 50000); 18079a5557fdSlucy wang - Sun Microsystems - Beijing China 18089a5557fdSlucy wang - Sun Microsystems - Beijing China if (adapter->intr_type == DDI_INTR_TYPE_MSI) 18099a5557fdSlucy wang - Sun Microsystems - Beijing China (void) ddi_intr_block_enable(&adapter->intr_handle, 1); 18109a5557fdSlucy wang - Sun Microsystems - Beijing China else 18119a5557fdSlucy wang - Sun Microsystems - Beijing China (void) ddi_intr_enable(adapter->intr_handle); 18129a5557fdSlucy wang - Sun Microsystems - Beijing China UNM_READ_LOCK(&adapter->adapter_lock); 18139a5557fdSlucy wang - Sun Microsystems - Beijing China unm_nic_enable_int(adapter); 18149a5557fdSlucy wang - Sun Microsystems - Beijing China UNM_READ_UNLOCK(&adapter->adapter_lock); 18159a5557fdSlucy wang - Sun Microsystems - Beijing China 18169a5557fdSlucy wang - Sun Microsystems - Beijing China mac_link_update(adapter->mach, LINK_STATE_UP); 18179a5557fdSlucy wang - Sun Microsystems - Beijing China 18189a5557fdSlucy wang - Sun Microsystems - Beijing China return (DDI_SUCCESS); 18199a5557fdSlucy wang - Sun Microsystems - Beijing China } 18209a5557fdSlucy wang - Sun Microsystems - Beijing China 18219a5557fdSlucy wang - Sun Microsystems - Beijing China int 18229a5557fdSlucy wang - Sun Microsystems - Beijing China unm_nic_suspend(unm_adapter *adapter) 18239a5557fdSlucy wang - Sun Microsystems - Beijing China { 18249a5557fdSlucy wang - Sun Microsystems - Beijing China mac_link_update(adapter->mach, LINK_STATE_DOWN); 18259a5557fdSlucy wang - Sun Microsystems - Beijing China 18269a5557fdSlucy wang - Sun Microsystems - Beijing China (void) untimeout(adapter->watchdog_timer); 18279a5557fdSlucy wang - Sun Microsystems - Beijing China 18289a5557fdSlucy wang - Sun Microsystems - Beijing China UNM_READ_LOCK(&adapter->adapter_lock); 18299a5557fdSlucy wang - Sun Microsystems - Beijing China unm_nic_disable_int(adapter); 18309a5557fdSlucy wang - Sun Microsystems - Beijing China UNM_READ_UNLOCK(&adapter->adapter_lock); 18319a5557fdSlucy wang - Sun Microsystems - Beijing China if (adapter->intr_type == DDI_INTR_TYPE_MSI) 18329a5557fdSlucy wang - Sun Microsystems - Beijing China (void) ddi_intr_block_disable(&adapter->intr_handle, 1); 18339a5557fdSlucy wang - Sun Microsystems - Beijing China else 18349a5557fdSlucy wang - Sun Microsystems - Beijing China (void) ddi_intr_disable(adapter->intr_handle); 18359a5557fdSlucy wang - Sun Microsystems - Beijing China 18369a5557fdSlucy wang - Sun Microsystems - Beijing China return (DDI_SUCCESS); 18379a5557fdSlucy wang - Sun Microsystems - Beijing China } 18389a5557fdSlucy wang - Sun Microsystems - Beijing China 18399a5557fdSlucy wang - Sun Microsystems - Beijing China static int 18409a5557fdSlucy wang - Sun Microsystems - Beijing China unm_nic_do_ioctl(unm_adapter *adapter, queue_t *wq, mblk_t *mp) 18419a5557fdSlucy wang - Sun Microsystems - Beijing China { 18429a5557fdSlucy wang - Sun Microsystems - Beijing China unm_nic_ioctl_data_t data; 18439a5557fdSlucy wang - Sun Microsystems - Beijing China struct unm_nic_ioctl_data *up_data; 18449a5557fdSlucy wang - Sun Microsystems - Beijing China ddi_acc_handle_t conf_handle; 18459a5557fdSlucy wang - Sun Microsystems - Beijing China int retval = 0; 1846dda0720aSjing xiong ERI-SUN uint64_t efuse_chip_id = 0; 18479a5557fdSlucy wang - Sun Microsystems - Beijing China char *ptr1; 18489a5557fdSlucy wang - Sun Microsystems - Beijing China short *ptr2; 18499a5557fdSlucy wang - Sun Microsystems - Beijing China int *ptr4; 18509a5557fdSlucy wang - Sun Microsystems - Beijing China 18519a5557fdSlucy wang - Sun Microsystems - Beijing China up_data = (struct unm_nic_ioctl_data *)(mp->b_cont->b_rptr); 18529a5557fdSlucy wang - Sun Microsystems - Beijing China (void) memcpy(&data, (void **)(uintptr_t)(mp->b_cont->b_rptr), 18539a5557fdSlucy wang - Sun Microsystems - Beijing China sizeof (data)); 18549a5557fdSlucy wang - Sun Microsystems - Beijing China 18559a5557fdSlucy wang - Sun Microsystems - Beijing China /* Shouldn't access beyond legal limits of "char u[64];" member */ 18569a5557fdSlucy wang - Sun Microsystems - Beijing China if (data.size > sizeof (data.uabc)) { 18579a5557fdSlucy wang - Sun Microsystems - Beijing China /* evil user tried to crash the kernel */ 18589a5557fdSlucy wang - Sun Microsystems - Beijing China cmn_err(CE_WARN, "bad size: %d\n", data.size); 18599a5557fdSlucy wang - Sun Microsystems - Beijing China retval = GLD_BADARG; 18609a5557fdSlucy wang - Sun Microsystems - Beijing China goto error_out; 18619a5557fdSlucy wang - Sun Microsystems - Beijing China } 18629a5557fdSlucy wang - Sun Microsystems - Beijing China 18639a5557fdSlucy wang - Sun Microsystems - Beijing China switch (data.cmd) { 18649a5557fdSlucy wang - Sun Microsystems - Beijing China case unm_nic_cmd_pci_read: 18659a5557fdSlucy wang - Sun Microsystems - Beijing China 18669a5557fdSlucy wang - Sun Microsystems - Beijing China if ((retval = adapter->unm_nic_hw_read_ioctl(adapter, 18679a5557fdSlucy wang - Sun Microsystems - Beijing China data.off, up_data, data.size))) { 18689a5557fdSlucy wang - Sun Microsystems - Beijing China DPRINTF(-1, (CE_WARN, "%s(%d) unm_nic_hw_read_wx " 18699a5557fdSlucy wang - Sun Microsystems - Beijing China "returned %d\n", __FUNCTION__, __LINE__, retval)); 18709a5557fdSlucy wang - Sun Microsystems - Beijing China 18719a5557fdSlucy wang - Sun Microsystems - Beijing China retval = data.rv; 18729a5557fdSlucy wang - Sun Microsystems - Beijing China goto error_out; 18739a5557fdSlucy wang - Sun Microsystems - Beijing China } 18749a5557fdSlucy wang - Sun Microsystems - Beijing China 18759a5557fdSlucy wang - Sun Microsystems - Beijing China data.rv = 0; 18769a5557fdSlucy wang - Sun Microsystems - Beijing China break; 18779a5557fdSlucy wang - Sun Microsystems - Beijing China 18789a5557fdSlucy wang - Sun Microsystems - Beijing China case unm_nic_cmd_pci_write: 18799a5557fdSlucy wang - Sun Microsystems - Beijing China if ((data.rv = adapter->unm_nic_hw_write_ioctl(adapter, 18809a5557fdSlucy wang - Sun Microsystems - Beijing China data.off, &(data.uabc), data.size))) { 18819a5557fdSlucy wang - Sun Microsystems - Beijing China DPRINTF(-1, (CE_WARN, "%s(%d) unm_nic_hw_write_wx " 18829a5557fdSlucy wang - Sun Microsystems - Beijing China "returned %d\n", __FUNCTION__, 18839a5557fdSlucy wang - Sun Microsystems - Beijing China __LINE__, data.rv)); 18849a5557fdSlucy wang - Sun Microsystems - Beijing China retval = data.rv; 18859a5557fdSlucy wang - Sun Microsystems - Beijing China goto error_out; 18869a5557fdSlucy wang - Sun Microsystems - Beijing China } 18879a5557fdSlucy wang - Sun Microsystems - Beijing China data.size = 0; 18889a5557fdSlucy wang - Sun Microsystems - Beijing China break; 18899a5557fdSlucy wang - Sun Microsystems - Beijing China 18909a5557fdSlucy wang - Sun Microsystems - Beijing China case unm_nic_cmd_pci_mem_read: 18919a5557fdSlucy wang - Sun Microsystems - Beijing China if ((data.rv = adapter->unm_nic_pci_mem_read(adapter, 18929a5557fdSlucy wang - Sun Microsystems - Beijing China data.off, up_data, data.size))) { 18939a5557fdSlucy wang - Sun Microsystems - Beijing China DPRINTF(-1, (CE_WARN, "%s(%d) unm_nic_pci_mem_read " 18949a5557fdSlucy wang - Sun Microsystems - Beijing China "returned %d\n", __FUNCTION__, 18959a5557fdSlucy wang - Sun Microsystems - Beijing China __LINE__, data.rv)); 18969a5557fdSlucy wang - Sun Microsystems - Beijing China retval = data.rv; 18979a5557fdSlucy wang - Sun Microsystems - Beijing China goto error_out; 18989a5557fdSlucy wang - Sun Microsystems - Beijing China } 18999a5557fdSlucy wang - Sun Microsystems - Beijing China data.rv = 0; 19009a5557fdSlucy wang - Sun Microsystems - Beijing China break; 19019a5557fdSlucy wang - Sun Microsystems - Beijing China 19029a5557fdSlucy wang - Sun Microsystems - Beijing China case unm_nic_cmd_pci_mem_write: 19039a5557fdSlucy wang - Sun Microsystems - Beijing China if ((data.rv = adapter->unm_nic_pci_mem_write(adapter, 19049a5557fdSlucy wang - Sun Microsystems - Beijing China data.off, &(data.uabc), data.size))) { 19059a5557fdSlucy wang - Sun Microsystems - Beijing China DPRINTF(-1, (CE_WARN, 19069a5557fdSlucy wang - Sun Microsystems - Beijing China "%s(%d) unm_nic_cmd_pci_mem_write " 19079a5557fdSlucy wang - Sun Microsystems - Beijing China "returned %d\n", 19089a5557fdSlucy wang - Sun Microsystems - Beijing China __FUNCTION__, __LINE__, data.rv)); 19099a5557fdSlucy wang - Sun Microsystems - Beijing China retval = data.rv; 19109a5557fdSlucy wang - Sun Microsystems - Beijing China goto error_out; 19119a5557fdSlucy wang - Sun Microsystems - Beijing China } 19129a5557fdSlucy wang - Sun Microsystems - Beijing China 19139a5557fdSlucy wang - Sun Microsystems - Beijing China data.size = 0; 19149a5557fdSlucy wang - Sun Microsystems - Beijing China data.rv = 0; 19159a5557fdSlucy wang - Sun Microsystems - Beijing China break; 19169a5557fdSlucy wang - Sun Microsystems - Beijing China 19179a5557fdSlucy wang - Sun Microsystems - Beijing China case unm_nic_cmd_pci_config_read: 19189a5557fdSlucy wang - Sun Microsystems - Beijing China 19199a5557fdSlucy wang - Sun Microsystems - Beijing China if (adapter->pci_cfg_handle != NULL) { 19209a5557fdSlucy wang - Sun Microsystems - Beijing China conf_handle = adapter->pci_cfg_handle; 19219a5557fdSlucy wang - Sun Microsystems - Beijing China 19229a5557fdSlucy wang - Sun Microsystems - Beijing China } else if ((retval = pci_config_setup(adapter->dip, 19239a5557fdSlucy wang - Sun Microsystems - Beijing China &conf_handle)) != DDI_SUCCESS) { 19249a5557fdSlucy wang - Sun Microsystems - Beijing China DPRINTF(-1, (CE_WARN, "!%s: pci_config_setup failed" 19259a5557fdSlucy wang - Sun Microsystems - Beijing China " error:%d\n", unm_nic_driver_name, retval)); 19269a5557fdSlucy wang - Sun Microsystems - Beijing China goto error_out; 19279a5557fdSlucy wang - Sun Microsystems - Beijing China 19289a5557fdSlucy wang - Sun Microsystems - Beijing China } else 19299a5557fdSlucy wang - Sun Microsystems - Beijing China adapter->pci_cfg_handle = conf_handle; 19309a5557fdSlucy wang - Sun Microsystems - Beijing China 19319a5557fdSlucy wang - Sun Microsystems - Beijing China switch (data.size) { 19329a5557fdSlucy wang - Sun Microsystems - Beijing China case 1: 19339a5557fdSlucy wang - Sun Microsystems - Beijing China ptr1 = (char *)up_data; 19349a5557fdSlucy wang - Sun Microsystems - Beijing China *ptr1 = (char)pci_config_get8(conf_handle, data.off); 19359a5557fdSlucy wang - Sun Microsystems - Beijing China break; 19369a5557fdSlucy wang - Sun Microsystems - Beijing China case 2: 19379a5557fdSlucy wang - Sun Microsystems - Beijing China ptr2 = (short *)up_data; 19389a5557fdSlucy wang - Sun Microsystems - Beijing China *ptr2 = (short)pci_config_get16(conf_handle, data.off); 19399a5557fdSlucy wang - Sun Microsystems - Beijing China break; 19409a5557fdSlucy wang - Sun Microsystems - Beijing China case 4: 19419a5557fdSlucy wang - Sun Microsystems - Beijing China ptr4 = (int *)up_data; 19429a5557fdSlucy wang - Sun Microsystems - Beijing China *ptr4 = (int)pci_config_get32(conf_handle, data.off); 19439a5557fdSlucy wang - Sun Microsystems - Beijing China break; 19449a5557fdSlucy wang - Sun Microsystems - Beijing China } 19459a5557fdSlucy wang - Sun Microsystems - Beijing China 19469a5557fdSlucy wang - Sun Microsystems - Beijing China break; 19479a5557fdSlucy wang - Sun Microsystems - Beijing China 19489a5557fdSlucy wang - Sun Microsystems - Beijing China case unm_nic_cmd_pci_config_write: 19499a5557fdSlucy wang - Sun Microsystems - Beijing China 19509a5557fdSlucy wang - Sun Microsystems - Beijing China if (adapter->pci_cfg_handle != NULL) { 19519a5557fdSlucy wang - Sun Microsystems - Beijing China conf_handle = adapter->pci_cfg_handle; 19529a5557fdSlucy wang - Sun Microsystems - Beijing China } else if ((retval = pci_config_setup(adapter->dip, 19539a5557fdSlucy wang - Sun Microsystems - Beijing China &conf_handle)) != DDI_SUCCESS) { 19549a5557fdSlucy wang - Sun Microsystems - Beijing China DPRINTF(-1, (CE_WARN, "!%s: pci_config_setup failed" 19559a5557fdSlucy wang - Sun Microsystems - Beijing China " error:%d\n", unm_nic_driver_name, retval)); 19569a5557fdSlucy wang - Sun Microsystems - Beijing China goto error_out; 19579a5557fdSlucy wang - Sun Microsystems - Beijing China } else { 19589a5557fdSlucy wang - Sun Microsystems - Beijing China adapter->pci_cfg_handle = conf_handle; 19599a5557fdSlucy wang - Sun Microsystems - Beijing China } 19609a5557fdSlucy wang - Sun Microsystems - Beijing China 19619a5557fdSlucy wang - Sun Microsystems - Beijing China switch (data.size) { 19629a5557fdSlucy wang - Sun Microsystems - Beijing China case 1: 19639a5557fdSlucy wang - Sun Microsystems - Beijing China pci_config_put8(conf_handle, 19649a5557fdSlucy wang - Sun Microsystems - Beijing China data.off, *(char *)&(data.uabc)); 19659a5557fdSlucy wang - Sun Microsystems - Beijing China break; 19669a5557fdSlucy wang - Sun Microsystems - Beijing China case 2: 19679a5557fdSlucy wang - Sun Microsystems - Beijing China pci_config_put16(conf_handle, 19689a5557fdSlucy wang - Sun Microsystems - Beijing China data.off, *(short *)(uintptr_t)&(data.uabc)); 19699a5557fdSlucy wang - Sun Microsystems - Beijing China break; 19709a5557fdSlucy wang - Sun Microsystems - Beijing China case 4: 19719a5557fdSlucy wang - Sun Microsystems - Beijing China pci_config_put32(conf_handle, 19729a5557fdSlucy wang - Sun Microsystems - Beijing China data.off, *(u32 *)(uintptr_t)&(data.uabc)); 19739a5557fdSlucy wang - Sun Microsystems - Beijing China break; 19749a5557fdSlucy wang - Sun Microsystems - Beijing China } 19759a5557fdSlucy wang - Sun Microsystems - Beijing China data.size = 0; 19769a5557fdSlucy wang - Sun Microsystems - Beijing China break; 19779a5557fdSlucy wang - Sun Microsystems - Beijing China 19789a5557fdSlucy wang - Sun Microsystems - Beijing China case unm_nic_cmd_get_stats: 19799a5557fdSlucy wang - Sun Microsystems - Beijing China data.rv = adapter->unm_nic_fill_statistics(adapter, 19809a5557fdSlucy wang - Sun Microsystems - Beijing China (struct unm_statistics *)up_data); 19819a5557fdSlucy wang - Sun Microsystems - Beijing China data.size = sizeof (struct unm_statistics); 19829a5557fdSlucy wang - Sun Microsystems - Beijing China 19839a5557fdSlucy wang - Sun Microsystems - Beijing China break; 19849a5557fdSlucy wang - Sun Microsystems - Beijing China 19859a5557fdSlucy wang - Sun Microsystems - Beijing China case unm_nic_cmd_clear_stats: 19869a5557fdSlucy wang - Sun Microsystems - Beijing China data.rv = adapter->unm_nic_clear_statistics(adapter); 19879a5557fdSlucy wang - Sun Microsystems - Beijing China break; 19889a5557fdSlucy wang - Sun Microsystems - Beijing China 19899a5557fdSlucy wang - Sun Microsystems - Beijing China case unm_nic_cmd_get_version: 19909a5557fdSlucy wang - Sun Microsystems - Beijing China (void) memcpy(up_data, UNM_NIC_VERSIONID, 19919a5557fdSlucy wang - Sun Microsystems - Beijing China sizeof (UNM_NIC_VERSIONID)); 19929a5557fdSlucy wang - Sun Microsystems - Beijing China data.size = sizeof (UNM_NIC_VERSIONID); 19939a5557fdSlucy wang - Sun Microsystems - Beijing China 19949a5557fdSlucy wang - Sun Microsystems - Beijing China break; 19959a5557fdSlucy wang - Sun Microsystems - Beijing China 19969a5557fdSlucy wang - Sun Microsystems - Beijing China case unm_nic_cmd_get_phy_type: 19979a5557fdSlucy wang - Sun Microsystems - Beijing China cmn_err(CE_WARN, "unm_nic_cmd_get_phy_type unimplemented\n"); 19989a5557fdSlucy wang - Sun Microsystems - Beijing China break; 19999a5557fdSlucy wang - Sun Microsystems - Beijing China 20009a5557fdSlucy wang - Sun Microsystems - Beijing China case unm_nic_cmd_efuse_chip_id: 20019a5557fdSlucy wang - Sun Microsystems - Beijing China efuse_chip_id = adapter->unm_nic_pci_read_normalize(adapter, 2002dda0720aSjing xiong ERI-SUN UNM_EFUSE_CHIP_ID_HIGH); 2003dda0720aSjing xiong ERI-SUN efuse_chip_id <<= 32; 2004dda0720aSjing xiong ERI-SUN efuse_chip_id |= adapter->unm_nic_pci_read_normalize(adapter, 2005dda0720aSjing xiong ERI-SUN UNM_EFUSE_CHIP_ID_LOW); 2006dda0720aSjing xiong ERI-SUN (void) memcpy(up_data, &efuse_chip_id, sizeof (uint64_t)); 20079a5557fdSlucy wang - Sun Microsystems - Beijing China data.rv = 0; 20089a5557fdSlucy wang - Sun Microsystems - Beijing China break; 20099a5557fdSlucy wang - Sun Microsystems - Beijing China 20109a5557fdSlucy wang - Sun Microsystems - Beijing China default: 20119a5557fdSlucy wang - Sun Microsystems - Beijing China cmn_err(CE_WARN, "%s%d: bad command %d\n", adapter->name, 20129a5557fdSlucy wang - Sun Microsystems - Beijing China adapter->instance, data.cmd); 20139a5557fdSlucy wang - Sun Microsystems - Beijing China data.rv = GLD_NOTSUPPORTED; 20149a5557fdSlucy wang - Sun Microsystems - Beijing China data.size = 0; 20159a5557fdSlucy wang - Sun Microsystems - Beijing China goto error_out; 20169a5557fdSlucy wang - Sun Microsystems - Beijing China } 20179a5557fdSlucy wang - Sun Microsystems - Beijing China 20189a5557fdSlucy wang - Sun Microsystems - Beijing China work_done: 20199a5557fdSlucy wang - Sun Microsystems - Beijing China miocack(wq, mp, data.size, data.rv); 20209a5557fdSlucy wang - Sun Microsystems - Beijing China return (DDI_SUCCESS); 20219a5557fdSlucy wang - Sun Microsystems - Beijing China 20229a5557fdSlucy wang - Sun Microsystems - Beijing China error_out: 20239a5557fdSlucy wang - Sun Microsystems - Beijing China cmn_err(CE_WARN, "%s(%d) ioctl error\n", __FUNCTION__, data.cmd); 20249a5557fdSlucy wang - Sun Microsystems - Beijing China miocnak(wq, mp, 0, EINVAL); 20259a5557fdSlucy wang - Sun Microsystems - Beijing China return (retval); 20269a5557fdSlucy wang - Sun Microsystems - Beijing China } 20279a5557fdSlucy wang - Sun Microsystems - Beijing China 20289a5557fdSlucy wang - Sun Microsystems - Beijing China /* 20299a5557fdSlucy wang - Sun Microsystems - Beijing China * Local datatype for defining tables of (Offset, Name) pairs 20309a5557fdSlucy wang - Sun Microsystems - Beijing China */ 20319a5557fdSlucy wang - Sun Microsystems - Beijing China typedef struct { 20329a5557fdSlucy wang - Sun Microsystems - Beijing China offset_t index; 20339a5557fdSlucy wang - Sun Microsystems - Beijing China char *name; 20349a5557fdSlucy wang - Sun Microsystems - Beijing China } unm_ksindex_t; 20359a5557fdSlucy wang - Sun Microsystems - Beijing China 20369a5557fdSlucy wang - Sun Microsystems - Beijing China static const unm_ksindex_t unm_kstat[] = { 20379a5557fdSlucy wang - Sun Microsystems - Beijing China { 0, "freehdls" }, 20389a5557fdSlucy wang - Sun Microsystems - Beijing China { 1, "freecmds" }, 20399a5557fdSlucy wang - Sun Microsystems - Beijing China { 2, "tx_bcopy_threshold" }, 20409a5557fdSlucy wang - Sun Microsystems - Beijing China { 3, "rx_bcopy_threshold" }, 20419a5557fdSlucy wang - Sun Microsystems - Beijing China { 4, "xmitcalled" }, 20429a5557fdSlucy wang - Sun Microsystems - Beijing China { 5, "xmitedframes" }, 20439a5557fdSlucy wang - Sun Microsystems - Beijing China { 6, "xmitfinished" }, 20449a5557fdSlucy wang - Sun Microsystems - Beijing China { 7, "txbytes" }, 20459a5557fdSlucy wang - Sun Microsystems - Beijing China { 8, "txcopyed" }, 20469a5557fdSlucy wang - Sun Microsystems - Beijing China { 9, "txmapped" }, 20479a5557fdSlucy wang - Sun Microsystems - Beijing China { 10, "outoftxdmahdl" }, 20489a5557fdSlucy wang - Sun Microsystems - Beijing China { 11, "outofcmddesc" }, 20499a5557fdSlucy wang - Sun Microsystems - Beijing China { 12, "txdropped" }, 20509a5557fdSlucy wang - Sun Microsystems - Beijing China { 13, "polled" }, 20519a5557fdSlucy wang - Sun Microsystems - Beijing China { 14, "uphappy" }, 20529a5557fdSlucy wang - Sun Microsystems - Beijing China { 15, "updropped" }, 20539a5557fdSlucy wang - Sun Microsystems - Beijing China { 16, "csummed" }, 20549a5557fdSlucy wang - Sun Microsystems - Beijing China { 17, "no_rcv" }, 20559a5557fdSlucy wang - Sun Microsystems - Beijing China { 18, "rxbytes" }, 20569a5557fdSlucy wang - Sun Microsystems - Beijing China { 19, "rxcopyed" }, 20579a5557fdSlucy wang - Sun Microsystems - Beijing China { 20, "rxmapped" }, 20589a5557fdSlucy wang - Sun Microsystems - Beijing China { 21, "desballocfailed" }, 20599a5557fdSlucy wang - Sun Microsystems - Beijing China { 22, "outofrxbuf" }, 20609a5557fdSlucy wang - Sun Microsystems - Beijing China { 23, "promiscmode" }, 20619a5557fdSlucy wang - Sun Microsystems - Beijing China { 24, "rxbufshort" }, 20629a5557fdSlucy wang - Sun Microsystems - Beijing China { 25, "allocbfailed" }, 20639a5557fdSlucy wang - Sun Microsystems - Beijing China { -1, NULL } 20649a5557fdSlucy wang - Sun Microsystems - Beijing China }; 20659a5557fdSlucy wang - Sun Microsystems - Beijing China 20669a5557fdSlucy wang - Sun Microsystems - Beijing China static int 20679a5557fdSlucy wang - Sun Microsystems - Beijing China unm_kstat_update(kstat_t *ksp, int flag) 20689a5557fdSlucy wang - Sun Microsystems - Beijing China { 20699a5557fdSlucy wang - Sun Microsystems - Beijing China unm_adapter *adapter; 20709a5557fdSlucy wang - Sun Microsystems - Beijing China kstat_named_t *knp; 20719a5557fdSlucy wang - Sun Microsystems - Beijing China 20729a5557fdSlucy wang - Sun Microsystems - Beijing China if (flag != KSTAT_READ) 20739a5557fdSlucy wang - Sun Microsystems - Beijing China return (EACCES); 20749a5557fdSlucy wang - Sun Microsystems - Beijing China 20759a5557fdSlucy wang - Sun Microsystems - Beijing China adapter = ksp->ks_private; 20769a5557fdSlucy wang - Sun Microsystems - Beijing China knp = ksp->ks_data; 20779a5557fdSlucy wang - Sun Microsystems - Beijing China 20789a5557fdSlucy wang - Sun Microsystems - Beijing China (knp++)->value.ui32 = adapter->freehdls; 20799a5557fdSlucy wang - Sun Microsystems - Beijing China (knp++)->value.ui64 = adapter->freecmds; 20809a5557fdSlucy wang - Sun Microsystems - Beijing China (knp++)->value.ui64 = adapter->tx_bcopy_threshold; 20819a5557fdSlucy wang - Sun Microsystems - Beijing China (knp++)->value.ui64 = adapter->rx_bcopy_threshold; 20829a5557fdSlucy wang - Sun Microsystems - Beijing China 20839a5557fdSlucy wang - Sun Microsystems - Beijing China (knp++)->value.ui64 = adapter->stats.xmitcalled; 20849a5557fdSlucy wang - Sun Microsystems - Beijing China (knp++)->value.ui64 = adapter->stats.xmitedframes; 20859a5557fdSlucy wang - Sun Microsystems - Beijing China (knp++)->value.ui64 = adapter->stats.xmitfinished; 20869a5557fdSlucy wang - Sun Microsystems - Beijing China (knp++)->value.ui64 = adapter->stats.txbytes; 20879a5557fdSlucy wang - Sun Microsystems - Beijing China (knp++)->value.ui64 = adapter->stats.txcopyed; 20889a5557fdSlucy wang - Sun Microsystems - Beijing China (knp++)->value.ui64 = adapter->stats.txmapped; 20899a5557fdSlucy wang - Sun Microsystems - Beijing China (knp++)->value.ui64 = adapter->stats.outoftxdmahdl; 20909a5557fdSlucy wang - Sun Microsystems - Beijing China (knp++)->value.ui64 = adapter->stats.outofcmddesc; 20919a5557fdSlucy wang - Sun Microsystems - Beijing China (knp++)->value.ui64 = adapter->stats.txdropped; 20929a5557fdSlucy wang - Sun Microsystems - Beijing China (knp++)->value.ui64 = adapter->stats.polled; 20939a5557fdSlucy wang - Sun Microsystems - Beijing China (knp++)->value.ui64 = adapter->stats.uphappy; 20949a5557fdSlucy wang - Sun Microsystems - Beijing China (knp++)->value.ui64 = adapter->stats.updropped; 20959a5557fdSlucy wang - Sun Microsystems - Beijing China (knp++)->value.ui64 = adapter->stats.csummed; 20969a5557fdSlucy wang - Sun Microsystems - Beijing China (knp++)->value.ui64 = adapter->stats.no_rcv; 20979a5557fdSlucy wang - Sun Microsystems - Beijing China (knp++)->value.ui64 = adapter->stats.rxbytes; 20989a5557fdSlucy wang - Sun Microsystems - Beijing China (knp++)->value.ui64 = adapter->stats.rxcopyed; 20999a5557fdSlucy wang - Sun Microsystems - Beijing China (knp++)->value.ui64 = adapter->stats.rxmapped; 21009a5557fdSlucy wang - Sun Microsystems - Beijing China (knp++)->value.ui64 = adapter->stats.desballocfailed; 21019a5557fdSlucy wang - Sun Microsystems - Beijing China (knp++)->value.ui64 = adapter->stats.outofrxbuf; 21029a5557fdSlucy wang - Sun Microsystems - Beijing China (knp++)->value.ui64 = adapter->stats.promiscmode; 21039a5557fdSlucy wang - Sun Microsystems - Beijing China (knp++)->value.ui64 = adapter->stats.rxbufshort; 21049a5557fdSlucy wang - Sun Microsystems - Beijing China (knp++)->value.ui64 = adapter->stats.allocbfailed; 21059a5557fdSlucy wang - Sun Microsystems - Beijing China 21069a5557fdSlucy wang - Sun Microsystems - Beijing China return (0); 21079a5557fdSlucy wang - Sun Microsystems - Beijing China } 21089a5557fdSlucy wang - Sun Microsystems - Beijing China 21099a5557fdSlucy wang - Sun Microsystems - Beijing China static kstat_t * 21109a5557fdSlucy wang - Sun Microsystems - Beijing China unm_setup_named_kstat(unm_adapter *adapter, int instance, char *name, 21119a5557fdSlucy wang - Sun Microsystems - Beijing China const unm_ksindex_t *ksip, size_t size, int (*update)(kstat_t *, int)) 21129a5557fdSlucy wang - Sun Microsystems - Beijing China { 21139a5557fdSlucy wang - Sun Microsystems - Beijing China kstat_t *ksp; 21149a5557fdSlucy wang - Sun Microsystems - Beijing China kstat_named_t *knp; 21159a5557fdSlucy wang - Sun Microsystems - Beijing China char *np; 21169a5557fdSlucy wang - Sun Microsystems - Beijing China int type; 21179a5557fdSlucy wang - Sun Microsystems - Beijing China int count = 0; 21189a5557fdSlucy wang - Sun Microsystems - Beijing China 21199a5557fdSlucy wang - Sun Microsystems - Beijing China size /= sizeof (unm_ksindex_t); 21209a5557fdSlucy wang - Sun Microsystems - Beijing China ksp = kstat_create(unm_nic_driver_name, instance, name, "net", 21219a5557fdSlucy wang - Sun Microsystems - Beijing China KSTAT_TYPE_NAMED, size-1, KSTAT_FLAG_PERSISTENT); 21229a5557fdSlucy wang - Sun Microsystems - Beijing China if (ksp == NULL) 21239a5557fdSlucy wang - Sun Microsystems - Beijing China return (NULL); 21249a5557fdSlucy wang - Sun Microsystems - Beijing China 21259a5557fdSlucy wang - Sun Microsystems - Beijing China ksp->ks_private = adapter; 21269a5557fdSlucy wang - Sun Microsystems - Beijing China ksp->ks_update = update; 21279a5557fdSlucy wang - Sun Microsystems - Beijing China for (knp = ksp->ks_data; (np = ksip->name) != NULL; ++knp, ++ksip) { 21289a5557fdSlucy wang - Sun Microsystems - Beijing China count++; 21299a5557fdSlucy wang - Sun Microsystems - Beijing China switch (*np) { 21309a5557fdSlucy wang - Sun Microsystems - Beijing China default: 21319a5557fdSlucy wang - Sun Microsystems - Beijing China type = KSTAT_DATA_UINT64; 21329a5557fdSlucy wang - Sun Microsystems - Beijing China break; 21339a5557fdSlucy wang - Sun Microsystems - Beijing China case '%': 21349a5557fdSlucy wang - Sun Microsystems - Beijing China np += 1; 21359a5557fdSlucy wang - Sun Microsystems - Beijing China type = KSTAT_DATA_UINT32; 21369a5557fdSlucy wang - Sun Microsystems - Beijing China break; 21379a5557fdSlucy wang - Sun Microsystems - Beijing China case '$': 21389a5557fdSlucy wang - Sun Microsystems - Beijing China np += 1; 21399a5557fdSlucy wang - Sun Microsystems - Beijing China type = KSTAT_DATA_STRING; 21409a5557fdSlucy wang - Sun Microsystems - Beijing China break; 21419a5557fdSlucy wang - Sun Microsystems - Beijing China case '&': 21429a5557fdSlucy wang - Sun Microsystems - Beijing China np += 1; 21439a5557fdSlucy wang - Sun Microsystems - Beijing China type = KSTAT_DATA_CHAR; 21449a5557fdSlucy wang - Sun Microsystems - Beijing China break; 21459a5557fdSlucy wang - Sun Microsystems - Beijing China } 21469a5557fdSlucy wang - Sun Microsystems - Beijing China kstat_named_init(knp, np, type); 21479a5557fdSlucy wang - Sun Microsystems - Beijing China } 21489a5557fdSlucy wang - Sun Microsystems - Beijing China kstat_install(ksp); 21499a5557fdSlucy wang - Sun Microsystems - Beijing China 21509a5557fdSlucy wang - Sun Microsystems - Beijing China return (ksp); 21519a5557fdSlucy wang - Sun Microsystems - Beijing China } 21529a5557fdSlucy wang - Sun Microsystems - Beijing China 21539a5557fdSlucy wang - Sun Microsystems - Beijing China void 21549a5557fdSlucy wang - Sun Microsystems - Beijing China unm_init_kstats(unm_adapter* adapter, int instance) 21559a5557fdSlucy wang - Sun Microsystems - Beijing China { 21569a5557fdSlucy wang - Sun Microsystems - Beijing China adapter->kstats[0] = unm_setup_named_kstat(adapter, 21579a5557fdSlucy wang - Sun Microsystems - Beijing China instance, "kstatinfo", unm_kstat, 21589a5557fdSlucy wang - Sun Microsystems - Beijing China sizeof (unm_kstat), unm_kstat_update); 21599a5557fdSlucy wang - Sun Microsystems - Beijing China } 21609a5557fdSlucy wang - Sun Microsystems - Beijing China 21619a5557fdSlucy wang - Sun Microsystems - Beijing China void 21629a5557fdSlucy wang - Sun Microsystems - Beijing China unm_fini_kstats(unm_adapter* adapter) 21639a5557fdSlucy wang - Sun Microsystems - Beijing China { 21649a5557fdSlucy wang - Sun Microsystems - Beijing China 21659a5557fdSlucy wang - Sun Microsystems - Beijing China if (adapter->kstats[0] != NULL) { 21669a5557fdSlucy wang - Sun Microsystems - Beijing China kstat_delete(adapter->kstats[0]); 21679a5557fdSlucy wang - Sun Microsystems - Beijing China adapter->kstats[0] = NULL; 21689a5557fdSlucy wang - Sun Microsystems - Beijing China } 21699a5557fdSlucy wang - Sun Microsystems - Beijing China } 21709a5557fdSlucy wang - Sun Microsystems - Beijing China 21719a5557fdSlucy wang - Sun Microsystems - Beijing China static int 21729a5557fdSlucy wang - Sun Microsystems - Beijing China unm_nic_set_pauseparam(unm_adapter *adapter, unm_pauseparam_t *pause) 21739a5557fdSlucy wang - Sun Microsystems - Beijing China { 21749a5557fdSlucy wang - Sun Microsystems - Beijing China int ret = 0; 21759a5557fdSlucy wang - Sun Microsystems - Beijing China 21769a5557fdSlucy wang - Sun Microsystems - Beijing China if (adapter->ahw.board_type == UNM_NIC_GBE) { 21779a5557fdSlucy wang - Sun Microsystems - Beijing China if (unm_niu_gbe_set_rx_flow_ctl(adapter, pause->rx_pause)) 21789a5557fdSlucy wang - Sun Microsystems - Beijing China ret = -EIO; 21799a5557fdSlucy wang - Sun Microsystems - Beijing China 21809a5557fdSlucy wang - Sun Microsystems - Beijing China if (unm_niu_gbe_set_tx_flow_ctl(adapter, pause->tx_pause)) 21819a5557fdSlucy wang - Sun Microsystems - Beijing China ret = -EIO; 21829a5557fdSlucy wang - Sun Microsystems - Beijing China 21839a5557fdSlucy wang - Sun Microsystems - Beijing China } else if (adapter->ahw.board_type == UNM_NIC_XGBE) { 21849a5557fdSlucy wang - Sun Microsystems - Beijing China if (unm_niu_xg_set_tx_flow_ctl(adapter, pause->tx_pause)) 21859a5557fdSlucy wang - Sun Microsystems - Beijing China ret = -EIO; 21869a5557fdSlucy wang - Sun Microsystems - Beijing China } else 21879a5557fdSlucy wang - Sun Microsystems - Beijing China ret = -EIO; 21889a5557fdSlucy wang - Sun Microsystems - Beijing China 21899a5557fdSlucy wang - Sun Microsystems - Beijing China return (ret); 21909a5557fdSlucy wang - Sun Microsystems - Beijing China } 21919a5557fdSlucy wang - Sun Microsystems - Beijing China 21929a5557fdSlucy wang - Sun Microsystems - Beijing China /* 21939a5557fdSlucy wang - Sun Microsystems - Beijing China * GLD/MAC interfaces 21949a5557fdSlucy wang - Sun Microsystems - Beijing China */ 21959a5557fdSlucy wang - Sun Microsystems - Beijing China static int 21969a5557fdSlucy wang - Sun Microsystems - Beijing China ntxn_m_start(void *arg) 21979a5557fdSlucy wang - Sun Microsystems - Beijing China { 21989a5557fdSlucy wang - Sun Microsystems - Beijing China unm_adapter *adapter = arg; 21999a5557fdSlucy wang - Sun Microsystems - Beijing China int ring; 22009a5557fdSlucy wang - Sun Microsystems - Beijing China 22019a5557fdSlucy wang - Sun Microsystems - Beijing China UNM_SPIN_LOCK(&adapter->lock); 22029a5557fdSlucy wang - Sun Microsystems - Beijing China if (adapter->is_up == UNM_ADAPTER_UP_MAGIC) { 22039a5557fdSlucy wang - Sun Microsystems - Beijing China UNM_SPIN_UNLOCK(&adapter->lock); 22049a5557fdSlucy wang - Sun Microsystems - Beijing China return (DDI_SUCCESS); 22059a5557fdSlucy wang - Sun Microsystems - Beijing China } 22069a5557fdSlucy wang - Sun Microsystems - Beijing China 2207dda0720aSjing xiong ERI-SUN if (create_rxtx_rings(adapter) != DDI_SUCCESS) { 2208dda0720aSjing xiong ERI-SUN UNM_SPIN_UNLOCK(&adapter->lock); 2209dda0720aSjing xiong ERI-SUN return (DDI_FAILURE); 2210dda0720aSjing xiong ERI-SUN } 2211dda0720aSjing xiong ERI-SUN 22129a5557fdSlucy wang - Sun Microsystems - Beijing China if (init_firmware(adapter) != DDI_SUCCESS) { 22139a5557fdSlucy wang - Sun Microsystems - Beijing China UNM_SPIN_UNLOCK(&adapter->lock); 22149a5557fdSlucy wang - Sun Microsystems - Beijing China cmn_err(CE_WARN, "%s%d: Failed to init firmware\n", 22159a5557fdSlucy wang - Sun Microsystems - Beijing China adapter->name, adapter->instance); 2216dda0720aSjing xiong ERI-SUN goto dest_rings; 22179a5557fdSlucy wang - Sun Microsystems - Beijing China } 22189a5557fdSlucy wang - Sun Microsystems - Beijing China 22199a5557fdSlucy wang - Sun Microsystems - Beijing China unm_nic_clear_stats(adapter); 22209a5557fdSlucy wang - Sun Microsystems - Beijing China 22219a5557fdSlucy wang - Sun Microsystems - Beijing China if (unm_nic_hw_resources(adapter) != 0) { 22229a5557fdSlucy wang - Sun Microsystems - Beijing China UNM_SPIN_UNLOCK(&adapter->lock); 22239a5557fdSlucy wang - Sun Microsystems - Beijing China cmn_err(CE_WARN, "%s%d: Error setting hw resources\n", 22249a5557fdSlucy wang - Sun Microsystems - Beijing China adapter->name, adapter->instance); 2225dda0720aSjing xiong ERI-SUN goto dest_rings; 22269a5557fdSlucy wang - Sun Microsystems - Beijing China } 22279a5557fdSlucy wang - Sun Microsystems - Beijing China 22289a5557fdSlucy wang - Sun Microsystems - Beijing China if (adapter->fw_major < 4) { 22299a5557fdSlucy wang - Sun Microsystems - Beijing China adapter->crb_addr_cmd_producer = 22309a5557fdSlucy wang - Sun Microsystems - Beijing China crb_cmd_producer[adapter->portnum]; 22319a5557fdSlucy wang - Sun Microsystems - Beijing China adapter->crb_addr_cmd_consumer = 22329a5557fdSlucy wang - Sun Microsystems - Beijing China crb_cmd_consumer[adapter->portnum]; 22339a5557fdSlucy wang - Sun Microsystems - Beijing China unm_nic_update_cmd_producer(adapter, 0); 22349a5557fdSlucy wang - Sun Microsystems - Beijing China unm_nic_update_cmd_consumer(adapter, 0); 22359a5557fdSlucy wang - Sun Microsystems - Beijing China } 22369a5557fdSlucy wang - Sun Microsystems - Beijing China 22379a5557fdSlucy wang - Sun Microsystems - Beijing China for (ring = 0; ring < adapter->max_rds_rings; ring++) { 22389a5557fdSlucy wang - Sun Microsystems - Beijing China if (unm_post_rx_buffers(adapter, ring) != DDI_SUCCESS) { 22399a5557fdSlucy wang - Sun Microsystems - Beijing China UNM_SPIN_UNLOCK(&adapter->lock); 2240dda0720aSjing xiong ERI-SUN goto free_hw_res; 22419a5557fdSlucy wang - Sun Microsystems - Beijing China } 22429a5557fdSlucy wang - Sun Microsystems - Beijing China } 22439a5557fdSlucy wang - Sun Microsystems - Beijing China 22449a5557fdSlucy wang - Sun Microsystems - Beijing China if (unm_nic_macaddr_set(adapter, adapter->mac_addr) != 0) { 22459a5557fdSlucy wang - Sun Microsystems - Beijing China UNM_SPIN_UNLOCK(&adapter->lock); 22469a5557fdSlucy wang - Sun Microsystems - Beijing China cmn_err(CE_WARN, "%s%d: Could not set mac address\n", 22479a5557fdSlucy wang - Sun Microsystems - Beijing China adapter->name, adapter->instance); 2248dda0720aSjing xiong ERI-SUN goto free_hw_res; 22499a5557fdSlucy wang - Sun Microsystems - Beijing China } 22509a5557fdSlucy wang - Sun Microsystems - Beijing China 22519a5557fdSlucy wang - Sun Microsystems - Beijing China if (unm_nic_init_port(adapter) != 0) { 22529a5557fdSlucy wang - Sun Microsystems - Beijing China UNM_SPIN_UNLOCK(&adapter->lock); 22539a5557fdSlucy wang - Sun Microsystems - Beijing China cmn_err(CE_WARN, "%s%d: Could not initialize port\n", 22549a5557fdSlucy wang - Sun Microsystems - Beijing China adapter->name, adapter->instance); 2255dda0720aSjing xiong ERI-SUN goto free_hw_res; 22569a5557fdSlucy wang - Sun Microsystems - Beijing China } 22579a5557fdSlucy wang - Sun Microsystems - Beijing China 22589a5557fdSlucy wang - Sun Microsystems - Beijing China unm_nic_set_link_parameters(adapter); 22599a5557fdSlucy wang - Sun Microsystems - Beijing China 22609a5557fdSlucy wang - Sun Microsystems - Beijing China /* 22619a5557fdSlucy wang - Sun Microsystems - Beijing China * P2 and P3 should be handled similarly. 22629a5557fdSlucy wang - Sun Microsystems - Beijing China */ 22639a5557fdSlucy wang - Sun Microsystems - Beijing China if (NX_IS_REVISION_P2(adapter->ahw.revision_id)) { 22649a5557fdSlucy wang - Sun Microsystems - Beijing China if (unm_nic_set_promisc_mode(adapter) != 0) { 22659a5557fdSlucy wang - Sun Microsystems - Beijing China UNM_SPIN_UNLOCK(&adapter->lock); 22669a5557fdSlucy wang - Sun Microsystems - Beijing China cmn_err(CE_WARN, "%s%d: Could not set promisc mode\n", 22679a5557fdSlucy wang - Sun Microsystems - Beijing China adapter->name, adapter->instance); 2268dda0720aSjing xiong ERI-SUN goto stop_and_free; 22699a5557fdSlucy wang - Sun Microsystems - Beijing China } 22709a5557fdSlucy wang - Sun Microsystems - Beijing China } else { 22719a5557fdSlucy wang - Sun Microsystems - Beijing China nx_p3_nic_set_multi(adapter); 22729a5557fdSlucy wang - Sun Microsystems - Beijing China } 22739a5557fdSlucy wang - Sun Microsystems - Beijing China adapter->stats.promiscmode = 1; 22749a5557fdSlucy wang - Sun Microsystems - Beijing China 22759a5557fdSlucy wang - Sun Microsystems - Beijing China if (unm_nic_set_mtu(adapter, adapter->mtu) != 0) { 22769a5557fdSlucy wang - Sun Microsystems - Beijing China UNM_SPIN_UNLOCK(&adapter->lock); 22779a5557fdSlucy wang - Sun Microsystems - Beijing China cmn_err(CE_WARN, "%s%d: Could not set mtu\n", 22789a5557fdSlucy wang - Sun Microsystems - Beijing China adapter->name, adapter->instance); 2279dda0720aSjing xiong ERI-SUN goto stop_and_free; 22809a5557fdSlucy wang - Sun Microsystems - Beijing China } 22819a5557fdSlucy wang - Sun Microsystems - Beijing China 22829a5557fdSlucy wang - Sun Microsystems - Beijing China adapter->watchdog_timer = timeout((void (*)(void *))&unm_watchdog, 22839a5557fdSlucy wang - Sun Microsystems - Beijing China (void *)adapter, 0); 22849a5557fdSlucy wang - Sun Microsystems - Beijing China 22859a5557fdSlucy wang - Sun Microsystems - Beijing China adapter->is_up = UNM_ADAPTER_UP_MAGIC; 22869a5557fdSlucy wang - Sun Microsystems - Beijing China 22879a5557fdSlucy wang - Sun Microsystems - Beijing China if (adapter->intr_type == DDI_INTR_TYPE_MSI) 22889a5557fdSlucy wang - Sun Microsystems - Beijing China (void) ddi_intr_block_enable(&adapter->intr_handle, 1); 22899a5557fdSlucy wang - Sun Microsystems - Beijing China else 22909a5557fdSlucy wang - Sun Microsystems - Beijing China (void) ddi_intr_enable(adapter->intr_handle); 22919a5557fdSlucy wang - Sun Microsystems - Beijing China unm_nic_enable_int(adapter); 22929a5557fdSlucy wang - Sun Microsystems - Beijing China 22939a5557fdSlucy wang - Sun Microsystems - Beijing China UNM_SPIN_UNLOCK(&adapter->lock); 22949a5557fdSlucy wang - Sun Microsystems - Beijing China return (GLD_SUCCESS); 2295dda0720aSjing xiong ERI-SUN 2296dda0720aSjing xiong ERI-SUN stop_and_free: 2297dda0720aSjing xiong ERI-SUN unm_nic_stop_port(adapter); 2298dda0720aSjing xiong ERI-SUN free_hw_res: 2299dda0720aSjing xiong ERI-SUN unm_free_hw_resources(adapter); 2300dda0720aSjing xiong ERI-SUN dest_rings: 2301dda0720aSjing xiong ERI-SUN destroy_rxtx_rings(adapter); 2302dda0720aSjing xiong ERI-SUN return (DDI_FAILURE); 23039a5557fdSlucy wang - Sun Microsystems - Beijing China } 23049a5557fdSlucy wang - Sun Microsystems - Beijing China 23059a5557fdSlucy wang - Sun Microsystems - Beijing China 23069a5557fdSlucy wang - Sun Microsystems - Beijing China /* 23079a5557fdSlucy wang - Sun Microsystems - Beijing China * This code is kept here for reference so as to 23089a5557fdSlucy wang - Sun Microsystems - Beijing China * see if something different is required to be done 23099a5557fdSlucy wang - Sun Microsystems - Beijing China * in GLDV3. This will be deleted later. 23109a5557fdSlucy wang - Sun Microsystems - Beijing China */ 23119a5557fdSlucy wang - Sun Microsystems - Beijing China /* ARGSUSED */ 23129a5557fdSlucy wang - Sun Microsystems - Beijing China static void 23139a5557fdSlucy wang - Sun Microsystems - Beijing China ntxn_m_stop(void *arg) 23149a5557fdSlucy wang - Sun Microsystems - Beijing China { 23159a5557fdSlucy wang - Sun Microsystems - Beijing China } 23169a5557fdSlucy wang - Sun Microsystems - Beijing China 23179a5557fdSlucy wang - Sun Microsystems - Beijing China /*ARGSUSED*/ 23189a5557fdSlucy wang - Sun Microsystems - Beijing China static int 23199a5557fdSlucy wang - Sun Microsystems - Beijing China ntxn_m_multicst(void *arg, boolean_t add, const uint8_t *ep) 23209a5557fdSlucy wang - Sun Microsystems - Beijing China { 23219a5557fdSlucy wang - Sun Microsystems - Beijing China /* 23229a5557fdSlucy wang - Sun Microsystems - Beijing China * When we correctly implement this, invoke nx_p3_nic_set_multi() 23239a5557fdSlucy wang - Sun Microsystems - Beijing China * or nx_p2_nic_set_multi() here. 23249a5557fdSlucy wang - Sun Microsystems - Beijing China */ 23259a5557fdSlucy wang - Sun Microsystems - Beijing China return (GLD_SUCCESS); 23269a5557fdSlucy wang - Sun Microsystems - Beijing China } 23279a5557fdSlucy wang - Sun Microsystems - Beijing China 23289a5557fdSlucy wang - Sun Microsystems - Beijing China /*ARGSUSED*/ 23299a5557fdSlucy wang - Sun Microsystems - Beijing China static int 23309a5557fdSlucy wang - Sun Microsystems - Beijing China ntxn_m_promisc(void *arg, boolean_t on) 23319a5557fdSlucy wang - Sun Microsystems - Beijing China { 23329a5557fdSlucy wang - Sun Microsystems - Beijing China #if 0 23339a5557fdSlucy wang - Sun Microsystems - Beijing China int err = 0; 23349a5557fdSlucy wang - Sun Microsystems - Beijing China struct unm_adapter_s *adapter = arg; 23359a5557fdSlucy wang - Sun Microsystems - Beijing China 23369a5557fdSlucy wang - Sun Microsystems - Beijing China err = on ? unm_nic_set_promisc_mode(adapter) : 23379a5557fdSlucy wang - Sun Microsystems - Beijing China unm_nic_unset_promisc_mode(adapter); 23389a5557fdSlucy wang - Sun Microsystems - Beijing China 23399a5557fdSlucy wang - Sun Microsystems - Beijing China if (err) 23409a5557fdSlucy wang - Sun Microsystems - Beijing China return (GLD_FAILURE); 23419a5557fdSlucy wang - Sun Microsystems - Beijing China #endif 23429a5557fdSlucy wang - Sun Microsystems - Beijing China 23439a5557fdSlucy wang - Sun Microsystems - Beijing China return (GLD_SUCCESS); 23449a5557fdSlucy wang - Sun Microsystems - Beijing China } 23459a5557fdSlucy wang - Sun Microsystems - Beijing China 23469a5557fdSlucy wang - Sun Microsystems - Beijing China static int 23479a5557fdSlucy wang - Sun Microsystems - Beijing China ntxn_m_stat(void *arg, uint_t stat, uint64_t *val) 23489a5557fdSlucy wang - Sun Microsystems - Beijing China { 23499a5557fdSlucy wang - Sun Microsystems - Beijing China struct unm_adapter_s *adapter = arg; 23509a5557fdSlucy wang - Sun Microsystems - Beijing China struct unm_adapter_stats *portstat = &adapter->stats; 23519a5557fdSlucy wang - Sun Microsystems - Beijing China 23529a5557fdSlucy wang - Sun Microsystems - Beijing China switch (stat) { 23539a5557fdSlucy wang - Sun Microsystems - Beijing China case MAC_STAT_IFSPEED: 23549a5557fdSlucy wang - Sun Microsystems - Beijing China if (adapter->ahw.board_type == UNM_NIC_XGBE) { 23559a5557fdSlucy wang - Sun Microsystems - Beijing China /* 10 Gigs */ 23569a5557fdSlucy wang - Sun Microsystems - Beijing China *val = 10000000000ULL; 23579a5557fdSlucy wang - Sun Microsystems - Beijing China } else { 23589a5557fdSlucy wang - Sun Microsystems - Beijing China /* 1 Gig */ 23599a5557fdSlucy wang - Sun Microsystems - Beijing China *val = 1000000000; 23609a5557fdSlucy wang - Sun Microsystems - Beijing China } 23619a5557fdSlucy wang - Sun Microsystems - Beijing China break; 23629a5557fdSlucy wang - Sun Microsystems - Beijing China 23639a5557fdSlucy wang - Sun Microsystems - Beijing China case MAC_STAT_MULTIRCV: 23649a5557fdSlucy wang - Sun Microsystems - Beijing China *val = 0; 23659a5557fdSlucy wang - Sun Microsystems - Beijing China break; 23669a5557fdSlucy wang - Sun Microsystems - Beijing China 23679a5557fdSlucy wang - Sun Microsystems - Beijing China case MAC_STAT_BRDCSTRCV: 23689a5557fdSlucy wang - Sun Microsystems - Beijing China case MAC_STAT_BRDCSTXMT: 23699a5557fdSlucy wang - Sun Microsystems - Beijing China *val = 0; 23709a5557fdSlucy wang - Sun Microsystems - Beijing China break; 23719a5557fdSlucy wang - Sun Microsystems - Beijing China 23729a5557fdSlucy wang - Sun Microsystems - Beijing China case MAC_STAT_NORCVBUF: 23739a5557fdSlucy wang - Sun Microsystems - Beijing China *val = portstat->updropped; 23749a5557fdSlucy wang - Sun Microsystems - Beijing China break; 23759a5557fdSlucy wang - Sun Microsystems - Beijing China 23769a5557fdSlucy wang - Sun Microsystems - Beijing China case MAC_STAT_NOXMTBUF: 23779a5557fdSlucy wang - Sun Microsystems - Beijing China *val = portstat->txdropped; 23789a5557fdSlucy wang - Sun Microsystems - Beijing China break; 23799a5557fdSlucy wang - Sun Microsystems - Beijing China 23809a5557fdSlucy wang - Sun Microsystems - Beijing China case MAC_STAT_RBYTES: 23819a5557fdSlucy wang - Sun Microsystems - Beijing China *val = portstat->rxbytes; 23829a5557fdSlucy wang - Sun Microsystems - Beijing China break; 23839a5557fdSlucy wang - Sun Microsystems - Beijing China 23849a5557fdSlucy wang - Sun Microsystems - Beijing China case MAC_STAT_OBYTES: 23859a5557fdSlucy wang - Sun Microsystems - Beijing China *val = portstat->txbytes; 23869a5557fdSlucy wang - Sun Microsystems - Beijing China break; 23879a5557fdSlucy wang - Sun Microsystems - Beijing China 23889a5557fdSlucy wang - Sun Microsystems - Beijing China case MAC_STAT_OPACKETS: 23899a5557fdSlucy wang - Sun Microsystems - Beijing China *val = portstat->xmitedframes; 23909a5557fdSlucy wang - Sun Microsystems - Beijing China break; 23919a5557fdSlucy wang - Sun Microsystems - Beijing China 23929a5557fdSlucy wang - Sun Microsystems - Beijing China case MAC_STAT_IPACKETS: 23939a5557fdSlucy wang - Sun Microsystems - Beijing China *val = portstat->uphappy; 23949a5557fdSlucy wang - Sun Microsystems - Beijing China break; 23959a5557fdSlucy wang - Sun Microsystems - Beijing China 23969a5557fdSlucy wang - Sun Microsystems - Beijing China case MAC_STAT_OERRORS: 23979a5557fdSlucy wang - Sun Microsystems - Beijing China *val = portstat->xmitcalled - portstat->xmitedframes; 23989a5557fdSlucy wang - Sun Microsystems - Beijing China break; 23999a5557fdSlucy wang - Sun Microsystems - Beijing China 24009a5557fdSlucy wang - Sun Microsystems - Beijing China case ETHER_STAT_LINK_DUPLEX: 24019a5557fdSlucy wang - Sun Microsystems - Beijing China *val = LINK_DUPLEX_FULL; 24029a5557fdSlucy wang - Sun Microsystems - Beijing China break; 24039a5557fdSlucy wang - Sun Microsystems - Beijing China 24049a5557fdSlucy wang - Sun Microsystems - Beijing China default: 24059a5557fdSlucy wang - Sun Microsystems - Beijing China /* 24069a5557fdSlucy wang - Sun Microsystems - Beijing China * Shouldn't reach here... 24079a5557fdSlucy wang - Sun Microsystems - Beijing China */ 24089a5557fdSlucy wang - Sun Microsystems - Beijing China *val = 0; 24099a5557fdSlucy wang - Sun Microsystems - Beijing China DPRINTF(0, (CE_WARN, ": unrecognized parameter = %d, value " 24109a5557fdSlucy wang - Sun Microsystems - Beijing China "returned 1\n", stat)); 24119a5557fdSlucy wang - Sun Microsystems - Beijing China 24129a5557fdSlucy wang - Sun Microsystems - Beijing China } 24139a5557fdSlucy wang - Sun Microsystems - Beijing China 24149a5557fdSlucy wang - Sun Microsystems - Beijing China return (0); 24159a5557fdSlucy wang - Sun Microsystems - Beijing China } 24169a5557fdSlucy wang - Sun Microsystems - Beijing China 24179a5557fdSlucy wang - Sun Microsystems - Beijing China static int 24189a5557fdSlucy wang - Sun Microsystems - Beijing China ntxn_m_unicst(void *arg, const uint8_t *mac) 24199a5557fdSlucy wang - Sun Microsystems - Beijing China { 24209a5557fdSlucy wang - Sun Microsystems - Beijing China struct unm_adapter_s *adapter = arg; 24219a5557fdSlucy wang - Sun Microsystems - Beijing China 24229a5557fdSlucy wang - Sun Microsystems - Beijing China DPRINTF(-1, (CE_CONT, "%s: called\n", __func__)); 24239a5557fdSlucy wang - Sun Microsystems - Beijing China 24249a5557fdSlucy wang - Sun Microsystems - Beijing China if (unm_nic_macaddr_set(adapter, (uint8_t *)mac)) 24259a5557fdSlucy wang - Sun Microsystems - Beijing China return (EAGAIN); 24269a5557fdSlucy wang - Sun Microsystems - Beijing China bcopy(mac, adapter->mac_addr, ETHERADDRL); 24279a5557fdSlucy wang - Sun Microsystems - Beijing China 24289a5557fdSlucy wang - Sun Microsystems - Beijing China return (0); 24299a5557fdSlucy wang - Sun Microsystems - Beijing China } 24309a5557fdSlucy wang - Sun Microsystems - Beijing China 24319a5557fdSlucy wang - Sun Microsystems - Beijing China static mblk_t * 24329a5557fdSlucy wang - Sun Microsystems - Beijing China ntxn_m_tx(void *arg, mblk_t *mp) 24339a5557fdSlucy wang - Sun Microsystems - Beijing China { 24349a5557fdSlucy wang - Sun Microsystems - Beijing China unm_adapter *adapter = arg; 24359a5557fdSlucy wang - Sun Microsystems - Beijing China mblk_t *next; 24369a5557fdSlucy wang - Sun Microsystems - Beijing China 24379a5557fdSlucy wang - Sun Microsystems - Beijing China while (mp != NULL) { 24389a5557fdSlucy wang - Sun Microsystems - Beijing China next = mp->b_next; 24399a5557fdSlucy wang - Sun Microsystems - Beijing China mp->b_next = NULL; 24409a5557fdSlucy wang - Sun Microsystems - Beijing China 24419a5557fdSlucy wang - Sun Microsystems - Beijing China if (unm_nic_xmit_frame(adapter, mp) != B_TRUE) { 24429a5557fdSlucy wang - Sun Microsystems - Beijing China mp->b_next = next; 24439a5557fdSlucy wang - Sun Microsystems - Beijing China break; 24449a5557fdSlucy wang - Sun Microsystems - Beijing China } 24459a5557fdSlucy wang - Sun Microsystems - Beijing China mp = next; 24469a5557fdSlucy wang - Sun Microsystems - Beijing China adapter->stats.xmitedframes++; 24479a5557fdSlucy wang - Sun Microsystems - Beijing China } 24489a5557fdSlucy wang - Sun Microsystems - Beijing China 24499a5557fdSlucy wang - Sun Microsystems - Beijing China return (mp); 24509a5557fdSlucy wang - Sun Microsystems - Beijing China } 24519a5557fdSlucy wang - Sun Microsystems - Beijing China 24529a5557fdSlucy wang - Sun Microsystems - Beijing China static void 24539a5557fdSlucy wang - Sun Microsystems - Beijing China ntxn_m_ioctl(void *arg, queue_t *wq, mblk_t *mp) 24549a5557fdSlucy wang - Sun Microsystems - Beijing China { 24559a5557fdSlucy wang - Sun Microsystems - Beijing China int cmd; 24569a5557fdSlucy wang - Sun Microsystems - Beijing China struct iocblk *iocp = (struct iocblk *)(uintptr_t)mp->b_rptr; 24579a5557fdSlucy wang - Sun Microsystems - Beijing China struct unm_adapter_s *adapter = (struct unm_adapter_s *)arg; 24589a5557fdSlucy wang - Sun Microsystems - Beijing China enum ioc_reply status = IOC_DONE; 24599a5557fdSlucy wang - Sun Microsystems - Beijing China 24609a5557fdSlucy wang - Sun Microsystems - Beijing China iocp->ioc_error = 0; 24619a5557fdSlucy wang - Sun Microsystems - Beijing China cmd = iocp->ioc_cmd; 24629a5557fdSlucy wang - Sun Microsystems - Beijing China 24639a5557fdSlucy wang - Sun Microsystems - Beijing China if (cmd == ND_GET || cmd == ND_SET) { 24649a5557fdSlucy wang - Sun Microsystems - Beijing China status = unm_nd_ioctl(adapter, wq, mp, iocp); 24659a5557fdSlucy wang - Sun Microsystems - Beijing China switch (status) { 24669a5557fdSlucy wang - Sun Microsystems - Beijing China default: 24679a5557fdSlucy wang - Sun Microsystems - Beijing China case IOC_INVAL: 24689a5557fdSlucy wang - Sun Microsystems - Beijing China miocnak(wq, mp, 0, iocp->ioc_error == 0 ? 24699a5557fdSlucy wang - Sun Microsystems - Beijing China EINVAL : iocp->ioc_error); 24709a5557fdSlucy wang - Sun Microsystems - Beijing China break; 24719a5557fdSlucy wang - Sun Microsystems - Beijing China 24729a5557fdSlucy wang - Sun Microsystems - Beijing China case IOC_DONE: 24739a5557fdSlucy wang - Sun Microsystems - Beijing China break; 24749a5557fdSlucy wang - Sun Microsystems - Beijing China 24759a5557fdSlucy wang - Sun Microsystems - Beijing China case IOC_RESTART_ACK: 24769a5557fdSlucy wang - Sun Microsystems - Beijing China case IOC_ACK: 24779a5557fdSlucy wang - Sun Microsystems - Beijing China miocack(wq, mp, 0, 0); 24789a5557fdSlucy wang - Sun Microsystems - Beijing China break; 24799a5557fdSlucy wang - Sun Microsystems - Beijing China 24809a5557fdSlucy wang - Sun Microsystems - Beijing China case IOC_RESTART_REPLY: 24819a5557fdSlucy wang - Sun Microsystems - Beijing China case IOC_REPLY: 24829a5557fdSlucy wang - Sun Microsystems - Beijing China mp->b_datap->db_type = iocp->ioc_error == 0 ? 24839a5557fdSlucy wang - Sun Microsystems - Beijing China M_IOCACK : M_IOCNAK; 24849a5557fdSlucy wang - Sun Microsystems - Beijing China qreply(wq, mp); 24859a5557fdSlucy wang - Sun Microsystems - Beijing China break; 24869a5557fdSlucy wang - Sun Microsystems - Beijing China } 24879a5557fdSlucy wang - Sun Microsystems - Beijing China } else if (cmd <= UNM_NIC_NAME && cmd >= UNM_CMD_START) { 24889a5557fdSlucy wang - Sun Microsystems - Beijing China unm_nic_ioctl(adapter, cmd, wq, mp); 24899a5557fdSlucy wang - Sun Microsystems - Beijing China return; 24909a5557fdSlucy wang - Sun Microsystems - Beijing China } else { 24919a5557fdSlucy wang - Sun Microsystems - Beijing China miocnak(wq, mp, 0, EINVAL); 24929a5557fdSlucy wang - Sun Microsystems - Beijing China return; 24939a5557fdSlucy wang - Sun Microsystems - Beijing China } 24949a5557fdSlucy wang - Sun Microsystems - Beijing China } 24959a5557fdSlucy wang - Sun Microsystems - Beijing China 24969a5557fdSlucy wang - Sun Microsystems - Beijing China /* ARGSUSED */ 24979a5557fdSlucy wang - Sun Microsystems - Beijing China static boolean_t 24989a5557fdSlucy wang - Sun Microsystems - Beijing China ntxn_m_getcapab(void *arg, mac_capab_t cap, void *cap_data) 24999a5557fdSlucy wang - Sun Microsystems - Beijing China { 25009a5557fdSlucy wang - Sun Microsystems - Beijing China switch (cap) { 25019a5557fdSlucy wang - Sun Microsystems - Beijing China case MAC_CAPAB_HCKSUM: 25029a5557fdSlucy wang - Sun Microsystems - Beijing China { 25039a5557fdSlucy wang - Sun Microsystems - Beijing China uint32_t *txflags = cap_data; 25049a5557fdSlucy wang - Sun Microsystems - Beijing China 25059a5557fdSlucy wang - Sun Microsystems - Beijing China *txflags = (HCKSUM_ENABLE | 25069a5557fdSlucy wang - Sun Microsystems - Beijing China HCKSUM_INET_FULL_V4 | HCKSUM_IPHDRCKSUM); 25079a5557fdSlucy wang - Sun Microsystems - Beijing China } 25089a5557fdSlucy wang - Sun Microsystems - Beijing China break; 2509dda0720aSjing xiong ERI-SUN 2510dda0720aSjing xiong ERI-SUN #ifdef SOLARIS11 2511dda0720aSjing xiong ERI-SUN case MAC_CAPAB_ANCHOR_VNIC: 2512dda0720aSjing xiong ERI-SUN case MAC_CAPAB_MULTIFACTADDR: 2513dda0720aSjing xiong ERI-SUN #else 2514dda0720aSjing xiong ERI-SUN case MAC_CAPAB_POLL: 2515dda0720aSjing xiong ERI-SUN case MAC_CAPAB_MULTIADDRESS: 2516dda0720aSjing xiong ERI-SUN #endif 25179a5557fdSlucy wang - Sun Microsystems - Beijing China default: 25189a5557fdSlucy wang - Sun Microsystems - Beijing China return (B_FALSE); 25199a5557fdSlucy wang - Sun Microsystems - Beijing China } 25209a5557fdSlucy wang - Sun Microsystems - Beijing China 25219a5557fdSlucy wang - Sun Microsystems - Beijing China return (B_TRUE); 25229a5557fdSlucy wang - Sun Microsystems - Beijing China } 25239a5557fdSlucy wang - Sun Microsystems - Beijing China 25249a5557fdSlucy wang - Sun Microsystems - Beijing China #define NETXEN_M_CALLBACK_FLAGS (MC_IOCTL | MC_GETCAPAB) 25259a5557fdSlucy wang - Sun Microsystems - Beijing China 25269a5557fdSlucy wang - Sun Microsystems - Beijing China static mac_callbacks_t ntxn_m_callbacks = { 25279a5557fdSlucy wang - Sun Microsystems - Beijing China NETXEN_M_CALLBACK_FLAGS, 25289a5557fdSlucy wang - Sun Microsystems - Beijing China ntxn_m_stat, 25299a5557fdSlucy wang - Sun Microsystems - Beijing China ntxn_m_start, 25309a5557fdSlucy wang - Sun Microsystems - Beijing China ntxn_m_stop, 25319a5557fdSlucy wang - Sun Microsystems - Beijing China ntxn_m_promisc, 25329a5557fdSlucy wang - Sun Microsystems - Beijing China ntxn_m_multicst, 25339a5557fdSlucy wang - Sun Microsystems - Beijing China ntxn_m_unicst, 25349a5557fdSlucy wang - Sun Microsystems - Beijing China ntxn_m_tx, 2535*0dc2366fSVenugopal Iyer NULL, /* mc_reserved */ 25369a5557fdSlucy wang - Sun Microsystems - Beijing China ntxn_m_ioctl, 25379a5557fdSlucy wang - Sun Microsystems - Beijing China ntxn_m_getcapab, 25389a5557fdSlucy wang - Sun Microsystems - Beijing China NULL, /* mc_open */ 25399a5557fdSlucy wang - Sun Microsystems - Beijing China NULL, /* mc_close */ 25409a5557fdSlucy wang - Sun Microsystems - Beijing China NULL, /* mc_setprop */ 25419a5557fdSlucy wang - Sun Microsystems - Beijing China NULL /* mc_getprop */ 25429a5557fdSlucy wang - Sun Microsystems - Beijing China }; 25439a5557fdSlucy wang - Sun Microsystems - Beijing China 25449a5557fdSlucy wang - Sun Microsystems - Beijing China int 25459a5557fdSlucy wang - Sun Microsystems - Beijing China unm_register_mac(unm_adapter *adapter) 25469a5557fdSlucy wang - Sun Microsystems - Beijing China { 25479a5557fdSlucy wang - Sun Microsystems - Beijing China int ret; 25489a5557fdSlucy wang - Sun Microsystems - Beijing China mac_register_t *macp; 25499a5557fdSlucy wang - Sun Microsystems - Beijing China unm_pauseparam_t pause; 25509a5557fdSlucy wang - Sun Microsystems - Beijing China 25519a5557fdSlucy wang - Sun Microsystems - Beijing China dev_info_t *dip = adapter->dip; 25529a5557fdSlucy wang - Sun Microsystems - Beijing China 25539a5557fdSlucy wang - Sun Microsystems - Beijing China if ((macp = mac_alloc(MAC_VERSION)) == NULL) { 25549a5557fdSlucy wang - Sun Microsystems - Beijing China cmn_err(CE_WARN, "Memory not available\n"); 25559a5557fdSlucy wang - Sun Microsystems - Beijing China return (DDI_FAILURE); 25569a5557fdSlucy wang - Sun Microsystems - Beijing China } 25579a5557fdSlucy wang - Sun Microsystems - Beijing China 25589a5557fdSlucy wang - Sun Microsystems - Beijing China macp->m_type_ident = MAC_PLUGIN_IDENT_ETHER; 25599a5557fdSlucy wang - Sun Microsystems - Beijing China macp->m_driver = adapter; 25609a5557fdSlucy wang - Sun Microsystems - Beijing China macp->m_dip = dip; 25619a5557fdSlucy wang - Sun Microsystems - Beijing China macp->m_instance = adapter->instance; 25629a5557fdSlucy wang - Sun Microsystems - Beijing China macp->m_src_addr = adapter->mac_addr; 25639a5557fdSlucy wang - Sun Microsystems - Beijing China macp->m_callbacks = &ntxn_m_callbacks; 25649a5557fdSlucy wang - Sun Microsystems - Beijing China macp->m_min_sdu = 0; 25659a5557fdSlucy wang - Sun Microsystems - Beijing China macp->m_max_sdu = adapter->mtu; 25669a5557fdSlucy wang - Sun Microsystems - Beijing China #ifdef SOLARIS11 25679a5557fdSlucy wang - Sun Microsystems - Beijing China macp->m_margin = VLAN_TAGSZ; 25689a5557fdSlucy wang - Sun Microsystems - Beijing China #endif /* SOLARIS11 */ 25699a5557fdSlucy wang - Sun Microsystems - Beijing China 25709a5557fdSlucy wang - Sun Microsystems - Beijing China ret = mac_register(macp, &adapter->mach); 25719a5557fdSlucy wang - Sun Microsystems - Beijing China mac_free(macp); 25729a5557fdSlucy wang - Sun Microsystems - Beijing China if (ret != 0) { 25739a5557fdSlucy wang - Sun Microsystems - Beijing China cmn_err(CE_WARN, "mac_register failed for port %d\n", 25749a5557fdSlucy wang - Sun Microsystems - Beijing China adapter->portnum); 25759a5557fdSlucy wang - Sun Microsystems - Beijing China return (DDI_FAILURE); 25769a5557fdSlucy wang - Sun Microsystems - Beijing China } 25779a5557fdSlucy wang - Sun Microsystems - Beijing China 25789a5557fdSlucy wang - Sun Microsystems - Beijing China unm_init_kstats(adapter, adapter->instance); 25799a5557fdSlucy wang - Sun Microsystems - Beijing China 25809a5557fdSlucy wang - Sun Microsystems - Beijing China /* Register NDD-tweakable parameters */ 25819a5557fdSlucy wang - Sun Microsystems - Beijing China if (unm_nd_init(adapter)) { 25829a5557fdSlucy wang - Sun Microsystems - Beijing China cmn_err(CE_WARN, "unm_nd_init() failed"); 25839a5557fdSlucy wang - Sun Microsystems - Beijing China return (DDI_FAILURE); 25849a5557fdSlucy wang - Sun Microsystems - Beijing China } 25859a5557fdSlucy wang - Sun Microsystems - Beijing China 25869a5557fdSlucy wang - Sun Microsystems - Beijing China pause.rx_pause = adapter->nd_params[PARAM_ADV_PAUSE_CAP].ndp_val; 25879a5557fdSlucy wang - Sun Microsystems - Beijing China pause.tx_pause = adapter->nd_params[PARAM_ADV_ASYM_PAUSE_CAP].ndp_val; 25889a5557fdSlucy wang - Sun Microsystems - Beijing China 25899a5557fdSlucy wang - Sun Microsystems - Beijing China if (unm_nic_set_pauseparam(adapter, &pause)) { 25909a5557fdSlucy wang - Sun Microsystems - Beijing China cmn_err(CE_WARN, "\nBad Pause settings RX %d, Tx %d", 25919a5557fdSlucy wang - Sun Microsystems - Beijing China pause.rx_pause, pause.tx_pause); 25929a5557fdSlucy wang - Sun Microsystems - Beijing China } 25939a5557fdSlucy wang - Sun Microsystems - Beijing China adapter->nd_params[PARAM_PAUSE_CAP].ndp_val = pause.rx_pause; 25949a5557fdSlucy wang - Sun Microsystems - Beijing China adapter->nd_params[PARAM_ASYM_PAUSE_CAP].ndp_val = pause.tx_pause; 25959a5557fdSlucy wang - Sun Microsystems - Beijing China 25969a5557fdSlucy wang - Sun Microsystems - Beijing China return (DDI_SUCCESS); 25979a5557fdSlucy wang - Sun Microsystems - Beijing China } 2598