Home | History | Annotate | Line # | Download | only in cxgb
cxgb_osdep.c revision 1.1.6.2
      1  1.1.6.2  yamt /**************************************************************************
      2  1.1.6.2  yamt 
      3  1.1.6.2  yamt Copyright (c) 2007, Chelsio Inc.
      4  1.1.6.2  yamt All rights reserved.
      5  1.1.6.2  yamt 
      6  1.1.6.2  yamt Redistribution and use in source and binary forms, with or without
      7  1.1.6.2  yamt modification, are permitted provided that the following conditions are met:
      8  1.1.6.2  yamt 
      9  1.1.6.2  yamt  1. Redistributions of source code must retain the above copyright notice,
     10  1.1.6.2  yamt     this list of conditions and the following disclaimer.
     11  1.1.6.2  yamt 
     12  1.1.6.2  yamt  2. Neither the name of the Chelsio Corporation nor the names of its
     13  1.1.6.2  yamt     contributors may be used to endorse or promote products derived from
     14  1.1.6.2  yamt     this software without specific prior written permission.
     15  1.1.6.2  yamt 
     16  1.1.6.2  yamt THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS "AS IS"
     17  1.1.6.2  yamt AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE
     18  1.1.6.2  yamt IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE
     19  1.1.6.2  yamt ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT OWNER OR CONTRIBUTORS BE
     20  1.1.6.2  yamt LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR
     21  1.1.6.2  yamt CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF
     22  1.1.6.2  yamt SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS
     23  1.1.6.2  yamt INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN
     24  1.1.6.2  yamt CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE)
     25  1.1.6.2  yamt ARISING IN ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE
     26  1.1.6.2  yamt POSSIBILITY OF SUCH DAMAGE.
     27  1.1.6.2  yamt 
     28  1.1.6.2  yamt ***************************************************************************/
     29  1.1.6.2  yamt 
     30  1.1.6.2  yamt #include <sys/cdefs.h>
     31  1.1.6.2  yamt 
     32  1.1.6.2  yamt #include <sys/param.h>
     33  1.1.6.2  yamt #include <sys/systm.h>
     34  1.1.6.2  yamt #include <sys/kernel.h>
     35  1.1.6.2  yamt #include <sys/conf.h>
     36  1.1.6.2  yamt #include <machine/bus.h>
     37  1.1.6.2  yamt #include <sys/ioccom.h>
     38  1.1.6.2  yamt #include <sys/mbuf.h>
     39  1.1.6.2  yamt #include <sys/socket.h>
     40  1.1.6.2  yamt #include <sys/sockio.h>
     41  1.1.6.2  yamt #include <sys/sysctl.h>
     42  1.1.6.2  yamt #include <sys/queue.h>
     43  1.1.6.2  yamt 
     44  1.1.6.2  yamt #include <net/bpf.h>
     45  1.1.6.2  yamt #include <net/if.h>
     46  1.1.6.2  yamt #include <net/if_arp.h>
     47  1.1.6.2  yamt #include <net/if_dl.h>
     48  1.1.6.2  yamt #include <net/if_media.h>
     49  1.1.6.2  yamt #include <net/if_types.h>
     50  1.1.6.2  yamt 
     51  1.1.6.2  yamt #include <netinet/in_systm.h>
     52  1.1.6.2  yamt #include <netinet/in.h>
     53  1.1.6.2  yamt #include <netinet/ip.h>
     54  1.1.6.2  yamt #include <netinet/tcp.h>
     55  1.1.6.2  yamt #include <netinet/udp.h>
     56  1.1.6.2  yamt 
     57  1.1.6.2  yamt #include <dev/pci/pcireg.h>
     58  1.1.6.2  yamt #include <dev/pci/pcivar.h>
     59  1.1.6.2  yamt 
     60  1.1.6.2  yamt #include <dev/pci/cxgb/cxgb_include.h>
     61  1.1.6.2  yamt #include <altq/altq_conf.h>
     62  1.1.6.2  yamt 
     63  1.1.6.2  yamt int cxgb_initialized = FALSE;
     64  1.1.6.2  yamt 
     65  1.1.6.2  yamt int atomic_fetchadd_int(volatile int *p, int v)
     66  1.1.6.2  yamt {
     67  1.1.6.2  yamt     int tmp = *p;
     68  1.1.6.2  yamt     *p += v;
     69  1.1.6.2  yamt     return (tmp);
     70  1.1.6.2  yamt }
     71  1.1.6.2  yamt 
     72  1.1.6.2  yamt #if 0
     73  1.1.6.2  yamt int atomic_add_int(volatile int *p, int v)
     74  1.1.6.2  yamt {
     75  1.1.6.2  yamt     return (*p += v);
     76  1.1.6.2  yamt }
     77  1.1.6.2  yamt #endif
     78  1.1.6.2  yamt 
     79  1.1.6.2  yamt int atomic_load_acq_int(volatile int *p)
     80  1.1.6.2  yamt {
     81  1.1.6.2  yamt     return (*p);
     82  1.1.6.2  yamt }
     83  1.1.6.2  yamt 
     84  1.1.6.2  yamt void atomic_store_rel_int(volatile int *p, int v)
     85  1.1.6.2  yamt {
     86  1.1.6.2  yamt     *p = v;
     87  1.1.6.2  yamt }
     88  1.1.6.2  yamt 
     89  1.1.6.2  yamt u_short in_cksum_hdr(struct ip *ih)
     90  1.1.6.2  yamt {
     91  1.1.6.2  yamt 	u_long sum = 0;
     92  1.1.6.2  yamt 	u_short *p = (u_short *)ih;
     93  1.1.6.2  yamt 	int i;
     94  1.1.6.2  yamt 
     95  1.1.6.2  yamt         i = ih->ip_hl*2;
     96  1.1.6.2  yamt 	while (i--)
     97  1.1.6.2  yamt 		sum += *p++;
     98  1.1.6.2  yamt 
     99  1.1.6.2  yamt 	if (sum > 0xffff)
    100  1.1.6.2  yamt 		sum -= 0xffff;
    101  1.1.6.2  yamt 
    102  1.1.6.2  yamt 	return (~sum);
    103  1.1.6.2  yamt }
    104  1.1.6.2  yamt 
    105  1.1.6.2  yamt void m_cljset(struct mbuf *m, void *cl, int type)
    106  1.1.6.2  yamt {
    107  1.1.6.2  yamt     MEXTADD(m, cl, m->m_len, M_DEVBUF, NULL, NULL);
    108  1.1.6.2  yamt }
    109  1.1.6.2  yamt 
    110  1.1.6.2  yamt int
    111  1.1.6.2  yamt _m_explode(struct mbuf *m)
    112  1.1.6.2  yamt {
    113  1.1.6.2  yamt         int i, offset, type, first, len;
    114  1.1.6.2  yamt         uint8_t *cl;
    115  1.1.6.2  yamt         struct mbuf *m0, *head = NULL;
    116  1.1.6.2  yamt         struct mbuf_vec *mv;
    117  1.1.6.2  yamt 
    118  1.1.6.2  yamt #ifdef INVARIANTS
    119  1.1.6.2  yamt         len = m->m_len;
    120  1.1.6.2  yamt         m0 = m->m_next;
    121  1.1.6.2  yamt         while (m0) {
    122  1.1.6.2  yamt                 KASSERT((m0->m_flags & M_PKTHDR) == 0,
    123  1.1.6.2  yamt                     ("pkthdr set on intermediate mbuf - pre"));
    124  1.1.6.2  yamt                 len += m0->m_len;
    125  1.1.6.2  yamt                 m0 = m0->m_next;
    126  1.1.6.2  yamt 
    127  1.1.6.2  yamt         }
    128  1.1.6.2  yamt         if (len != m->m_pkthdr.len)
    129  1.1.6.2  yamt                 panic("at start len=%d pktlen=%d", len, m->m_pkthdr.len);
    130  1.1.6.2  yamt #endif
    131  1.1.6.2  yamt         mv = (struct mbuf_vec *)((m)->m_pktdat);
    132  1.1.6.2  yamt         first = mv->mv_first;
    133  1.1.6.2  yamt         for (i = mv->mv_count + first - 1; i > first; i--) {
    134  1.1.6.2  yamt                 type = mbuf_vec_get_type(mv, i);
    135  1.1.6.2  yamt                 cl = mv->mv_vec[i].mi_base;
    136  1.1.6.2  yamt                 offset = mv->mv_vec[i].mi_offset;
    137  1.1.6.2  yamt                 len = mv->mv_vec[i].mi_len;
    138  1.1.6.2  yamt #if 0
    139  1.1.6.2  yamt                 if (__predict_false(type == EXT_MBUF)) {
    140  1.1.6.2  yamt                         m0 = (struct mbuf *)cl;
    141  1.1.6.2  yamt                         KASSERT((m0->m_flags & M_EXT) == 0);
    142  1.1.6.2  yamt                         m0->m_len = len;
    143  1.1.6.2  yamt                         m0->m_data = cl + offset;
    144  1.1.6.2  yamt                         goto skip_cluster;
    145  1.1.6.2  yamt 
    146  1.1.6.2  yamt                 } else
    147  1.1.6.2  yamt #endif
    148  1.1.6.2  yamt 		if ((m0 = m_get(M_NOWAIT, MT_DATA)) == NULL) {
    149  1.1.6.2  yamt                         /*
    150  1.1.6.2  yamt                          * Check for extra memory leaks
    151  1.1.6.2  yamt                          */
    152  1.1.6.2  yamt                         m_freem(head);
    153  1.1.6.2  yamt                         return (ENOMEM);
    154  1.1.6.2  yamt                 }
    155  1.1.6.2  yamt                 m0->m_flags = 0;
    156  1.1.6.2  yamt 
    157  1.1.6.2  yamt                 m0->m_len = mv->mv_vec[i].mi_len;
    158  1.1.6.2  yamt                 m_cljset(m0, (uint8_t *)cl, type);
    159  1.1.6.2  yamt                 if (offset)
    160  1.1.6.2  yamt                         m_adj(m0, offset);
    161  1.1.6.2  yamt //        skip_cluster:
    162  1.1.6.2  yamt                 m0->m_next = head;
    163  1.1.6.2  yamt                 m->m_len -= m0->m_len;
    164  1.1.6.2  yamt                 head = m0;
    165  1.1.6.2  yamt         }
    166  1.1.6.2  yamt         offset = mv->mv_vec[first].mi_offset;
    167  1.1.6.2  yamt         cl = mv->mv_vec[first].mi_base;
    168  1.1.6.2  yamt         type = mbuf_vec_get_type(mv, first);
    169  1.1.6.2  yamt         m->m_flags &= ~(M_IOVEC);
    170  1.1.6.2  yamt         m_cljset(m, cl, type);
    171  1.1.6.2  yamt         if (offset)
    172  1.1.6.2  yamt                 m_adj(m, offset);
    173  1.1.6.2  yamt         m->m_next = head;
    174  1.1.6.2  yamt         head = m;
    175  1.1.6.2  yamt         M_SANITY(m, 0);
    176  1.1.6.2  yamt 
    177  1.1.6.2  yamt         return (0);
    178  1.1.6.2  yamt }
    179  1.1.6.2  yamt 
    180  1.1.6.2  yamt /*
    181  1.1.6.2  yamt  * Allocate a chunk of memory using kmalloc or, if that fails, vmalloc.
    182  1.1.6.2  yamt  * The allocated memory is cleared.
    183  1.1.6.2  yamt  */
    184  1.1.6.2  yamt void *
    185  1.1.6.2  yamt cxgb_alloc_mem(unsigned long size)
    186  1.1.6.2  yamt {
    187  1.1.6.2  yamt     return malloc(size, M_DEVBUF, M_ZERO);
    188  1.1.6.2  yamt }
    189  1.1.6.2  yamt 
    190  1.1.6.2  yamt /*
    191  1.1.6.2  yamt  * Free memory allocated through t3_alloc_mem().
    192  1.1.6.2  yamt  */
    193  1.1.6.2  yamt void
    194  1.1.6.2  yamt cxgb_free_mem(void *addr)
    195  1.1.6.2  yamt {
    196  1.1.6.2  yamt     free(addr, M_DEVBUF);
    197  1.1.6.2  yamt }
    198  1.1.6.2  yamt 
    199  1.1.6.2  yamt void pci_enable_busmaster(device_t dev)
    200  1.1.6.2  yamt {
    201  1.1.6.2  yamt     adapter_t *sc = (adapter_t *)dev;
    202  1.1.6.2  yamt     uint32_t reg;
    203  1.1.6.2  yamt 
    204  1.1.6.2  yamt     t3_os_pci_read_config_4(sc, PCI_COMMAND_STATUS_REG, &reg);
    205  1.1.6.2  yamt     reg |= PCI_COMMAND_MASTER_ENABLE;
    206  1.1.6.2  yamt     t3_os_pci_write_config_4(sc, PCI_COMMAND_STATUS_REG, reg);
    207  1.1.6.2  yamt }
    208