1*4882a593Smuzhiyun // SPDX-License-Identifier: GPL-2.0
2*4882a593Smuzhiyun /* Copyright(c) 1999 - 2008 Intel Corporation. */
3*4882a593Smuzhiyun
4*4882a593Smuzhiyun #define pr_fmt(fmt) KBUILD_MODNAME ": " fmt
5*4882a593Smuzhiyun
6*4882a593Smuzhiyun #include "ixgb.h"
7*4882a593Smuzhiyun
8*4882a593Smuzhiyun /* This is the only thing that needs to be changed to adjust the
9*4882a593Smuzhiyun * maximum number of ports that the driver can manage.
10*4882a593Smuzhiyun */
11*4882a593Smuzhiyun
12*4882a593Smuzhiyun #define IXGB_MAX_NIC 8
13*4882a593Smuzhiyun
14*4882a593Smuzhiyun #define OPTION_UNSET -1
15*4882a593Smuzhiyun #define OPTION_DISABLED 0
16*4882a593Smuzhiyun #define OPTION_ENABLED 1
17*4882a593Smuzhiyun
18*4882a593Smuzhiyun /* All parameters are treated the same, as an integer array of values.
19*4882a593Smuzhiyun * This macro just reduces the need to repeat the same declaration code
20*4882a593Smuzhiyun * over and over (plus this helps to avoid typo bugs).
21*4882a593Smuzhiyun */
22*4882a593Smuzhiyun
23*4882a593Smuzhiyun #define IXGB_PARAM_INIT { [0 ... IXGB_MAX_NIC] = OPTION_UNSET }
24*4882a593Smuzhiyun #define IXGB_PARAM(X, desc) \
25*4882a593Smuzhiyun static int X[IXGB_MAX_NIC+1] \
26*4882a593Smuzhiyun = IXGB_PARAM_INIT; \
27*4882a593Smuzhiyun static unsigned int num_##X = 0; \
28*4882a593Smuzhiyun module_param_array_named(X, X, int, &num_##X, 0); \
29*4882a593Smuzhiyun MODULE_PARM_DESC(X, desc);
30*4882a593Smuzhiyun
31*4882a593Smuzhiyun /* Transmit Descriptor Count
32*4882a593Smuzhiyun *
33*4882a593Smuzhiyun * Valid Range: 64-4096
34*4882a593Smuzhiyun *
35*4882a593Smuzhiyun * Default Value: 256
36*4882a593Smuzhiyun */
37*4882a593Smuzhiyun
38*4882a593Smuzhiyun IXGB_PARAM(TxDescriptors, "Number of transmit descriptors");
39*4882a593Smuzhiyun
40*4882a593Smuzhiyun /* Receive Descriptor Count
41*4882a593Smuzhiyun *
42*4882a593Smuzhiyun * Valid Range: 64-4096
43*4882a593Smuzhiyun *
44*4882a593Smuzhiyun * Default Value: 1024
45*4882a593Smuzhiyun */
46*4882a593Smuzhiyun
47*4882a593Smuzhiyun IXGB_PARAM(RxDescriptors, "Number of receive descriptors");
48*4882a593Smuzhiyun
49*4882a593Smuzhiyun /* User Specified Flow Control Override
50*4882a593Smuzhiyun *
51*4882a593Smuzhiyun * Valid Range: 0-3
52*4882a593Smuzhiyun * - 0 - No Flow Control
53*4882a593Smuzhiyun * - 1 - Rx only, respond to PAUSE frames but do not generate them
54*4882a593Smuzhiyun * - 2 - Tx only, generate PAUSE frames but ignore them on receive
55*4882a593Smuzhiyun * - 3 - Full Flow Control Support
56*4882a593Smuzhiyun *
57*4882a593Smuzhiyun * Default Value: 2 - Tx only (silicon bug avoidance)
58*4882a593Smuzhiyun */
59*4882a593Smuzhiyun
60*4882a593Smuzhiyun IXGB_PARAM(FlowControl, "Flow Control setting");
61*4882a593Smuzhiyun
62*4882a593Smuzhiyun /* XsumRX - Receive Checksum Offload Enable/Disable
63*4882a593Smuzhiyun *
64*4882a593Smuzhiyun * Valid Range: 0, 1
65*4882a593Smuzhiyun * - 0 - disables all checksum offload
66*4882a593Smuzhiyun * - 1 - enables receive IP/TCP/UDP checksum offload
67*4882a593Smuzhiyun * on 82597 based NICs
68*4882a593Smuzhiyun *
69*4882a593Smuzhiyun * Default Value: 1
70*4882a593Smuzhiyun */
71*4882a593Smuzhiyun
72*4882a593Smuzhiyun IXGB_PARAM(XsumRX, "Disable or enable Receive Checksum offload");
73*4882a593Smuzhiyun
74*4882a593Smuzhiyun /* Transmit Interrupt Delay in units of 0.8192 microseconds
75*4882a593Smuzhiyun *
76*4882a593Smuzhiyun * Valid Range: 0-65535
77*4882a593Smuzhiyun *
78*4882a593Smuzhiyun * Default Value: 32
79*4882a593Smuzhiyun */
80*4882a593Smuzhiyun
81*4882a593Smuzhiyun IXGB_PARAM(TxIntDelay, "Transmit Interrupt Delay");
82*4882a593Smuzhiyun
83*4882a593Smuzhiyun /* Receive Interrupt Delay in units of 0.8192 microseconds
84*4882a593Smuzhiyun *
85*4882a593Smuzhiyun * Valid Range: 0-65535
86*4882a593Smuzhiyun *
87*4882a593Smuzhiyun * Default Value: 72
88*4882a593Smuzhiyun */
89*4882a593Smuzhiyun
90*4882a593Smuzhiyun IXGB_PARAM(RxIntDelay, "Receive Interrupt Delay");
91*4882a593Smuzhiyun
92*4882a593Smuzhiyun /* Receive Flow control high threshold (when we send a pause frame)
93*4882a593Smuzhiyun * (FCRTH)
94*4882a593Smuzhiyun *
95*4882a593Smuzhiyun * Valid Range: 1,536 - 262,136 (0x600 - 0x3FFF8, 8 byte granularity)
96*4882a593Smuzhiyun *
97*4882a593Smuzhiyun * Default Value: 196,608 (0x30000)
98*4882a593Smuzhiyun */
99*4882a593Smuzhiyun
100*4882a593Smuzhiyun IXGB_PARAM(RxFCHighThresh, "Receive Flow Control High Threshold");
101*4882a593Smuzhiyun
102*4882a593Smuzhiyun /* Receive Flow control low threshold (when we send a resume frame)
103*4882a593Smuzhiyun * (FCRTL)
104*4882a593Smuzhiyun *
105*4882a593Smuzhiyun * Valid Range: 64 - 262,136 (0x40 - 0x3FFF8, 8 byte granularity)
106*4882a593Smuzhiyun * must be less than high threshold by at least 8 bytes
107*4882a593Smuzhiyun *
108*4882a593Smuzhiyun * Default Value: 163,840 (0x28000)
109*4882a593Smuzhiyun */
110*4882a593Smuzhiyun
111*4882a593Smuzhiyun IXGB_PARAM(RxFCLowThresh, "Receive Flow Control Low Threshold");
112*4882a593Smuzhiyun
113*4882a593Smuzhiyun /* Flow control request timeout (how long to pause the link partner's tx)
114*4882a593Smuzhiyun * (PAP 15:0)
115*4882a593Smuzhiyun *
116*4882a593Smuzhiyun * Valid Range: 1 - 65535
117*4882a593Smuzhiyun *
118*4882a593Smuzhiyun * Default Value: 65535 (0xffff) (we'll send an xon if we recover)
119*4882a593Smuzhiyun */
120*4882a593Smuzhiyun
121*4882a593Smuzhiyun IXGB_PARAM(FCReqTimeout, "Flow Control Request Timeout");
122*4882a593Smuzhiyun
123*4882a593Smuzhiyun /* Interrupt Delay Enable
124*4882a593Smuzhiyun *
125*4882a593Smuzhiyun * Valid Range: 0, 1
126*4882a593Smuzhiyun *
127*4882a593Smuzhiyun * - 0 - disables transmit interrupt delay
128*4882a593Smuzhiyun * - 1 - enables transmmit interrupt delay
129*4882a593Smuzhiyun *
130*4882a593Smuzhiyun * Default Value: 1
131*4882a593Smuzhiyun */
132*4882a593Smuzhiyun
133*4882a593Smuzhiyun IXGB_PARAM(IntDelayEnable, "Transmit Interrupt Delay Enable");
134*4882a593Smuzhiyun
135*4882a593Smuzhiyun
136*4882a593Smuzhiyun #define DEFAULT_TIDV 32
137*4882a593Smuzhiyun #define MAX_TIDV 0xFFFF
138*4882a593Smuzhiyun #define MIN_TIDV 0
139*4882a593Smuzhiyun
140*4882a593Smuzhiyun #define DEFAULT_RDTR 72
141*4882a593Smuzhiyun #define MAX_RDTR 0xFFFF
142*4882a593Smuzhiyun #define MIN_RDTR 0
143*4882a593Smuzhiyun
144*4882a593Smuzhiyun #define XSUMRX_DEFAULT OPTION_ENABLED
145*4882a593Smuzhiyun
146*4882a593Smuzhiyun #define DEFAULT_FCRTL 0x28000
147*4882a593Smuzhiyun #define DEFAULT_FCRTH 0x30000
148*4882a593Smuzhiyun #define MIN_FCRTL 0
149*4882a593Smuzhiyun #define MAX_FCRTL 0x3FFE8
150*4882a593Smuzhiyun #define MIN_FCRTH 8
151*4882a593Smuzhiyun #define MAX_FCRTH 0x3FFF0
152*4882a593Smuzhiyun
153*4882a593Smuzhiyun #define MIN_FCPAUSE 1
154*4882a593Smuzhiyun #define MAX_FCPAUSE 0xffff
155*4882a593Smuzhiyun #define DEFAULT_FCPAUSE 0xFFFF /* this may be too long */
156*4882a593Smuzhiyun
157*4882a593Smuzhiyun struct ixgb_option {
158*4882a593Smuzhiyun enum { enable_option, range_option, list_option } type;
159*4882a593Smuzhiyun const char *name;
160*4882a593Smuzhiyun const char *err;
161*4882a593Smuzhiyun int def;
162*4882a593Smuzhiyun union {
163*4882a593Smuzhiyun struct { /* range_option info */
164*4882a593Smuzhiyun int min;
165*4882a593Smuzhiyun int max;
166*4882a593Smuzhiyun } r;
167*4882a593Smuzhiyun struct { /* list_option info */
168*4882a593Smuzhiyun int nr;
169*4882a593Smuzhiyun const struct ixgb_opt_list {
170*4882a593Smuzhiyun int i;
171*4882a593Smuzhiyun const char *str;
172*4882a593Smuzhiyun } *p;
173*4882a593Smuzhiyun } l;
174*4882a593Smuzhiyun } arg;
175*4882a593Smuzhiyun };
176*4882a593Smuzhiyun
177*4882a593Smuzhiyun static int
ixgb_validate_option(unsigned int * value,const struct ixgb_option * opt)178*4882a593Smuzhiyun ixgb_validate_option(unsigned int *value, const struct ixgb_option *opt)
179*4882a593Smuzhiyun {
180*4882a593Smuzhiyun if (*value == OPTION_UNSET) {
181*4882a593Smuzhiyun *value = opt->def;
182*4882a593Smuzhiyun return 0;
183*4882a593Smuzhiyun }
184*4882a593Smuzhiyun
185*4882a593Smuzhiyun switch (opt->type) {
186*4882a593Smuzhiyun case enable_option:
187*4882a593Smuzhiyun switch (*value) {
188*4882a593Smuzhiyun case OPTION_ENABLED:
189*4882a593Smuzhiyun pr_info("%s Enabled\n", opt->name);
190*4882a593Smuzhiyun return 0;
191*4882a593Smuzhiyun case OPTION_DISABLED:
192*4882a593Smuzhiyun pr_info("%s Disabled\n", opt->name);
193*4882a593Smuzhiyun return 0;
194*4882a593Smuzhiyun }
195*4882a593Smuzhiyun break;
196*4882a593Smuzhiyun case range_option:
197*4882a593Smuzhiyun if (*value >= opt->arg.r.min && *value <= opt->arg.r.max) {
198*4882a593Smuzhiyun pr_info("%s set to %i\n", opt->name, *value);
199*4882a593Smuzhiyun return 0;
200*4882a593Smuzhiyun }
201*4882a593Smuzhiyun break;
202*4882a593Smuzhiyun case list_option: {
203*4882a593Smuzhiyun int i;
204*4882a593Smuzhiyun const struct ixgb_opt_list *ent;
205*4882a593Smuzhiyun
206*4882a593Smuzhiyun for (i = 0; i < opt->arg.l.nr; i++) {
207*4882a593Smuzhiyun ent = &opt->arg.l.p[i];
208*4882a593Smuzhiyun if (*value == ent->i) {
209*4882a593Smuzhiyun if (ent->str[0] != '\0')
210*4882a593Smuzhiyun pr_info("%s\n", ent->str);
211*4882a593Smuzhiyun return 0;
212*4882a593Smuzhiyun }
213*4882a593Smuzhiyun }
214*4882a593Smuzhiyun }
215*4882a593Smuzhiyun break;
216*4882a593Smuzhiyun default:
217*4882a593Smuzhiyun BUG();
218*4882a593Smuzhiyun }
219*4882a593Smuzhiyun
220*4882a593Smuzhiyun pr_info("Invalid %s specified (%i) %s\n", opt->name, *value, opt->err);
221*4882a593Smuzhiyun *value = opt->def;
222*4882a593Smuzhiyun return -1;
223*4882a593Smuzhiyun }
224*4882a593Smuzhiyun
225*4882a593Smuzhiyun /**
226*4882a593Smuzhiyun * ixgb_check_options - Range Checking for Command Line Parameters
227*4882a593Smuzhiyun * @adapter: board private structure
228*4882a593Smuzhiyun *
229*4882a593Smuzhiyun * This routine checks all command line parameters for valid user
230*4882a593Smuzhiyun * input. If an invalid value is given, or if no user specified
231*4882a593Smuzhiyun * value exists, a default value is used. The final value is stored
232*4882a593Smuzhiyun * in a variable in the adapter structure.
233*4882a593Smuzhiyun **/
234*4882a593Smuzhiyun
235*4882a593Smuzhiyun void
ixgb_check_options(struct ixgb_adapter * adapter)236*4882a593Smuzhiyun ixgb_check_options(struct ixgb_adapter *adapter)
237*4882a593Smuzhiyun {
238*4882a593Smuzhiyun int bd = adapter->bd_number;
239*4882a593Smuzhiyun if (bd >= IXGB_MAX_NIC) {
240*4882a593Smuzhiyun pr_notice("Warning: no configuration for board #%i\n", bd);
241*4882a593Smuzhiyun pr_notice("Using defaults for all values\n");
242*4882a593Smuzhiyun }
243*4882a593Smuzhiyun
244*4882a593Smuzhiyun { /* Transmit Descriptor Count */
245*4882a593Smuzhiyun static const struct ixgb_option opt = {
246*4882a593Smuzhiyun .type = range_option,
247*4882a593Smuzhiyun .name = "Transmit Descriptors",
248*4882a593Smuzhiyun .err = "using default of " __MODULE_STRING(DEFAULT_TXD),
249*4882a593Smuzhiyun .def = DEFAULT_TXD,
250*4882a593Smuzhiyun .arg = { .r = { .min = MIN_TXD,
251*4882a593Smuzhiyun .max = MAX_TXD}}
252*4882a593Smuzhiyun };
253*4882a593Smuzhiyun struct ixgb_desc_ring *tx_ring = &adapter->tx_ring;
254*4882a593Smuzhiyun
255*4882a593Smuzhiyun if (num_TxDescriptors > bd) {
256*4882a593Smuzhiyun tx_ring->count = TxDescriptors[bd];
257*4882a593Smuzhiyun ixgb_validate_option(&tx_ring->count, &opt);
258*4882a593Smuzhiyun } else {
259*4882a593Smuzhiyun tx_ring->count = opt.def;
260*4882a593Smuzhiyun }
261*4882a593Smuzhiyun tx_ring->count = ALIGN(tx_ring->count, IXGB_REQ_TX_DESCRIPTOR_MULTIPLE);
262*4882a593Smuzhiyun }
263*4882a593Smuzhiyun { /* Receive Descriptor Count */
264*4882a593Smuzhiyun static const struct ixgb_option opt = {
265*4882a593Smuzhiyun .type = range_option,
266*4882a593Smuzhiyun .name = "Receive Descriptors",
267*4882a593Smuzhiyun .err = "using default of " __MODULE_STRING(DEFAULT_RXD),
268*4882a593Smuzhiyun .def = DEFAULT_RXD,
269*4882a593Smuzhiyun .arg = { .r = { .min = MIN_RXD,
270*4882a593Smuzhiyun .max = MAX_RXD}}
271*4882a593Smuzhiyun };
272*4882a593Smuzhiyun struct ixgb_desc_ring *rx_ring = &adapter->rx_ring;
273*4882a593Smuzhiyun
274*4882a593Smuzhiyun if (num_RxDescriptors > bd) {
275*4882a593Smuzhiyun rx_ring->count = RxDescriptors[bd];
276*4882a593Smuzhiyun ixgb_validate_option(&rx_ring->count, &opt);
277*4882a593Smuzhiyun } else {
278*4882a593Smuzhiyun rx_ring->count = opt.def;
279*4882a593Smuzhiyun }
280*4882a593Smuzhiyun rx_ring->count = ALIGN(rx_ring->count, IXGB_REQ_RX_DESCRIPTOR_MULTIPLE);
281*4882a593Smuzhiyun }
282*4882a593Smuzhiyun { /* Receive Checksum Offload Enable */
283*4882a593Smuzhiyun static const struct ixgb_option opt = {
284*4882a593Smuzhiyun .type = enable_option,
285*4882a593Smuzhiyun .name = "Receive Checksum Offload",
286*4882a593Smuzhiyun .err = "defaulting to Enabled",
287*4882a593Smuzhiyun .def = OPTION_ENABLED
288*4882a593Smuzhiyun };
289*4882a593Smuzhiyun
290*4882a593Smuzhiyun if (num_XsumRX > bd) {
291*4882a593Smuzhiyun unsigned int rx_csum = XsumRX[bd];
292*4882a593Smuzhiyun ixgb_validate_option(&rx_csum, &opt);
293*4882a593Smuzhiyun adapter->rx_csum = rx_csum;
294*4882a593Smuzhiyun } else {
295*4882a593Smuzhiyun adapter->rx_csum = opt.def;
296*4882a593Smuzhiyun }
297*4882a593Smuzhiyun }
298*4882a593Smuzhiyun { /* Flow Control */
299*4882a593Smuzhiyun
300*4882a593Smuzhiyun static const struct ixgb_opt_list fc_list[] = {
301*4882a593Smuzhiyun { ixgb_fc_none, "Flow Control Disabled" },
302*4882a593Smuzhiyun { ixgb_fc_rx_pause, "Flow Control Receive Only" },
303*4882a593Smuzhiyun { ixgb_fc_tx_pause, "Flow Control Transmit Only" },
304*4882a593Smuzhiyun { ixgb_fc_full, "Flow Control Enabled" },
305*4882a593Smuzhiyun { ixgb_fc_default, "Flow Control Hardware Default" }
306*4882a593Smuzhiyun };
307*4882a593Smuzhiyun
308*4882a593Smuzhiyun static const struct ixgb_option opt = {
309*4882a593Smuzhiyun .type = list_option,
310*4882a593Smuzhiyun .name = "Flow Control",
311*4882a593Smuzhiyun .err = "reading default settings from EEPROM",
312*4882a593Smuzhiyun .def = ixgb_fc_tx_pause,
313*4882a593Smuzhiyun .arg = { .l = { .nr = ARRAY_SIZE(fc_list),
314*4882a593Smuzhiyun .p = fc_list }}
315*4882a593Smuzhiyun };
316*4882a593Smuzhiyun
317*4882a593Smuzhiyun if (num_FlowControl > bd) {
318*4882a593Smuzhiyun unsigned int fc = FlowControl[bd];
319*4882a593Smuzhiyun ixgb_validate_option(&fc, &opt);
320*4882a593Smuzhiyun adapter->hw.fc.type = fc;
321*4882a593Smuzhiyun } else {
322*4882a593Smuzhiyun adapter->hw.fc.type = opt.def;
323*4882a593Smuzhiyun }
324*4882a593Smuzhiyun }
325*4882a593Smuzhiyun { /* Receive Flow Control High Threshold */
326*4882a593Smuzhiyun static const struct ixgb_option opt = {
327*4882a593Smuzhiyun .type = range_option,
328*4882a593Smuzhiyun .name = "Rx Flow Control High Threshold",
329*4882a593Smuzhiyun .err = "using default of " __MODULE_STRING(DEFAULT_FCRTH),
330*4882a593Smuzhiyun .def = DEFAULT_FCRTH,
331*4882a593Smuzhiyun .arg = { .r = { .min = MIN_FCRTH,
332*4882a593Smuzhiyun .max = MAX_FCRTH}}
333*4882a593Smuzhiyun };
334*4882a593Smuzhiyun
335*4882a593Smuzhiyun if (num_RxFCHighThresh > bd) {
336*4882a593Smuzhiyun adapter->hw.fc.high_water = RxFCHighThresh[bd];
337*4882a593Smuzhiyun ixgb_validate_option(&adapter->hw.fc.high_water, &opt);
338*4882a593Smuzhiyun } else {
339*4882a593Smuzhiyun adapter->hw.fc.high_water = opt.def;
340*4882a593Smuzhiyun }
341*4882a593Smuzhiyun if (!(adapter->hw.fc.type & ixgb_fc_tx_pause) )
342*4882a593Smuzhiyun pr_info("Ignoring RxFCHighThresh when no RxFC\n");
343*4882a593Smuzhiyun }
344*4882a593Smuzhiyun { /* Receive Flow Control Low Threshold */
345*4882a593Smuzhiyun static const struct ixgb_option opt = {
346*4882a593Smuzhiyun .type = range_option,
347*4882a593Smuzhiyun .name = "Rx Flow Control Low Threshold",
348*4882a593Smuzhiyun .err = "using default of " __MODULE_STRING(DEFAULT_FCRTL),
349*4882a593Smuzhiyun .def = DEFAULT_FCRTL,
350*4882a593Smuzhiyun .arg = { .r = { .min = MIN_FCRTL,
351*4882a593Smuzhiyun .max = MAX_FCRTL}}
352*4882a593Smuzhiyun };
353*4882a593Smuzhiyun
354*4882a593Smuzhiyun if (num_RxFCLowThresh > bd) {
355*4882a593Smuzhiyun adapter->hw.fc.low_water = RxFCLowThresh[bd];
356*4882a593Smuzhiyun ixgb_validate_option(&adapter->hw.fc.low_water, &opt);
357*4882a593Smuzhiyun } else {
358*4882a593Smuzhiyun adapter->hw.fc.low_water = opt.def;
359*4882a593Smuzhiyun }
360*4882a593Smuzhiyun if (!(adapter->hw.fc.type & ixgb_fc_tx_pause) )
361*4882a593Smuzhiyun pr_info("Ignoring RxFCLowThresh when no RxFC\n");
362*4882a593Smuzhiyun }
363*4882a593Smuzhiyun { /* Flow Control Pause Time Request*/
364*4882a593Smuzhiyun static const struct ixgb_option opt = {
365*4882a593Smuzhiyun .type = range_option,
366*4882a593Smuzhiyun .name = "Flow Control Pause Time Request",
367*4882a593Smuzhiyun .err = "using default of "__MODULE_STRING(DEFAULT_FCPAUSE),
368*4882a593Smuzhiyun .def = DEFAULT_FCPAUSE,
369*4882a593Smuzhiyun .arg = { .r = { .min = MIN_FCPAUSE,
370*4882a593Smuzhiyun .max = MAX_FCPAUSE}}
371*4882a593Smuzhiyun };
372*4882a593Smuzhiyun
373*4882a593Smuzhiyun if (num_FCReqTimeout > bd) {
374*4882a593Smuzhiyun unsigned int pause_time = FCReqTimeout[bd];
375*4882a593Smuzhiyun ixgb_validate_option(&pause_time, &opt);
376*4882a593Smuzhiyun adapter->hw.fc.pause_time = pause_time;
377*4882a593Smuzhiyun } else {
378*4882a593Smuzhiyun adapter->hw.fc.pause_time = opt.def;
379*4882a593Smuzhiyun }
380*4882a593Smuzhiyun if (!(adapter->hw.fc.type & ixgb_fc_tx_pause) )
381*4882a593Smuzhiyun pr_info("Ignoring FCReqTimeout when no RxFC\n");
382*4882a593Smuzhiyun }
383*4882a593Smuzhiyun /* high low and spacing check for rx flow control thresholds */
384*4882a593Smuzhiyun if (adapter->hw.fc.type & ixgb_fc_tx_pause) {
385*4882a593Smuzhiyun /* high must be greater than low */
386*4882a593Smuzhiyun if (adapter->hw.fc.high_water < (adapter->hw.fc.low_water + 8)) {
387*4882a593Smuzhiyun /* set defaults */
388*4882a593Smuzhiyun pr_info("RxFCHighThresh must be >= (RxFCLowThresh + 8), Using Defaults\n");
389*4882a593Smuzhiyun adapter->hw.fc.high_water = DEFAULT_FCRTH;
390*4882a593Smuzhiyun adapter->hw.fc.low_water = DEFAULT_FCRTL;
391*4882a593Smuzhiyun }
392*4882a593Smuzhiyun }
393*4882a593Smuzhiyun { /* Receive Interrupt Delay */
394*4882a593Smuzhiyun static const struct ixgb_option opt = {
395*4882a593Smuzhiyun .type = range_option,
396*4882a593Smuzhiyun .name = "Receive Interrupt Delay",
397*4882a593Smuzhiyun .err = "using default of " __MODULE_STRING(DEFAULT_RDTR),
398*4882a593Smuzhiyun .def = DEFAULT_RDTR,
399*4882a593Smuzhiyun .arg = { .r = { .min = MIN_RDTR,
400*4882a593Smuzhiyun .max = MAX_RDTR}}
401*4882a593Smuzhiyun };
402*4882a593Smuzhiyun
403*4882a593Smuzhiyun if (num_RxIntDelay > bd) {
404*4882a593Smuzhiyun adapter->rx_int_delay = RxIntDelay[bd];
405*4882a593Smuzhiyun ixgb_validate_option(&adapter->rx_int_delay, &opt);
406*4882a593Smuzhiyun } else {
407*4882a593Smuzhiyun adapter->rx_int_delay = opt.def;
408*4882a593Smuzhiyun }
409*4882a593Smuzhiyun }
410*4882a593Smuzhiyun { /* Transmit Interrupt Delay */
411*4882a593Smuzhiyun static const struct ixgb_option opt = {
412*4882a593Smuzhiyun .type = range_option,
413*4882a593Smuzhiyun .name = "Transmit Interrupt Delay",
414*4882a593Smuzhiyun .err = "using default of " __MODULE_STRING(DEFAULT_TIDV),
415*4882a593Smuzhiyun .def = DEFAULT_TIDV,
416*4882a593Smuzhiyun .arg = { .r = { .min = MIN_TIDV,
417*4882a593Smuzhiyun .max = MAX_TIDV}}
418*4882a593Smuzhiyun };
419*4882a593Smuzhiyun
420*4882a593Smuzhiyun if (num_TxIntDelay > bd) {
421*4882a593Smuzhiyun adapter->tx_int_delay = TxIntDelay[bd];
422*4882a593Smuzhiyun ixgb_validate_option(&adapter->tx_int_delay, &opt);
423*4882a593Smuzhiyun } else {
424*4882a593Smuzhiyun adapter->tx_int_delay = opt.def;
425*4882a593Smuzhiyun }
426*4882a593Smuzhiyun }
427*4882a593Smuzhiyun
428*4882a593Smuzhiyun { /* Transmit Interrupt Delay Enable */
429*4882a593Smuzhiyun static const struct ixgb_option opt = {
430*4882a593Smuzhiyun .type = enable_option,
431*4882a593Smuzhiyun .name = "Tx Interrupt Delay Enable",
432*4882a593Smuzhiyun .err = "defaulting to Enabled",
433*4882a593Smuzhiyun .def = OPTION_ENABLED
434*4882a593Smuzhiyun };
435*4882a593Smuzhiyun
436*4882a593Smuzhiyun if (num_IntDelayEnable > bd) {
437*4882a593Smuzhiyun unsigned int ide = IntDelayEnable[bd];
438*4882a593Smuzhiyun ixgb_validate_option(&ide, &opt);
439*4882a593Smuzhiyun adapter->tx_int_delay_enable = ide;
440*4882a593Smuzhiyun } else {
441*4882a593Smuzhiyun adapter->tx_int_delay_enable = opt.def;
442*4882a593Smuzhiyun }
443*4882a593Smuzhiyun }
444*4882a593Smuzhiyun }
445