[ source navigation ] [ diff markup ] [ identifier search ] [ freetext search ] [ file search ]

FreeBSD/Linux Kernel Cross Reference
sys/dev/nxge/if_nxge.c

Version: -  FREEBSD  -  FREEBSD7  -  FREEBSD70  -  FREEBSD6  -  FREEBSD64  -  FREEBSD63  -  FREEBSD62  -  FREEBSD61  -  FREEBSD60  -  FREEBSD5  -  FREEBSD55  -  FREEBSD54  -  FREEBSD53  -  FREEBSD52  -  FREEBSD51  -  FREEBSD50  -  FREEBSD4  -  FREEBSD3  -  FREEBSD22  -  linux-2.6  -  linux-2.4.22  -  MK83  -  MK84  -  PLAN9  -  DFBSD  -  NETBSD  -  NETBSD5  -  NETBSD4  -  NETBSD3  -  NETBSD20  -  OPENBSD  -  xnu-517  -  xnu-792  -  xnu-792.6.70  -  xnu-1228  -  OPENSOLARIS  -  minix-3-1-1  -  TRUSTEDBSD-SEBSD  -  FREEBSD-LIBC  -  FREEBSD7-LIBC  -  FREEBSD6-LIBC  -  GLIBC27 
SearchContext: -  none  -  excerpts  -  bigexcerpts 

  1 /*-
  2  * Copyright (c) 2002-2007 Neterion, Inc.
  3  * All rights reserved.
  4  *
  5  * Redistribution and use in source and binary forms, with or without
  6  * modification, are permitted provided that the following conditions
  7  * are met:
  8  * 1. Redistributions of source code must retain the above copyright
  9  *    notice, this list of conditions and the following disclaimer.
 10  * 2. Redistributions in binary form must reproduce the above copyright
 11  *    notice, this list of conditions and the following disclaimer in the
 12  *    documentation and/or other materials provided with the distribution.
 13  *
 14  * THIS SOFTWARE IS PROVIDED BY THE AUTHOR AND CONTRIBUTORS ``AS IS'' AND
 15  * ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE
 16  * IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE
 17  * ARE DISCLAIMED.  IN NO EVENT SHALL THE AUTHOR OR CONTRIBUTORS BE LIABLE
 18  * FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL
 19  * DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS
 20  * OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION)
 21  * HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT
 22  * LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY
 23  * OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF
 24  * SUCH DAMAGE.
 25  *
 26  * $FreeBSD: src/sys/dev/nxge/if_nxge.c,v 1.4 2007/10/29 14:19:30 rwatson Exp $
 27  */
 28 
 29 #include <dev/nxge/if_nxge.h>
 30 #include <dev/nxge/xge-osdep.h>
 31 #include <net/if_arp.h>
 32 #include <sys/types.h>
 33 #include <net/if.h>
 34 #include <net/if_vlan_var.h>
 35 
 36 int       copyright_print       = 0;
 37 int       hal_driver_init_count = 0;
 38 size_t    size                  = sizeof(int);
 39 
 40 static void inline xge_flush_txds(xge_hal_channel_h);
 41 
 42 /**
 43  * xge_probe
 44  * Probes for Xframe devices
 45  *
 46  * @dev Device handle
 47  *
 48  * Returns
 49  * BUS_PROBE_DEFAULT if device is supported
 50  * ENXIO if device is not supported
 51  */
 52 int
 53 xge_probe(device_t dev)
 54 {
 55         int  devid    = pci_get_device(dev);
 56         int  vendorid = pci_get_vendor(dev);
 57         int  retValue = ENXIO;
 58 
 59         if(vendorid == XGE_PCI_VENDOR_ID) {
 60             if((devid == XGE_PCI_DEVICE_ID_XENA_2) ||
 61                 (devid == XGE_PCI_DEVICE_ID_HERC_2)) {
 62                 if(!copyright_print) {
 63                     xge_os_printf(XGE_COPYRIGHT);
 64                     copyright_print = 1;
 65                 }
 66                 device_set_desc_copy(dev,
 67                     "Neterion Xframe 10 Gigabit Ethernet Adapter");
 68                 retValue = BUS_PROBE_DEFAULT;
 69             }
 70         }
 71 
 72         return retValue;
 73 }
 74 
 75 /**
 76  * xge_init_params
 77  * Sets HAL parameter values (from kenv).
 78  *
 79  * @dconfig Device Configuration
 80  * @dev Device Handle
 81  */
 82 void
 83 xge_init_params(xge_hal_device_config_t *dconfig, device_t dev)
 84 {
 85         int qindex, tindex, revision;
 86         device_t checkdev;
 87         xge_lldev_t *lldev = (xge_lldev_t *)device_get_softc(dev);
 88 
 89         dconfig->mtu                   = XGE_DEFAULT_INITIAL_MTU;
 90         dconfig->pci_freq_mherz        = XGE_DEFAULT_USER_HARDCODED;
 91         dconfig->device_poll_millis    = XGE_HAL_DEFAULT_DEVICE_POLL_MILLIS;
 92         dconfig->link_stability_period = XGE_HAL_DEFAULT_LINK_STABILITY_PERIOD;
 93         dconfig->mac.rmac_bcast_en     = XGE_DEFAULT_MAC_RMAC_BCAST_EN;
 94         dconfig->fifo.alignment_size   = XGE_DEFAULT_FIFO_ALIGNMENT_SIZE;
 95 
 96         XGE_GET_PARAM("hw.xge.enable_tso", (*lldev), enabled_tso,
 97             XGE_DEFAULT_ENABLED_TSO);
 98         XGE_GET_PARAM("hw.xge.enable_lro", (*lldev), enabled_lro,
 99             XGE_DEFAULT_ENABLED_LRO);
100         XGE_GET_PARAM("hw.xge.enable_msi", (*lldev), enabled_msi,
101             XGE_DEFAULT_ENABLED_MSI);
102 
103         XGE_GET_PARAM("hw.xge.latency_timer", (*dconfig), latency_timer,
104             XGE_DEFAULT_LATENCY_TIMER);
105         XGE_GET_PARAM("hw.xge.max_splits_trans", (*dconfig), max_splits_trans,
106             XGE_DEFAULT_MAX_SPLITS_TRANS);
107         XGE_GET_PARAM("hw.xge.mmrb_count", (*dconfig), mmrb_count,
108             XGE_DEFAULT_MMRB_COUNT);
109         XGE_GET_PARAM("hw.xge.shared_splits", (*dconfig), shared_splits,
110             XGE_DEFAULT_SHARED_SPLITS);
111         XGE_GET_PARAM("hw.xge.isr_polling_cnt", (*dconfig), isr_polling_cnt,
112             XGE_DEFAULT_ISR_POLLING_CNT);
113         XGE_GET_PARAM("hw.xge.stats_refresh_time_sec", (*dconfig),
114             stats_refresh_time_sec, XGE_DEFAULT_STATS_REFRESH_TIME_SEC);
115 
116         XGE_GET_PARAM_MAC("hw.xge.mac_tmac_util_period", tmac_util_period,
117             XGE_DEFAULT_MAC_TMAC_UTIL_PERIOD);
118         XGE_GET_PARAM_MAC("hw.xge.mac_rmac_util_period", rmac_util_period,
119             XGE_DEFAULT_MAC_RMAC_UTIL_PERIOD);
120         XGE_GET_PARAM_MAC("hw.xge.mac_rmac_pause_gen_en", rmac_pause_gen_en,
121             XGE_DEFAULT_MAC_RMAC_PAUSE_GEN_EN);
122         XGE_GET_PARAM_MAC("hw.xge.mac_rmac_pause_rcv_en", rmac_pause_rcv_en,
123             XGE_DEFAULT_MAC_RMAC_PAUSE_RCV_EN);
124         XGE_GET_PARAM_MAC("hw.xge.mac_rmac_pause_time", rmac_pause_time,
125             XGE_DEFAULT_MAC_RMAC_PAUSE_TIME);
126         XGE_GET_PARAM_MAC("hw.xge.mac_mc_pause_threshold_q0q3",
127             mc_pause_threshold_q0q3, XGE_DEFAULT_MAC_MC_PAUSE_THRESHOLD_Q0Q3);
128         XGE_GET_PARAM_MAC("hw.xge.mac_mc_pause_threshold_q4q7",
129             mc_pause_threshold_q4q7, XGE_DEFAULT_MAC_MC_PAUSE_THRESHOLD_Q4Q7);
130 
131         XGE_GET_PARAM_FIFO("hw.xge.fifo_memblock_size", memblock_size,
132             XGE_DEFAULT_FIFO_MEMBLOCK_SIZE);
133         XGE_GET_PARAM_FIFO("hw.xge.fifo_reserve_threshold", reserve_threshold,
134             XGE_DEFAULT_FIFO_RESERVE_THRESHOLD);
135         XGE_GET_PARAM_FIFO("hw.xge.fifo_max_frags", max_frags,
136             XGE_DEFAULT_FIFO_MAX_FRAGS);
137 
138         for(qindex = 0; qindex < XGE_FIFO_COUNT; qindex++) {
139             XGE_GET_PARAM_FIFO_QUEUE("hw.xge.fifo_queue_intr", intr, qindex,
140                 XGE_DEFAULT_FIFO_QUEUE_INTR);
141             XGE_GET_PARAM_FIFO_QUEUE("hw.xge.fifo_queue_max", max, qindex,
142                 XGE_DEFAULT_FIFO_QUEUE_MAX);
143             XGE_GET_PARAM_FIFO_QUEUE("hw.xge.fifo_queue_initial", initial,
144                 qindex, XGE_DEFAULT_FIFO_QUEUE_INITIAL);
145 
146             for (tindex = 0; tindex < XGE_HAL_MAX_FIFO_TTI_NUM; tindex++) {
147                 dconfig->fifo.queue[qindex].tti[tindex].enabled  = 1;
148                 dconfig->fifo.queue[qindex].configured = 1;
149 
150                 XGE_GET_PARAM_FIFO_QUEUE_TTI("hw.xge.fifo_queue_tti_urange_a",
151                     urange_a, qindex, tindex,
152                     XGE_DEFAULT_FIFO_QUEUE_TTI_URANGE_A);
153                 XGE_GET_PARAM_FIFO_QUEUE_TTI("hw.xge.fifo_queue_tti_urange_b",
154                     urange_b, qindex, tindex,
155                     XGE_DEFAULT_FIFO_QUEUE_TTI_URANGE_B);
156                 XGE_GET_PARAM_FIFO_QUEUE_TTI("hw.xge.fifo_queue_tti_urange_c",
157                     urange_c, qindex, tindex,
158                     XGE_DEFAULT_FIFO_QUEUE_TTI_URANGE_C);
159                 XGE_GET_PARAM_FIFO_QUEUE_TTI("hw.xge.fifo_queue_tti_ufc_a",
160                     ufc_a, qindex, tindex, XGE_DEFAULT_FIFO_QUEUE_TTI_UFC_A);
161                 XGE_GET_PARAM_FIFO_QUEUE_TTI("hw.xge.fifo_queue_tti_ufc_b",
162                     ufc_b, qindex, tindex, XGE_DEFAULT_FIFO_QUEUE_TTI_UFC_B);
163                 XGE_GET_PARAM_FIFO_QUEUE_TTI("hw.xge.fifo_queue_tti_ufc_c",
164                     ufc_c, qindex, tindex, XGE_DEFAULT_FIFO_QUEUE_TTI_UFC_C);
165                 XGE_GET_PARAM_FIFO_QUEUE_TTI("hw.xge.fifo_queue_tti_ufc_d",
166                     ufc_d, qindex, tindex, XGE_DEFAULT_FIFO_QUEUE_TTI_UFC_D);
167                 XGE_GET_PARAM_FIFO_QUEUE_TTI(
168                     "hw.xge.fifo_queue_tti_timer_ci_en", timer_ci_en, qindex,
169                     tindex, XGE_DEFAULT_FIFO_QUEUE_TTI_TIMER_CI_EN);
170                 XGE_GET_PARAM_FIFO_QUEUE_TTI(
171                     "hw.xge.fifo_queue_tti_timer_ac_en", timer_ac_en, qindex,
172                     tindex, XGE_DEFAULT_FIFO_QUEUE_TTI_TIMER_AC_EN);
173                 XGE_GET_PARAM_FIFO_QUEUE_TTI(
174                     "hw.xge.fifo_queue_tti_timer_val_us", timer_val_us, qindex,
175                     tindex, XGE_DEFAULT_FIFO_QUEUE_TTI_TIMER_VAL_US);
176             }
177         }
178 
179         XGE_GET_PARAM_RING("hw.xge.ring_memblock_size", memblock_size,
180             XGE_DEFAULT_RING_MEMBLOCK_SIZE);
181 
182         XGE_GET_PARAM_RING("hw.xge.ring_strip_vlan_tag", strip_vlan_tag,
183             XGE_DEFAULT_RING_STRIP_VLAN_TAG);
184 
185         XGE_GET_PARAM("hw.xge.buffer_mode", (*lldev), buffer_mode,
186             XGE_DEFAULT_BUFFER_MODE);
187         if((lldev->buffer_mode < XGE_HAL_RING_QUEUE_BUFFER_MODE_1) ||
188             (lldev->buffer_mode > XGE_HAL_RING_QUEUE_BUFFER_MODE_2)) {
189             xge_trace(XGE_ERR, "Supported buffer modes are 1 and 2");
190             lldev->buffer_mode = XGE_HAL_RING_QUEUE_BUFFER_MODE_1;
191         }
192 
193         for (qindex = 0; qindex < XGE_RING_COUNT; qindex++) {
194             dconfig->ring.queue[qindex].max_frm_len  = XGE_HAL_RING_USE_MTU;
195             dconfig->ring.queue[qindex].priority     = 0;
196             dconfig->ring.queue[qindex].configured   = 1;
197             dconfig->ring.queue[qindex].buffer_mode  =
198                 (lldev->buffer_mode == XGE_HAL_RING_QUEUE_BUFFER_MODE_2) ?
199                 XGE_HAL_RING_QUEUE_BUFFER_MODE_3 : lldev->buffer_mode;
200 
201             XGE_GET_PARAM_RING_QUEUE("hw.xge.ring_queue_max", max, qindex,
202                 XGE_DEFAULT_RING_QUEUE_MAX);
203             XGE_GET_PARAM_RING_QUEUE("hw.xge.ring_queue_initial", initial,
204                 qindex, XGE_DEFAULT_RING_QUEUE_INITIAL);
205             XGE_GET_PARAM_RING_QUEUE("hw.xge.ring_queue_dram_size_mb",
206                 dram_size_mb, qindex, XGE_DEFAULT_RING_QUEUE_DRAM_SIZE_MB);
207             XGE_GET_PARAM_RING_QUEUE("hw.xge.ring_queue_indicate_max_pkts",
208                 indicate_max_pkts, qindex,
209                 XGE_DEFAULT_RING_QUEUE_INDICATE_MAX_PKTS);
210             XGE_GET_PARAM_RING_QUEUE("hw.xge.ring_queue_backoff_interval_us",
211                 backoff_interval_us, qindex,
212                 XGE_DEFAULT_RING_QUEUE_BACKOFF_INTERVAL_US);
213 
214             XGE_GET_PARAM_RING_QUEUE_RTI("hw.xge.ring_queue_rti_ufc_a", ufc_a,
215                 qindex, XGE_DEFAULT_RING_QUEUE_RTI_UFC_A);
216             XGE_GET_PARAM_RING_QUEUE_RTI("hw.xge.ring_queue_rti_ufc_b", ufc_b,
217                 qindex, XGE_DEFAULT_RING_QUEUE_RTI_UFC_B);
218             XGE_GET_PARAM_RING_QUEUE_RTI("hw.xge.ring_queue_rti_ufc_c", ufc_c,
219                 qindex, XGE_DEFAULT_RING_QUEUE_RTI_UFC_C);
220             XGE_GET_PARAM_RING_QUEUE_RTI("hw.xge.ring_queue_rti_ufc_d", ufc_d,
221                 qindex, XGE_DEFAULT_RING_QUEUE_RTI_UFC_D);
222             XGE_GET_PARAM_RING_QUEUE_RTI("hw.xge.ring_queue_rti_timer_ac_en",
223                 timer_ac_en, qindex, XGE_DEFAULT_RING_QUEUE_RTI_TIMER_AC_EN);
224             XGE_GET_PARAM_RING_QUEUE_RTI("hw.xge.ring_queue_rti_timer_val_us",
225                 timer_val_us, qindex, XGE_DEFAULT_RING_QUEUE_RTI_TIMER_VAL_US);
226             XGE_GET_PARAM_RING_QUEUE_RTI("hw.xge.ring_queue_rti_urange_a",
227                 urange_a, qindex, XGE_DEFAULT_RING_QUEUE_RTI_URANGE_A);
228             XGE_GET_PARAM_RING_QUEUE_RTI("hw.xge.ring_queue_rti_urange_b",
229                 urange_b, qindex, XGE_DEFAULT_RING_QUEUE_RTI_URANGE_B);
230             XGE_GET_PARAM_RING_QUEUE_RTI("hw.xge.ring_queue_rti_urange_c",
231                 urange_c, qindex, XGE_DEFAULT_RING_QUEUE_RTI_URANGE_C);
232         }
233 
234         if(dconfig->fifo.max_frags > (PAGE_SIZE/32)) {
235             xge_os_printf("fifo_max_frags = %d", dconfig->fifo.max_frags)
236             xge_os_printf("fifo_max_frags should be <= (PAGE_SIZE / 32) = %d",
237                 (int)(PAGE_SIZE / 32))
238             xge_os_printf("Using fifo_max_frags = %d", (int)(PAGE_SIZE / 32))
239             dconfig->fifo.max_frags = (PAGE_SIZE / 32);
240         }
241 
242         checkdev = pci_find_device(VENDOR_ID_AMD, DEVICE_ID_8131_PCI_BRIDGE);
243         if(checkdev != NULL) {
244             /* Check Revision for 0x12 */
245             revision = pci_read_config(checkdev,
246                 xge_offsetof(xge_hal_pci_config_t, revision), 1);
247             if(revision <= 0x12) {
248                 /* Set mmrb_count to 1k and max splits = 2 */
249                 dconfig->mmrb_count       = 1;
250                 dconfig->max_splits_trans = XGE_HAL_THREE_SPLIT_TRANSACTION;
251             }
252         }
253 }
254 
255 /**
256  * xge_buffer_sizes_set
257  * Set buffer sizes based on Rx buffer mode
258  *
259  * @lldev Per-adapter Data
260  * @buffer_mode Rx Buffer Mode
261  */
262 void
263 xge_rx_buffer_sizes_set(xge_lldev_t *lldev, int buffer_mode, int mtu)
264 {
265         int index = 0;
266         int frame_header = XGE_HAL_MAC_HEADER_MAX_SIZE;
267         int buffer_size = mtu + frame_header;
268 
269         xge_os_memzero(lldev->rxd_mbuf_len, sizeof(lldev->rxd_mbuf_len));
270 
271         if(buffer_mode != XGE_HAL_RING_QUEUE_BUFFER_MODE_5)
272             lldev->rxd_mbuf_len[buffer_mode - 1] = mtu;
273 
274         lldev->rxd_mbuf_len[0] = (buffer_mode == 1) ? buffer_size:frame_header;
275 
276         if(buffer_mode == XGE_HAL_RING_QUEUE_BUFFER_MODE_5)
277             lldev->rxd_mbuf_len[1] = XGE_HAL_TCPIP_HEADER_MAX_SIZE;
278 
279         if(buffer_mode == XGE_HAL_RING_QUEUE_BUFFER_MODE_5) {
280             index = 2;
281             buffer_size -= XGE_HAL_TCPIP_HEADER_MAX_SIZE;
282             while(buffer_size > MJUMPAGESIZE) {
283                 lldev->rxd_mbuf_len[index++] = MJUMPAGESIZE;
284                 buffer_size -= MJUMPAGESIZE;
285             }
286             XGE_ALIGN_TO(buffer_size, 128);
287             lldev->rxd_mbuf_len[index] = buffer_size;
288             lldev->rxd_mbuf_cnt = index + 1;
289         }
290 
291         for(index = 0; index < buffer_mode; index++)
292             xge_trace(XGE_TRACE, "Buffer[%d] %d\n", index,
293                 lldev->rxd_mbuf_len[index]);
294 }
295 
296 /**
297  * xge_buffer_mode_init
298  * Init Rx buffer mode
299  *
300  * @lldev Per-adapter Data
301  * @mtu Interface MTU
302  */
303 void
304 xge_buffer_mode_init(xge_lldev_t *lldev, int mtu)
305 {
306         int index = 0, buffer_size = 0;
307         xge_hal_ring_config_t *ring_config = &((lldev->devh)->config.ring);
308 
309         buffer_size = mtu + XGE_HAL_MAC_HEADER_MAX_SIZE;
310 
311         if(lldev->enabled_lro)
312             (lldev->ifnetp)->if_capenable |= IFCAP_LRO;
313         else
314             (lldev->ifnetp)->if_capenable &= ~IFCAP_LRO;
315 
316         lldev->rxd_mbuf_cnt = lldev->buffer_mode;
317         if(lldev->buffer_mode == XGE_HAL_RING_QUEUE_BUFFER_MODE_2) {
318             XGE_SET_BUFFER_MODE_IN_RINGS(XGE_HAL_RING_QUEUE_BUFFER_MODE_3);
319             ring_config->scatter_mode = XGE_HAL_RING_QUEUE_SCATTER_MODE_B;
320         }
321         else {
322             XGE_SET_BUFFER_MODE_IN_RINGS(lldev->buffer_mode);
323             ring_config->scatter_mode = XGE_HAL_RING_QUEUE_SCATTER_MODE_A;
324         }
325         xge_rx_buffer_sizes_set(lldev, lldev->buffer_mode, mtu);
326 
327         xge_os_printf("%s: TSO %s", device_get_nameunit(lldev->device),
328             ((lldev->enabled_tso) ? "Enabled":"Disabled"));
329         xge_os_printf("%s: LRO %s", device_get_nameunit(lldev->device),
330             ((lldev->ifnetp)->if_capenable & IFCAP_LRO) ? "Enabled":"Disabled");
331         xge_os_printf("%s: Rx %d Buffer Mode Enabled",
332             device_get_nameunit(lldev->device), lldev->buffer_mode);
333 }
334 
335 /**
336  * xge_driver_initialize
337  * Initializes HAL driver (common for all devices)
338  *
339  * Returns
340  * XGE_HAL_OK if success
341  * XGE_HAL_ERR_BAD_DRIVER_CONFIG if driver configuration parameters are invalid
342  */
343 int
344 xge_driver_initialize(void)
345 {
346         xge_hal_uld_cbs_t       uld_callbacks;
347         xge_hal_driver_config_t driver_config;
348         xge_hal_status_e        status = XGE_HAL_OK;
349 
350         /* Initialize HAL driver */
351         if(!hal_driver_init_count) {
352             xge_os_memzero(&uld_callbacks, sizeof(xge_hal_uld_cbs_t));
353             xge_os_memzero(&driver_config, sizeof(xge_hal_driver_config_t));
354 
355             /*
356              * Initial and maximum size of the queue used to store the events
357              * like Link up/down (xge_hal_event_e)
358              */
359             driver_config.queue_size_initial = XGE_HAL_MIN_QUEUE_SIZE_INITIAL;
360             driver_config.queue_size_max     = XGE_HAL_MAX_QUEUE_SIZE_MAX;
361 
362             uld_callbacks.link_up   = xge_callback_link_up;
363             uld_callbacks.link_down = xge_callback_link_down;
364             uld_callbacks.crit_err  = xge_callback_crit_err;
365             uld_callbacks.event     = xge_callback_event;
366 
367             status = xge_hal_driver_initialize(&driver_config, &uld_callbacks);
368             if(status != XGE_HAL_OK) {
369                 XGE_EXIT_ON_ERR("xgeX: Initialization of HAL driver failed",
370                     xdi_out, status);
371             }
372         }
373         hal_driver_init_count = hal_driver_init_count + 1;
374 
375         xge_hal_driver_debug_module_mask_set(0xffffffff);
376         xge_hal_driver_debug_level_set(XGE_TRACE);
377 
378 xdi_out:
379         return status;
380 }
381 
382 /**
383  * xge_media_init
384  * Initializes, adds and sets media
385  *
386  * @devc Device Handle
387  */
388 void
389 xge_media_init(device_t devc)
390 {
391         xge_lldev_t *lldev = (xge_lldev_t *)device_get_softc(devc);
392 
393         /* Initialize Media */
394         ifmedia_init(&lldev->media, IFM_IMASK, xge_ifmedia_change,
395             xge_ifmedia_status);
396 
397         /* Add supported media */
398         ifmedia_add(&lldev->media, IFM_ETHER | IFM_1000_SX | IFM_FDX, 0, NULL);
399         ifmedia_add(&lldev->media, IFM_ETHER | IFM_1000_SX, 0, NULL);
400         ifmedia_add(&lldev->media, IFM_ETHER | IFM_AUTO,    0, NULL);
401         ifmedia_add(&lldev->media, IFM_ETHER | IFM_10G_SR,  0, NULL);
402         ifmedia_add(&lldev->media, IFM_ETHER | IFM_10G_LR,  0, NULL);
403 
404         /* Set media */
405         ifmedia_set(&lldev->media, IFM_ETHER | IFM_AUTO);
406 }
407 
408 /**
409  * xge_pci_space_save
410  * Save PCI configuration space
411  *
412  * @dev Device Handle
413  */
414 void
415 xge_pci_space_save(device_t dev)
416 {
417         struct pci_devinfo *dinfo = NULL;
418 
419         dinfo = device_get_ivars(dev);
420         xge_trace(XGE_TRACE, "Saving PCI configuration space");
421         pci_cfg_save(dev, dinfo, 0);
422 }
423 
424 /**
425  * xge_pci_space_restore
426  * Restore saved PCI configuration space
427  *
428  * @dev Device Handle
429  */
430 void
431 xge_pci_space_restore(device_t dev)
432 {
433         struct pci_devinfo *dinfo = NULL;
434 
435         dinfo = device_get_ivars(dev);
436         xge_trace(XGE_TRACE, "Restoring PCI configuration space");
437         pci_cfg_restore(dev, dinfo);
438 }
439 
440 /**
441  * xge_msi_info_save
442  * Save MSI info
443  *
444  * @lldev Per-adapter Data
445  */
446 void
447 xge_msi_info_save(xge_lldev_t * lldev)
448 {
449         xge_os_pci_read16(lldev->pdev, NULL,
450             xge_offsetof(xge_hal_pci_config_le_t, msi_control),
451             &lldev->msi_info.msi_control);
452         xge_os_pci_read32(lldev->pdev, NULL,
453             xge_offsetof(xge_hal_pci_config_le_t, msi_lower_address),
454             &lldev->msi_info.msi_lower_address);
455         xge_os_pci_read32(lldev->pdev, NULL,
456             xge_offsetof(xge_hal_pci_config_le_t, msi_higher_address),
457             &lldev->msi_info.msi_higher_address);
458         xge_os_pci_read16(lldev->pdev, NULL,
459             xge_offsetof(xge_hal_pci_config_le_t, msi_data),
460             &lldev->msi_info.msi_data);
461 }
462 
463 /**
464  * xge_msi_info_restore
465  * Restore saved MSI info
466  *
467  * @dev Device Handle
468  */
469 void
470 xge_msi_info_restore(xge_lldev_t *lldev)
471 {
472         /*
473          * If interface is made down and up, traffic fails. It was observed that
474          * MSI information were getting reset on down. Restoring them.
475          */
476         xge_os_pci_write16(lldev->pdev, NULL,
477             xge_offsetof(xge_hal_pci_config_le_t, msi_control),
478             lldev->msi_info.msi_control);
479 
480         xge_os_pci_write32(lldev->pdev, NULL,
481             xge_offsetof(xge_hal_pci_config_le_t, msi_lower_address),
482             lldev->msi_info.msi_lower_address);
483 
484         xge_os_pci_write32(lldev->pdev, NULL,
485             xge_offsetof(xge_hal_pci_config_le_t, msi_higher_address),
486             lldev->msi_info.msi_higher_address);
487 
488         xge_os_pci_write16(lldev->pdev, NULL,
489             xge_offsetof(xge_hal_pci_config_le_t, msi_data),
490             lldev->msi_info.msi_data);
491 }
492 
493 /**
494  * xge_init_mutex
495  * Initializes mutexes used in driver
496  *
497  * @lldev  Per-adapter Data
498  */
499 void
500 xge_mutex_init(xge_lldev_t *lldev)
501 {
502         int qindex;
503 
504         sprintf(lldev->mtx_name_drv, "%s_drv",
505             device_get_nameunit(lldev->device));
506         mtx_init(&lldev->mtx_drv, lldev->mtx_name_drv, MTX_NETWORK_LOCK,
507             MTX_DEF);
508 
509         for(qindex = 0; qindex < XGE_FIFO_COUNT; qindex++) {
510             sprintf(lldev->mtx_name_tx[qindex], "%s_tx_%d",
511                 device_get_nameunit(lldev->device), qindex);
512             mtx_init(&lldev->mtx_tx[qindex], lldev->mtx_name_tx[qindex], NULL,
513                 MTX_DEF);
514         }
515 }
516 
517 /**
518  * xge_mutex_destroy
519  * Destroys mutexes used in driver
520  *
521  * @lldev Per-adapter Data
522  */
523 void
524 xge_mutex_destroy(xge_lldev_t *lldev)
525 {
526         int qindex;
527 
528         for(qindex = 0; qindex < XGE_FIFO_COUNT; qindex++)
529             mtx_destroy(&lldev->mtx_tx[qindex]);
530         mtx_destroy(&lldev->mtx_drv);
531 }
532 
533 /**
534  * xge_print_info
535  * Print device and driver information
536  *
537  * @lldev Per-adapter Data
538  */
539 void
540 xge_print_info(xge_lldev_t *lldev)
541 {
542         device_t dev = lldev->device;
543         xge_hal_device_t *hldev = lldev->devh;
544         xge_hal_status_e status = XGE_HAL_OK;
545         u64 val64 = 0;
546         const char *xge_pci_bus_speeds[17] = {
547             "PCI 33MHz Bus",
548             "PCI 66MHz Bus",
549             "PCIX(M1) 66MHz Bus",
550             "PCIX(M1) 100MHz Bus",
551             "PCIX(M1) 133MHz Bus",
552             "PCIX(M2) 133MHz Bus",
553             "PCIX(M2) 200MHz Bus",
554             "PCIX(M2) 266MHz Bus",
555             "PCIX(M1) Reserved",
556             "PCIX(M1) 66MHz Bus (Not Supported)",
557             "PCIX(M1) 100MHz Bus (Not Supported)",
558             "PCIX(M1) 133MHz Bus (Not Supported)",
559             "PCIX(M2) Reserved",
560             "PCIX 533 Reserved",
561             "PCI Basic Mode",
562             "PCIX Basic Mode",
563             "PCI Invalid Mode"
564         };
565 
566         xge_os_printf("%s: Xframe%s %s Revision %d Driver v%s",
567             device_get_nameunit(dev),
568             ((hldev->device_id == XGE_PCI_DEVICE_ID_XENA_2) ? "I" : "II"),
569             hldev->vpd_data.product_name, hldev->revision, XGE_DRIVER_VERSION);
570         xge_os_printf("%s: Serial Number %s",
571             device_get_nameunit(dev), hldev->vpd_data.serial_num);
572 
573         if(pci_get_device(dev) == XGE_PCI_DEVICE_ID_HERC_2) {
574             status = xge_hal_mgmt_reg_read(hldev, 0,
575                 xge_offsetof(xge_hal_pci_bar0_t, pci_info), &val64);
576             if(status != XGE_HAL_OK)
577                 xge_trace(XGE_ERR, "Error for getting bus speed");
578 
579             xge_os_printf("%s: Adapter is on %s bit %s",
580                 device_get_nameunit(dev), ((val64 & BIT(8)) ? "32":"64"),
581                 (xge_pci_bus_speeds[((val64 & XGE_HAL_PCI_INFO) >> 60)]));
582         }
583 
584         xge_os_printf("%s: Using %s Interrupts",
585             device_get_nameunit(dev),
586             (lldev->enabled_msi == XGE_HAL_INTR_MODE_MSI) ? "MSI":"Line");
587 }
588 
589 /**
590  * xge_create_dma_tags
591  * Creates DMA tags for both Tx and Rx
592  *
593  * @dev Device Handle
594  *
595  * Returns XGE_HAL_OK or XGE_HAL_FAIL (if errors)
596  */
597 xge_hal_status_e
598 xge_create_dma_tags(device_t dev)
599 {
600         xge_lldev_t *lldev = (xge_lldev_t *)device_get_softc(dev);
601         xge_hal_status_e status = XGE_HAL_FAIL;
602         int mtu = (lldev->ifnetp)->if_mtu, maxsize;
603 
604         /* DMA tag for Tx */
605         status = bus_dma_tag_create(
606             bus_get_dma_tag(dev),                /* Parent                    */
607             PAGE_SIZE,                           /* Alignment                 */
608             0,                                   /* Bounds                    */
609             BUS_SPACE_MAXADDR,                   /* Low Address               */
610             BUS_SPACE_MAXADDR,                   /* High Address              */
611             NULL,                                /* Filter Function           */
612             NULL,                                /* Filter Function Arguments */
613             MCLBYTES * XGE_MAX_SEGS,             /* Maximum Size              */
614             XGE_MAX_SEGS,                        /* Number of Segments        */
615             MCLBYTES,                            /* Maximum Segment Size      */
616             BUS_DMA_ALLOCNOW,                    /* Flags                     */
617             NULL,                                /* Lock Function             */
618             NULL,                                /* Lock Function Arguments   */
619             (&lldev->dma_tag_tx));               /* DMA Tag                   */
620         if(status != 0)
621             goto _exit;
622 
623         maxsize = mtu + XGE_HAL_MAC_HEADER_MAX_SIZE;
624         if(maxsize <= MCLBYTES) {
625             maxsize = MCLBYTES;
626         }
627         else {
628             if(lldev->buffer_mode == XGE_HAL_RING_QUEUE_BUFFER_MODE_5)
629                 maxsize = MJUMPAGESIZE;
630             else
631                 maxsize = (maxsize <= MJUMPAGESIZE) ? MJUMPAGESIZE : MJUM9BYTES;
632         }
633         
634         /* DMA tag for Rx */
635         status = bus_dma_tag_create(
636             bus_get_dma_tag(dev),                /* Parent                    */
637             PAGE_SIZE,                           /* Alignment                 */
638             0,                                   /* Bounds                    */
639             BUS_SPACE_MAXADDR,                   /* Low Address               */
640             BUS_SPACE_MAXADDR,                   /* High Address              */
641             NULL,                                /* Filter Function           */
642             NULL,                                /* Filter Function Arguments */
643             maxsize,                             /* Maximum Size              */
644             1,                                   /* Number of Segments        */
645             maxsize,                             /* Maximum Segment Size      */
646             BUS_DMA_ALLOCNOW,                    /* Flags                     */
647             NULL,                                /* Lock Function             */
648             NULL,                                /* Lock Function Arguments   */
649             (&lldev->dma_tag_rx));               /* DMA Tag                   */
650         if(status != 0)
651             goto _exit1;
652 
653         status = bus_dmamap_create(lldev->dma_tag_rx, BUS_DMA_NOWAIT,
654             &lldev->extra_dma_map);
655         if(status != 0)
656             goto _exit2;
657 
658         status = XGE_HAL_OK;
659         goto _exit;
660 
661 _exit2:
662         status = bus_dma_tag_destroy(lldev->dma_tag_rx);
663         if(status != 0)
664             xge_trace(XGE_ERR, "Rx DMA tag destroy failed");
665 _exit1:
666         status = bus_dma_tag_destroy(lldev->dma_tag_tx);
667         if(status != 0)
668             xge_trace(XGE_ERR, "Tx DMA tag destroy failed");
669         status = XGE_HAL_FAIL;
670 _exit:
671         return status;
672 }
673 
674 /**
675  * xge_confirm_changes
676  * Disables and Enables interface to apply requested change
677  *
678  * @lldev Per-adapter Data
679  * @mtu_set Is it called for changing MTU? (Yes: 1, No: 0)
680  *
681  * Returns 0 or Error Number
682  */
683 void
684 xge_confirm_changes(xge_lldev_t *lldev, xge_option_e option)
685 {
686         if(lldev->initialized == 0) goto _exit1;
687 
688         mtx_lock(&lldev->mtx_drv);
689         if_down(lldev->ifnetp);
690         xge_device_stop(lldev, XGE_HAL_CHANNEL_OC_NORMAL);
691 
692         if(option == XGE_SET_MTU)
693             (lldev->ifnetp)->if_mtu = lldev->mtu;
694         else
695             xge_buffer_mode_init(lldev, lldev->mtu);
696 
697         xge_device_init(lldev, XGE_HAL_CHANNEL_OC_NORMAL);
698         if_up(lldev->ifnetp);
699         mtx_unlock(&lldev->mtx_drv);
700         goto _exit;
701 
702 _exit1:
703         /* Request was to change MTU and device not initialized */
704         if(option == XGE_SET_MTU) {
705             (lldev->ifnetp)->if_mtu = lldev->mtu;
706             xge_buffer_mode_init(lldev, lldev->mtu);
707         }
708 _exit:
709         return;
710 }
711 
712 /**
713  * xge_change_lro_status
714  * Enable/Disable LRO feature
715  *
716  * @SYSCTL_HANDLER_ARGS sysctl_oid structure with arguments
717  *
718  * Returns 0 or error number.
719  */
720 static int
721 xge_change_lro_status(SYSCTL_HANDLER_ARGS)
722 {
723         xge_lldev_t *lldev = (xge_lldev_t *)arg1;
724         int request = lldev->enabled_lro, status = XGE_HAL_OK;
725 
726         status = sysctl_handle_int(oidp, &request, arg2, req);
727         if((status != XGE_HAL_OK) || (!req->newptr))
728             goto _exit;
729 
730         if((request < 0) || (request > 1)) {
731             status = EINVAL;
732             goto _exit;
733         }
734 
735         /* Return if current and requested states are same */
736         if(request == lldev->enabled_lro){
737             xge_trace(XGE_ERR, "LRO is already %s",
738                 ((request) ? "enabled" : "disabled"));
739             goto _exit;
740         }
741 
742         lldev->enabled_lro = request;
743         xge_confirm_changes(lldev, XGE_CHANGE_LRO);
744         arg2 = lldev->enabled_lro;
745 
746 _exit:
747         return status;
748 }
749 
750 /**
751  * xge_add_sysctl_handlers
752  * Registers sysctl parameter value update handlers
753  *
754  * @lldev Per-adapter data
755  */
756 void
757 xge_add_sysctl_handlers(xge_lldev_t *lldev)
758 {
759         struct sysctl_ctx_list *context_list =
760             device_get_sysctl_ctx(lldev->device);
761         struct sysctl_oid *oid = device_get_sysctl_tree(lldev->device);
762 
763         SYSCTL_ADD_PROC(context_list, SYSCTL_CHILDREN(oid), OID_AUTO,
764             "enable_lro", CTLTYPE_INT | CTLFLAG_RW, lldev, 0,
765             xge_change_lro_status, "I", "Enable or disable LRO feature");
766 }
767 
768 /**
769  * xge_attach
770  * Connects driver to the system if probe was success
771  *
772  * @dev Device Handle
773  */
774 int
775 xge_attach(device_t dev)
776 {
777         xge_hal_device_config_t *device_config;
778         xge_hal_device_attr_t   attr;
779         xge_lldev_t             *lldev;
780         xge_hal_device_t        *hldev;
781         xge_pci_info_t          *pci_info;
782         struct ifnet            *ifnetp;
783         int                     rid, rid0, rid1, error;
784         int                     msi_count = 0, status = XGE_HAL_OK;
785         int                     enable_msi = XGE_HAL_INTR_MODE_IRQLINE;
786 
787         device_config = xge_os_malloc(NULL, sizeof(xge_hal_device_config_t));
788         if(!device_config) {
789             XGE_EXIT_ON_ERR("Memory allocation for device configuration failed",
790                 attach_out_config, ENOMEM);
791         }
792 
793         lldev = (xge_lldev_t *) device_get_softc(dev);
794         if(!lldev) {
795             XGE_EXIT_ON_ERR("Adapter softc is NULL", attach_out, ENOMEM);
796         }
797         lldev->device = dev;
798 
799         xge_mutex_init(lldev);
800 
801         error = xge_driver_initialize();
802         if(error != XGE_HAL_OK) {
803             xge_resources_free(dev, xge_free_mutex);
804             XGE_EXIT_ON_ERR("Initializing driver failed", attach_out, ENXIO);
805         }
806 
807         /* HAL device */
808         hldev =
809             (xge_hal_device_t *)xge_os_malloc(NULL, sizeof(xge_hal_device_t));
810         if(!hldev) {
811             xge_resources_free(dev, xge_free_terminate_hal_driver);
812             XGE_EXIT_ON_ERR("Memory allocation for HAL device failed",
813                 attach_out, ENOMEM);
814         }
815         lldev->devh = hldev;
816 
817         /* Our private structure */
818         pci_info =
819             (xge_pci_info_t*) xge_os_malloc(NULL, sizeof(xge_pci_info_t));
820         if(!pci_info) {
821             xge_resources_free(dev, xge_free_hal_device);
822             XGE_EXIT_ON_ERR("Memory allocation for PCI info. failed",
823                 attach_out, ENOMEM);
824         }
825         lldev->pdev      = pci_info;
826         pci_info->device = dev;
827 
828         /* Set bus master */
829         pci_enable_busmaster(dev);
830 
831         /* Get virtual address for BAR0 */
832         rid0 = PCIR_BAR(0);
833         pci_info->regmap0 = bus_alloc_resource_any(dev, SYS_RES_MEMORY, &rid0,
834             RF_ACTIVE);
835         if(pci_info->regmap0 == NULL) {
836             xge_resources_free(dev, xge_free_pci_info);
837             XGE_EXIT_ON_ERR("Bus resource allocation for BAR0 failed",
838                 attach_out, ENOMEM);
839         }
840         attr.bar0 = (char *)pci_info->regmap0;
841 
842         pci_info->bar0resource = (xge_bus_resource_t*)
843             xge_os_malloc(NULL, sizeof(xge_bus_resource_t));
844         if(pci_info->bar0resource == NULL) {
845             xge_resources_free(dev, xge_free_bar0);
846             XGE_EXIT_ON_ERR("Memory allocation for BAR0 Resources failed",
847                 attach_out, ENOMEM);
848         }
849         ((xge_bus_resource_t *)(pci_info->bar0resource))->bus_tag =
850             rman_get_bustag(pci_info->regmap0);
851         ((xge_bus_resource_t *)(pci_info->bar0resource))->bus_handle =
852             rman_get_bushandle(pci_info->regmap0);
853         ((xge_bus_resource_t *)(pci_info->bar0resource))->bar_start_addr =
854             pci_info->regmap0;
855 
856         /* Get virtual address for BAR1 */
857         rid1 = PCIR_BAR(2);
858         pci_info->regmap1 = bus_alloc_resource_any(dev, SYS_RES_MEMORY, &rid1,
859             RF_ACTIVE);
860         if(pci_info->regmap1 == NULL) {
861             xge_resources_free(dev, xge_free_bar0_resource);
862             XGE_EXIT_ON_ERR("Bus resource allocation for BAR1 failed",
863                 attach_out, ENOMEM);
864         }
865         attr.bar1 = (char *)pci_info->regmap1;
866 
867         pci_info->bar1resource = (xge_bus_resource_t*)
868             xge_os_malloc(NULL, sizeof(xge_bus_resource_t));
869         if(pci_info->bar1resource == NULL) {
870             xge_resources_free(dev, xge_free_bar1);
871             XGE_EXIT_ON_ERR("Memory allocation for BAR1 Resources failed",
872                 attach_out, ENOMEM);
873         }
874         ((xge_bus_resource_t *)(pci_info->bar1resource))->bus_tag =
875             rman_get_bustag(pci_info->regmap1);
876         ((xge_bus_resource_t *)(pci_info->bar1resource))->bus_handle =
877             rman_get_bushandle(pci_info->regmap1);
878         ((xge_bus_resource_t *)(pci_info->bar1resource))->bar_start_addr =
879             pci_info->regmap1;
880 
881         /* Save PCI config space */
882         xge_pci_space_save(dev);
883 
884         attr.regh0 = (xge_bus_resource_t *) pci_info->bar0resource;
885         attr.regh1 = (xge_bus_resource_t *) pci_info->bar1resource;
886         attr.irqh  = lldev->irqhandle;
887         attr.cfgh  = pci_info;
888         attr.pdev  = pci_info;
889 
890         /* Initialize device configuration parameters */
891         xge_init_params(device_config, dev);
892 
893         rid = 0;
894         if(lldev->enabled_msi) {
895             /* Number of MSI messages supported by device */
896             msi_count = pci_msi_count(dev);
897             if(msi_count > 1) {
898                 /* Device supports MSI */
899                 if(bootverbose) {
900                     xge_trace(XGE_ERR, "MSI count: %d", msi_count);
901                     xge_trace(XGE_ERR, "Now, driver supporting 1 message");
902                 }
903                 msi_count = 1;
904                 error = pci_alloc_msi(dev, &msi_count);
905                 if(error == 0) {
906                     if(bootverbose)
907                         xge_trace(XGE_ERR, "Allocated messages: %d", msi_count);
908                     enable_msi = XGE_HAL_INTR_MODE_MSI;
909                     rid = 1;
910                 }
911                 else {
912                     if(bootverbose)
913                         xge_trace(XGE_ERR, "pci_alloc_msi failed, %d", error);
914                 }
915             }
916         }
917         lldev->enabled_msi = enable_msi;
918 
919         /* Allocate resource for irq */
920         lldev->irq = bus_alloc_resource_any(dev, SYS_RES_IRQ, &rid,
921             (RF_SHAREABLE | RF_ACTIVE));
922         if(lldev->irq == NULL) {
923             xge_trace(XGE_ERR, "Allocating irq resource for %s failed",
924                 ((rid == 0) ? "line interrupt" : "MSI"));
925             if(rid == 1) {
926                 error = pci_release_msi(dev);
927                 if(error != 0) {
928                     xge_trace(XGE_ERR, "Releasing MSI resources failed %d",
929                         error);
930                     xge_trace(XGE_ERR, "Requires reboot to use MSI again");
931                 }
932                 xge_trace(XGE_ERR, "Trying line interrupts");
933                 rid = 0;
934                 lldev->enabled_msi = XGE_HAL_INTR_MODE_IRQLINE;
935                 lldev->irq = bus_alloc_resource_any(dev, SYS_RES_IRQ, &rid,
936                     (RF_SHAREABLE | RF_ACTIVE));
937             }
938             if(lldev->irq == NULL) {
939                 xge_trace(XGE_ERR, "Allocating irq resource failed");
940                 xge_resources_free(dev, xge_free_bar1_resource);
941                 status = ENOMEM;
942                 goto attach_out;
943             }
944         }
945 
946         device_config->intr_mode = lldev->enabled_msi;
947         if(bootverbose) {
948             xge_trace(XGE_TRACE, "rid: %d, Mode: %d, MSI count: %d", rid,
949                 lldev->enabled_msi, msi_count);
950         }
951 
952         /* Initialize HAL device */
953         error = xge_hal_device_initialize(hldev, &attr, device_config);
954         if(error != XGE_HAL_OK) {
955             xge_resources_free(dev, xge_free_irq_resource);
956             XGE_EXIT_ON_ERR("Initializing HAL device failed", attach_out,
957                 ENXIO);
958         }
959 
960         xge_hal_device_private_set(hldev, lldev);
961 
962         error = xge_interface_setup(dev);
963         if(error != 0) {
964             status = error;
965             goto attach_out;
966         }
967 
968         ifnetp         = lldev->ifnetp;
969         ifnetp->if_mtu = device_config->mtu;
970 
971         xge_media_init(dev);
972 
973         /* Associate interrupt handler with the device */
974         if(lldev->enabled_msi ==