8 * You can obtain a copy of the license at usr/src/OPENSOLARIS.LICENSE
9 * or http://www.opensolaris.org/os/licensing.
10 * See the License for the specific language governing permissions
11 * and limitations under the License.
12 *
13 * When distributing Covered Code, include this CDDL HEADER in each
14 * file and include the License file at usr/src/OPENSOLARIS.LICENSE.
15 * If applicable, add the following below this CDDL HEADER, with the
16 * fields enclosed by brackets "[]" replaced with your own identifying
17 * information: Portions Copyright [yyyy] [name of copyright owner]
18 *
19 * CDDL HEADER END
20 */
21
22 /*
23 * Copyright(c) 2007-2010 Intel Corporation. All rights reserved.
24 */
25
26 /*
27 * Copyright (c) 2008, 2010, Oracle and/or its affiliates. All rights reserved.
28 * Copyright 2012 Nexenta Systems, Inc. All rights reserved.
29 * Copyright 2016 OmniTI Computer Consulting, Inc. All rights reserved.
30 * Copyright (c) 2017, Joyent, Inc.
31 */
32
33 #include "ixgbe_sw.h"
34
35 /*
36 * Bring the device out of the reset/quiesced state that it
37 * was in when the interface was registered.
38 */
39 int
40 ixgbe_m_start(void *arg)
41 {
42 ixgbe_t *ixgbe = (ixgbe_t *)arg;
43
44 mutex_enter(&ixgbe->gen_lock);
45
46 if (ixgbe->ixgbe_state & IXGBE_SUSPENDED) {
47 mutex_exit(&ixgbe->gen_lock);
48 return (ECANCELED);
203 break;
204
205 case IOC_ACK:
206 /*
207 * OK, reply with an ACK
208 */
209 miocack(q, mp, 0, 0);
210 break;
211
212 case IOC_REPLY:
213 /*
214 * OK, send prepared reply as ACK or NAK
215 */
216 mp->b_datap->db_type = iocp->ioc_error == 0 ?
217 M_IOCACK : M_IOCNAK;
218 qreply(q, mp);
219 break;
220 }
221 }
222
223 /*
224 * Obtain the MAC's capabilities and associated data from
225 * the driver.
226 */
227 boolean_t
228 ixgbe_m_getcapab(void *arg, mac_capab_t cap, void *cap_data)
229 {
230 ixgbe_t *ixgbe = (ixgbe_t *)arg;
231
232 switch (cap) {
233 case MAC_CAPAB_HCKSUM: {
234 uint32_t *tx_hcksum_flags = cap_data;
235
236 /*
237 * We advertise our capabilities only if tx hcksum offload is
238 * enabled. On receive, the stack will accept checksummed
239 * packets anyway, even if we haven't said we can deliver
240 * them.
241 */
242 if (!ixgbe->tx_hcksum_enable)
278 break;
279 default:
280 break;
281 }
282 break;
283 }
284 case MAC_CAPAB_TRANSCEIVER: {
285 mac_capab_transceiver_t *mct = cap_data;
286
287 /*
288 * Rather than try and guess based on the media type whether or
289 * not we have a transceiver we can read, we instead will let
290 * the actual function calls figure that out for us.
291 */
292 mct->mct_flags = 0;
293 mct->mct_ntransceivers = 1;
294 mct->mct_info = ixgbe_transceiver_info;
295 mct->mct_read = ixgbe_transceiver_read;
296 return (B_TRUE);
297 }
298 default:
299 return (B_FALSE);
300 }
301 return (B_TRUE);
302 }
303
304 int
305 ixgbe_m_setprop(void *arg, const char *pr_name, mac_prop_id_t pr_num,
306 uint_t pr_valsize, const void *pr_val)
307 {
308 ixgbe_t *ixgbe = (ixgbe_t *)arg;
309 struct ixgbe_hw *hw = &ixgbe->hw;
310 int err = 0;
311 uint32_t flow_control;
312 uint32_t cur_mtu, new_mtu;
313 uint32_t rx_size;
314 uint32_t tx_size;
315 ixgbe_link_speed speeds = 0;
316
317 mutex_enter(&ixgbe->gen_lock);
403
404 switch (flow_control) {
405 default:
406 err = EINVAL;
407 break;
408 case LINK_FLOWCTRL_NONE:
409 hw->fc.requested_mode = ixgbe_fc_none;
410 break;
411 case LINK_FLOWCTRL_RX:
412 hw->fc.requested_mode = ixgbe_fc_rx_pause;
413 break;
414 case LINK_FLOWCTRL_TX:
415 hw->fc.requested_mode = ixgbe_fc_tx_pause;
416 break;
417 case LINK_FLOWCTRL_BI:
418 hw->fc.requested_mode = ixgbe_fc_full;
419 break;
420 }
421 setup_link:
422 if (err == 0) {
423 if (ixgbe_driver_setup_link(ixgbe, B_TRUE) !=
424 IXGBE_SUCCESS)
425 err = EINVAL;
426 }
427 break;
428 case MAC_PROP_ADV_10GFDX_CAP:
429 case MAC_PROP_ADV_5000FDX_CAP:
430 case MAC_PROP_ADV_2500FDX_CAP:
431 case MAC_PROP_ADV_1000FDX_CAP:
432 case MAC_PROP_ADV_100FDX_CAP:
433 case MAC_PROP_STATUS:
434 case MAC_PROP_SPEED:
435 case MAC_PROP_DUPLEX:
436 err = ENOTSUP; /* read-only prop. Can't set this. */
437 break;
438 case MAC_PROP_MTU:
439 cur_mtu = ixgbe->default_mtu;
440 bcopy(pr_val, &new_mtu, sizeof (new_mtu));
441 if (new_mtu == cur_mtu) {
442 err = 0;
|
8 * You can obtain a copy of the license at usr/src/OPENSOLARIS.LICENSE
9 * or http://www.opensolaris.org/os/licensing.
10 * See the License for the specific language governing permissions
11 * and limitations under the License.
12 *
13 * When distributing Covered Code, include this CDDL HEADER in each
14 * file and include the License file at usr/src/OPENSOLARIS.LICENSE.
15 * If applicable, add the following below this CDDL HEADER, with the
16 * fields enclosed by brackets "[]" replaced with your own identifying
17 * information: Portions Copyright [yyyy] [name of copyright owner]
18 *
19 * CDDL HEADER END
20 */
21
22 /*
23 * Copyright(c) 2007-2010 Intel Corporation. All rights reserved.
24 */
25
26 /*
27 * Copyright (c) 2008, 2010, Oracle and/or its affiliates. All rights reserved.
28 * Copyright 2013 Nexenta Systems, Inc. All rights reserved.
29 * Copyright 2016 OmniTI Computer Consulting, Inc. All rights reserved.
30 * Copyright (c) 2017, Joyent, Inc.
31 */
32
33 #include "ixgbe_sw.h"
34
35 /*
36 * Bring the device out of the reset/quiesced state that it
37 * was in when the interface was registered.
38 */
39 int
40 ixgbe_m_start(void *arg)
41 {
42 ixgbe_t *ixgbe = (ixgbe_t *)arg;
43
44 mutex_enter(&ixgbe->gen_lock);
45
46 if (ixgbe->ixgbe_state & IXGBE_SUSPENDED) {
47 mutex_exit(&ixgbe->gen_lock);
48 return (ECANCELED);
203 break;
204
205 case IOC_ACK:
206 /*
207 * OK, reply with an ACK
208 */
209 miocack(q, mp, 0, 0);
210 break;
211
212 case IOC_REPLY:
213 /*
214 * OK, send prepared reply as ACK or NAK
215 */
216 mp->b_datap->db_type = iocp->ioc_error == 0 ?
217 M_IOCACK : M_IOCNAK;
218 qreply(q, mp);
219 break;
220 }
221 }
222
223 static int
224 ixgbe_led_set(void *arg, mac_led_mode_t mode, uint_t flags)
225 {
226 ixgbe_t *ixgbe = arg;
227 struct ixgbe_hw *hw = &ixgbe->hw;
228 uint32_t lidx = ixgbe->ixgbe_led_index;
229
230 if (flags != 0)
231 return (EINVAL);
232
233 if (mode != MAC_LED_DEFAULT &&
234 mode != MAC_LED_IDENT &&
235 mode != MAC_LED_OFF &&
236 mode != MAC_LED_ON)
237 return (ENOTSUP);
238
239 if (ixgbe->ixgbe_led_blink && mode != MAC_LED_IDENT) {
240 if (ixgbe_blink_led_stop(hw, lidx) != IXGBE_SUCCESS) {
241 return (EIO);
242 }
243 ixgbe->ixgbe_led_blink = B_FALSE;
244 }
245
246 if (mode != MAC_LED_DEFAULT && !ixgbe->ixgbe_led_active) {
247 ixgbe->ixgbe_led_reg = IXGBE_READ_REG(hw, IXGBE_LEDCTL);
248 ixgbe->ixgbe_led_active = B_TRUE;
249 }
250
251 switch (mode) {
252 case MAC_LED_DEFAULT:
253 if (ixgbe->ixgbe_led_active) {
254 IXGBE_WRITE_REG(hw, IXGBE_LEDCTL, ixgbe->ixgbe_led_reg);
255 ixgbe->ixgbe_led_active = B_FALSE;
256 }
257 break;
258 case MAC_LED_IDENT:
259 if (ixgbe_blink_led_start(hw, lidx) != IXGBE_SUCCESS)
260 return (EIO);
261 ixgbe->ixgbe_led_blink = B_TRUE;
262 break;
263 case MAC_LED_OFF:
264 if (ixgbe_led_off(hw, lidx) != IXGBE_SUCCESS)
265 return (EIO);
266 break;
267 case MAC_LED_ON:
268 if (ixgbe_led_on(hw, lidx) != IXGBE_SUCCESS)
269 return (EIO);
270 break;
271 default:
272 return (ENOTSUP);
273 }
274
275 return (0);
276 }
277
278 /*
279 * Obtain the MAC's capabilities and associated data from
280 * the driver.
281 */
282 boolean_t
283 ixgbe_m_getcapab(void *arg, mac_capab_t cap, void *cap_data)
284 {
285 ixgbe_t *ixgbe = (ixgbe_t *)arg;
286
287 switch (cap) {
288 case MAC_CAPAB_HCKSUM: {
289 uint32_t *tx_hcksum_flags = cap_data;
290
291 /*
292 * We advertise our capabilities only if tx hcksum offload is
293 * enabled. On receive, the stack will accept checksummed
294 * packets anyway, even if we haven't said we can deliver
295 * them.
296 */
297 if (!ixgbe->tx_hcksum_enable)
333 break;
334 default:
335 break;
336 }
337 break;
338 }
339 case MAC_CAPAB_TRANSCEIVER: {
340 mac_capab_transceiver_t *mct = cap_data;
341
342 /*
343 * Rather than try and guess based on the media type whether or
344 * not we have a transceiver we can read, we instead will let
345 * the actual function calls figure that out for us.
346 */
347 mct->mct_flags = 0;
348 mct->mct_ntransceivers = 1;
349 mct->mct_info = ixgbe_transceiver_info;
350 mct->mct_read = ixgbe_transceiver_read;
351 return (B_TRUE);
352 }
353 case MAC_CAPAB_LED: {
354 mac_capab_led_t *mcl = cap_data;
355
356 mcl->mcl_flags = 0;
357 mcl->mcl_modes = MAC_LED_DEFAULT | MAC_LED_ON | MAC_LED_OFF |
358 MAC_LED_IDENT;
359 mcl->mcl_set = ixgbe_led_set;
360 break;
361
362 }
363 default:
364 return (B_FALSE);
365 }
366 return (B_TRUE);
367 }
368
369 int
370 ixgbe_m_setprop(void *arg, const char *pr_name, mac_prop_id_t pr_num,
371 uint_t pr_valsize, const void *pr_val)
372 {
373 ixgbe_t *ixgbe = (ixgbe_t *)arg;
374 struct ixgbe_hw *hw = &ixgbe->hw;
375 int err = 0;
376 uint32_t flow_control;
377 uint32_t cur_mtu, new_mtu;
378 uint32_t rx_size;
379 uint32_t tx_size;
380 ixgbe_link_speed speeds = 0;
381
382 mutex_enter(&ixgbe->gen_lock);
468
469 switch (flow_control) {
470 default:
471 err = EINVAL;
472 break;
473 case LINK_FLOWCTRL_NONE:
474 hw->fc.requested_mode = ixgbe_fc_none;
475 break;
476 case LINK_FLOWCTRL_RX:
477 hw->fc.requested_mode = ixgbe_fc_rx_pause;
478 break;
479 case LINK_FLOWCTRL_TX:
480 hw->fc.requested_mode = ixgbe_fc_tx_pause;
481 break;
482 case LINK_FLOWCTRL_BI:
483 hw->fc.requested_mode = ixgbe_fc_full;
484 break;
485 }
486 setup_link:
487 if (err == 0) {
488 /* Don't autoneg if forcing a value */
489 ixgbe->hw.fc.disable_fc_autoneg = TRUE;
490 (void) ixgbe_fc_enable(hw);
491
492 if (ixgbe_driver_setup_link(ixgbe, B_TRUE) !=
493 IXGBE_SUCCESS)
494 err = EINVAL;
495 }
496 break;
497 case MAC_PROP_ADV_10GFDX_CAP:
498 case MAC_PROP_ADV_5000FDX_CAP:
499 case MAC_PROP_ADV_2500FDX_CAP:
500 case MAC_PROP_ADV_1000FDX_CAP:
501 case MAC_PROP_ADV_100FDX_CAP:
502 case MAC_PROP_STATUS:
503 case MAC_PROP_SPEED:
504 case MAC_PROP_DUPLEX:
505 err = ENOTSUP; /* read-only prop. Can't set this. */
506 break;
507 case MAC_PROP_MTU:
508 cur_mtu = ixgbe->default_mtu;
509 bcopy(pr_val, &new_mtu, sizeof (new_mtu));
510 if (new_mtu == cur_mtu) {
511 err = 0;
|