1 /*****************************************************************************
4 * Project: GEnesis, PCI Gigabit Ethernet Adapter
5 * Version: $Revision: 1.109 $
6 * Date: $Date: 2003/07/17 14:15:24 $
7 * Purpose: Private Network Management Interface
9 ****************************************************************************/
11 /******************************************************************************
13 * (C)Copyright 1998-2002 SysKonnect GmbH.
14 * (C)Copyright 2002-2003 Marvell.
16 * This program is free software; you can redistribute it and/or modify
17 * it under the terms of the GNU General Public License as published by
18 * the Free Software Foundation; either version 2 of the License, or
19 * (at your option) any later version.
21 * The information in this file is provided "AS IS" without warranty.
23 ******************************************************************************/
25 /*****************************************************************************
29 * $Log: skgepnmi.c,v $
30 * Revision 1.109 2003/07/17 14:15:24 tschilli
31 * Bug in SkPnmiGenIoctl() fixed.
33 * Revision 1.108 2003/05/27 07:10:11 tschilli
34 * Bug in SkPnmiGenIoctl() fixed.
36 * Revision 1.107 2003/05/23 13:01:10 tschilli
37 * Code for DIAG support added (#define SK_DIAG_SUPPORT).
38 * Code for generic PNMI IOCTL support added. The new function
39 * SkPnmiGenIoctl() is used for this purpose.
40 * Handling of OID_SKGE_BOARDLEVEL added.
41 * Incorrect buffer size handling of OID_SKGE_MTU during GET action fixed.
42 * Return code handling in PowerManagement() fixed.
45 * Revision 1.106 2003/04/10 14:47:31 rschmidt
46 * Fixed handling for OID_GEN_RCV_OK and OID_GEN_XMIT_OK for YUKON's GMAC
47 * in GetPhysStatVal().
48 * Replaced macro PHY_READ() with function call SkXmPhyRead().
49 * Made optimisations for readability and code size.
52 * Revision 1.105 2003/04/09 12:51:32 rschmidt
53 * Fixed XMAC only handling for some events in SkPnmiEvent().
54 * Fixed return value for OID_GEN_RCV_OK (SK_PNMI_HRX) in GetPhysStatVal().
57 * Revision 1.104 2003/03/27 11:18:21 tschilli
58 * BRK statements from DEBUG code removed.
59 * OID_GEN_XMIT_OK and OID_GEN_RCV_OK work with Yukon now.
60 * Copyright messages changed.
62 * Revision 1.103 2002/12/20 09:57:13 tschilli
63 * SK_PNMI_EVT_VCT_RESET event code changed.
64 * Unused variable from Vct() removed.
66 * Revision 1.102 2002/12/16 14:03:24 tschilli
67 * VCT code in Vct() changed.
69 * Revision 1.101 2002/12/16 09:04:10 tschilli
70 * Code for VCT handling added.
72 * Revision 1.100 2002/09/26 14:28:13 tschilli
73 * For XMAC the values in the SK_PNMI_PORT Port struct are copied to
74 * the new SK_PNMI_PORT BufPort struct during a MacUpdate() call.
75 * These values are used when GetPhysStatVal() is called. With this
76 * mechanism you get the best results when software corrections for
77 * counters are needed. Example: RX_LONGFRAMES.
79 * Revision 1.99 2002/09/17 12:31:19 tschilli
80 * OID_SKGE_TX_HW_ERROR_CTS, OID_SKGE_OUT_ERROR_CTS, OID_GEN_XMIT_ERROR:
81 * Double count of SK_PNMI_HTX_EXCESS_COL in function General() removed.
82 * OID_PNP_CAPABILITIES: sizeof(SK_PM_WAKE_UP_CAPABILITIES) changed to
83 * sizeof(SK_PNP_CAPABILITIES) in function PowerManagement().
85 * Revision 1.98 2002/09/10 09:00:03 rwahl
86 * Adapted boolean definitions according sktypes.
88 * Revision 1.97 2002/09/05 15:07:03 rwahl
91 * Revision 1.96 2002/09/05 11:04:14 rwahl
92 * - Rx/Tx packets statistics of virtual port were zero on link down (#10750)
93 * - For GMAC the overflow IRQ for Rx longframe counter was not counted.
94 * - Incorrect calculation for oids OID_SKGE_RX_HW_ERROR_CTS,
95 * OID_SKGE_IN_ERRORS_CTS, OID_GEN_RCV_ERROR.
96 * - Moved correction for OID_SKGE_STAT_RX_TOO_LONG to GetPhysStatVal().
97 * - Editorial changes.
99 * Revision 1.95 2002/09/04 08:53:37 rwahl
100 * - Incorrect statistics for Rx_too_long counter with jumbo frame (#10751)
101 * - StatRxFrameTooLong & StatRxPMaccErr counters were not reset.
102 * - Fixed compiler warning for debug msg arg types.
104 * Revision 1.94 2002/08/09 15:42:14 rwahl
105 * - Fixed StatAddr table for GMAC.
106 * - VirtualConf(): returned indeterminated status for speed oids if no
109 * Revision 1.93 2002/08/09 11:04:59 rwahl
110 * Added handler for link speed caps.
112 * Revision 1.92 2002/08/09 09:43:03 rwahl
113 * - Added handler for NDIS OID_PNP_xxx ids.
115 * Revision 1.91 2002/07/17 19:53:03 rwahl
116 * - Added StatOvrflwBit table for XMAC & GMAC.
117 * - Extended StatAddr table for GMAC. Added check of number of counters
118 * in enumeration and size of StatAddr table on init level.
119 * - Added use of GIFunc table.
120 * - ChipSet is not static anymore,
121 * - Extended SIRQ event handler for both mac types.
122 * - Fixed rx short counter bug (#10620)
123 * - Added handler for oids SKGE_SPEED_MODE & SKGE_SPEED_STATUS.
124 * - Extended GetPhysStatVal() for GMAC.
125 * - Editorial changes.
127 * Revision 1.90 2002/05/22 08:56:25 rwahl
128 * - Moved OID table to separate source file.
129 * - Fix: TX_DEFFERAL counter incremented in full-duplex mode.
130 * - Use string definitions for error msgs.
132 * Revision 1.89 2001/09/18 10:01:30 mkunz
133 * some OID's fixed for dualnetmode
135 * Revision 1.88 2001/08/02 07:58:08 rwahl
136 * - Fixed NetIndex to csum module at ResetCounter().
138 * Revision 1.87 2001/04/06 13:35:09 mkunz
139 * -Bugs fixed in handling of OID_SKGE_MTU and the VPD OID's
141 * Revision 1.86 2001/03/09 09:18:03 mkunz
142 * Changes in SK_DBG_MSG
144 * Revision 1.85 2001/03/08 09:37:31 mkunz
145 * Bugfix in ResetCounter for Pnmi.Port structure
147 * Revision 1.84 2001/03/06 09:04:55 mkunz
148 * Made some changes in instance calculation
150 * Revision 1.83 2001/02/15 09:15:32 mkunz
151 * Necessary changes for dual net mode added
153 * Revision 1.82 2001/02/07 08:24:19 mkunz
154 * -Made changes in handling of OID_SKGE_MTU
156 * Revision 1.81 2001/02/06 09:58:00 mkunz
158 * -OID_SKGE_MTU added
159 * -pnmi support for dual net mode. Interface function and macros extended
161 * Revision 1.80 2001/01/22 13:41:35 rassmann
162 * Supporting two nets on dual-port adapters.
164 * Revision 1.79 2000/12/05 14:57:40 cgoos
165 * SetStruct failed before first Link Up (link mode of virtual
166 * port "INDETERMINATED").
168 * Revision 1.78 2000/09/12 10:44:58 cgoos
169 * Fixed SK_PNMI_STORE_U32 calls with typecasted argument.
171 * Revision 1.77 2000/09/07 08:10:19 rwahl
172 * - Modified algorithm for 64bit NDIS statistic counters;
173 * returns 64bit or 32bit value depending on passed buffer
174 * size. Indicate capability for 64bit NDIS counter, if passed
175 * buffer size is zero. OID_GEN_XMIT_ERROR, OID_GEN_RCV_ERROR,
176 * and OID_GEN_RCV_NO_BUFFER handled as 64bit counter, too.
177 * - corrected OID_SKGE_RLMT_PORT_PREFERRED.
179 * Revision 1.76 2000/08/03 15:23:39 rwahl
180 * - Correction for FrameTooLong counter has to be moved to OID handling
181 * routines (instead of statistic counter routine).
182 * - Fix in XMAC Reset Event handling: Only offset counter for hardware
183 * statistic registers are updated.
185 * Revision 1.75 2000/08/01 16:46:05 rwahl
186 * - Added StatRxLongFrames counter and correction of FrameTooLong counter.
187 * - Added directive to control width (default = 32bit) of NDIS statistic
188 * counters (SK_NDIS_64BIT_CTR).
190 * Revision 1.74 2000/07/04 11:41:53 rwahl
191 * - Added volition connector type.
193 * Revision 1.73 2000/03/15 16:33:10 rwahl
194 * Fixed bug 10510; wrong reset of virtual port statistic counters.
196 * Revision 1.72 1999/12/06 16:15:53 rwahl
197 * Fixed problem of instance range for current and factory MAC address.
199 * Revision 1.71 1999/12/06 10:14:20 rwahl
200 * Fixed bug 10476; set operation for PHY_OPERATION_MODE.
202 * Revision 1.70 1999/11/22 13:33:34 cgoos
203 * Changed license header to GPL.
205 * Revision 1.69 1999/10/18 11:42:15 rwahl
206 * Added typecasts for checking event dependent param (debug only).
208 * Revision 1.68 1999/10/06 09:35:59 cgoos
209 * Added state check to PHY_READ call (hanged if called during startup).
211 * Revision 1.67 1999/09/22 09:53:20 rwahl
212 * - Read Broadcom register for updating FCS error counter (1000Base-T).
214 * Revision 1.66 1999/08/26 13:47:56 rwahl
215 * Added SK_DRIVER_SENDEVENT when queueing RLMT_CHANGE_THRES trap.
217 * Revision 1.65 1999/07/26 07:49:35 cgoos
218 * Added two typecasts to avoid compiler warnings.
220 * Revision 1.64 1999/05/20 09:24:12 cgoos
221 * Changes for 1000Base-T (sensors, Master/Slave).
223 * Revision 1.63 1999/04/13 15:11:58 mhaveman
224 * Moved include of rlmt.h to header skgepnmi.h because some macros
227 * Revision 1.62 1999/04/13 15:08:07 mhaveman
228 * Replaced again SK_RLMT_CHECK_LINK with SK_PNMI_RLMT_MODE_CHK_LINK
229 * to grant unified interface by only using the PNMI header file.
230 * SK_PNMI_RLMT_MODE_CHK_LINK is defined the same as SK_RLMT_CHECK_LINK.
232 * Revision 1.61 1999/04/13 15:02:48 mhaveman
233 * Changes caused by review:
234 * -Changed some comments
235 * -Removed redundant check for OID_SKGE_PHYS_FAC_ADDR
236 * -Optimized PRESET check.
237 * -Meaning of error SK_ADDR_DUPLICATE_ADDRESS changed. Set of same
238 * address will now not cause this error. Removed corresponding check.
240 * Revision 1.60 1999/03/23 10:41:23 mhaveman
243 * Revision 1.59 1999/02/19 08:01:28 mhaveman
244 * Fixed bug 10372 that after counter reset all ports were displayed
247 * Revision 1.58 1999/02/16 18:04:47 mhaveman
248 * Fixed problem of twisted OIDs SENSOR_WAR_TIME and SENSOR_ERR_TIME.
250 * Revision 1.56 1999/01/27 12:29:11 mhaveman
251 * SkTimerStart was called with time value in milli seconds but needs
254 * Revision 1.55 1999/01/25 15:00:38 mhaveman
255 * Added support to allow multiple ports to be active. If this feature in
256 * future will be used, the Management Data Base variables PORT_ACTIVE
257 * and PORT_PREFERED should be moved to the port specific part of RLMT.
258 * Currently they return the values of the first active physical port
259 * found. A set to the virtual port will actually change all active
260 * physical ports. A get returns the melted values of all active physical
261 * ports. If the port values differ a return value INDETERMINATED will
262 * be returned. This effects especially the CONF group.
264 * Revision 1.54 1999/01/19 10:10:22 mhaveman
265 * -Fixed bug 10354: Counter values of virtual port were wrong after port
267 * -Added check if a switch to the same port is notified.
269 * Revision 1.53 1999/01/07 09:25:21 mhaveman
270 * Forgot to initialize a variable.
272 * Revision 1.52 1999/01/05 10:34:33 mhaveman
273 * Fixed little error in RlmtChangeEstimate calculation.
275 * Revision 1.51 1999/01/05 09:59:07 mhaveman
276 * -Moved timer start to init level 2
277 * -Redesigned port switch average calculation to avoid 64bit
280 * Revision 1.50 1998/12/10 15:13:59 mhaveman
281 * -Fixed: PHYS_CUR_ADDR returned wrong addresses
282 * -Fixed: RLMT_PORT_PREFERED and RLMT_CHANGE_THRES preset returned
284 * -Fixed: TRAP buffer seemed to sometimes suddenly empty
286 * Revision 1.49 1998/12/09 16:17:07 mhaveman
287 * Fixed: Couldnot delete VPD keys on UNIX.
289 * Revision 1.48 1998/12/09 14:11:10 mhaveman
290 * -Add: Debugmessage for XMAC_RESET supressed to minimize output.
291 * -Fixed: RlmtChangeThreshold will now be initialized.
292 * -Fixed: VPD_ENTRIES_LIST extended value with unnecessary space char.
293 * -Fixed: On VPD key creation an invalid key name could be created
295 * -Some minor changes in comments and code.
297 * Revision 1.47 1998/12/08 16:00:31 mhaveman
298 * -Fixed: For RLMT_PORT_ACTIVE will now be returned a 0 if no port
300 * -Fixed: For the RLMT statistics group only the last value was
301 * returned and the rest of the buffer was filled with 0xff
302 * -Fixed: Mysteriously the preset on RLMT_MODE still returned
304 * Revision 1.46 1998/12/08 10:04:56 mhaveman
305 * -Fixed: Preset on RLMT_MODE returned always BAD_VALUE error.
306 * -Fixed: Alignment error in GetStruct
307 * -Fixed: If for Get/Preset/SetStruct the buffer size is equal or
308 * larger than SK_PNMI_MIN_STRUCT_SIZE the return value is stored
309 * to the buffer. In this case the caller should always return
310 * ok to its upper routines. Only if the buffer size is less
311 * than SK_PNMI_MIN_STRUCT_SIZE and the return value is unequal
312 * to 0, an error should be returned by the caller.
313 * -Fixed: Wrong number of instances with RLMT statistic.
314 * -Fixed: Return now SK_LMODE_STAT_UNKNOWN if the LinkModeStatus is 0.
316 * Revision 1.45 1998/12/03 17:17:24 mhaveman
317 * -Removed for VPD create action the buffer size limitation to 4 bytes.
318 * -Pass now physical/active physical port to ADDR for CUR_ADDR set
320 * Revision 1.44 1998/12/03 15:14:35 mhaveman
321 * Another change to Vpd instance evaluation.
323 * Revision 1.43 1998/12/03 14:18:10 mhaveman
324 * -Fixed problem in PnmiSetStruct. It was impossible to set any value.
325 * -Removed VPD key evaluation for VPD_FREE_BYTES and VPD_ACTION.
327 * Revision 1.42 1998/12/03 11:31:47 mhaveman
328 * Inserted cast to satisfy lint.
330 * Revision 1.41 1998/12/03 11:28:16 mhaveman
331 * Removed SK_PNMI_CHECKPTR
333 * Revision 1.40 1998/12/03 11:19:07 mhaveman
335 * -A set to virtual port will now be ignored. A set with broadcast
336 * address to any port will be ignored.
337 * -GetStruct function made VPD instance calculation wrong.
338 * -Prefered port returned -1 instead of 0.
340 * Revision 1.39 1998/11/26 15:30:29 mhaveman
341 * Added sense mode to link mode.
343 * Revision 1.38 1998/11/23 15:34:00 mhaveman
344 * -Fixed bug for RX counters. On an RX overflow interrupt the high
345 * words of all RX counters were incremented.
346 * -SET operations on FLOWCTRL_MODE and LINK_MODE accept now the
347 * value 0, which has no effect. It is usefull for multiple instance
350 * Revision 1.37 1998/11/20 08:02:04 mhaveman
351 * -Fixed: Ports were compared with MAX_SENSORS
352 * -Fixed: Crash in GetTrapEntry with MEMSET macro
353 * -Fixed: Conversions between physical, logical port index and instance
355 * Revision 1.36 1998/11/16 07:48:53 mhaveman
356 * Casted SK_DRIVER_SENDEVENT with (void) to eleminate compiler warnings
359 * Revision 1.35 1998/11/16 07:45:34 mhaveman
360 * SkAddrOverride now returns value and will be checked.
362 * Revision 1.34 1998/11/10 13:40:37 mhaveman
363 * Needed to change interface, because NT driver needs a return value
364 * of needed buffer space on TOO_SHORT errors. Therefore all
365 * SkPnmiGet/Preset/Set functions now have a pointer to the length
366 * parameter, where the needed space on error is returned.
368 * Revision 1.33 1998/11/03 13:52:46 mhaveman
369 * Made file lint conform.
371 * Revision 1.32 1998/11/03 13:19:07 mhaveman
372 * The events SK_HWEV_SET_LMODE and SK_HWEV_SET_FLOWMODE pass now in
373 * Para32[0] the physical MAC index and in Para32[1] the new mode.
375 * Revision 1.31 1998/11/03 12:30:40 gklug
376 * fix: compiler warning memset
378 * Revision 1.30 1998/11/03 12:04:46 mhaveman
379 * Fixed problem in SENSOR_VALUE, which wrote beyond the buffer end
380 * Fixed alignment problem with CHIPSET.
382 * Revision 1.29 1998/11/02 11:23:54 mhaveman
383 * Corrected SK_ERROR_LOG to SK_ERR_LOG. Sorry.
385 * Revision 1.28 1998/11/02 10:47:16 mhaveman
386 * Added syslog messages for internal errors.
388 * Revision 1.27 1998/10/30 15:48:06 mhaveman
389 * Fixed problems after simulation of SK_PNMI_EVT_CHG_EST_TIMER and
390 * RlmtChangeThreshold calculation.
392 * Revision 1.26 1998/10/29 15:36:55 mhaveman
393 * -Fixed bug in trap buffer handling.
394 * -OID_SKGE_DRIVER_DESCR, OID_SKGE_DRIVER_VERSION, OID_SKGE_HW_DESCR,
395 * OID_SKGE_HW_VERSION, OID_SKGE_VPD_ENTRIES_LIST, OID_SKGE_VPD_KEY,
396 * OID_SKGE_VPD_VALUE, and OID_SKGE_SENSOR_DESCR return values with
397 * a leading octet before each string storing the string length.
398 * -Perform a RlmtUpdate during SK_PNMI_EVT_XMAC_RESET to minimize
399 * RlmtUpdate calls in GetStatVal.
400 * -Inserted SK_PNMI_CHECKFLAGS macro increase readability.
402 * Revision 1.25 1998/10/29 08:50:36 mhaveman
403 * Fixed problems after second event simulation.
405 * Revision 1.24 1998/10/28 08:44:37 mhaveman
406 * -Fixed alignment problem
407 * -Fixed problems during event simulation
408 * -Fixed sequence of error return code (INSTANCE -> ACCESS -> SHORT)
409 * -Changed type of parameter Instance back to SK_U32 because of VPD
410 * -Updated new VPD function calls
412 * Revision 1.23 1998/10/23 10:16:37 mhaveman
413 * Fixed bugs after buffer test simulation.
415 * Revision 1.22 1998/10/21 13:23:52 mhaveman
416 * -Call syntax of SkOsGetTime() changed to SkOsGetTime(pAc).
417 * -Changed calculation of hundrets of seconds.
419 * Revision 1.20 1998/10/20 07:30:45 mhaveman
420 * Made type changes to unsigned integer where possible.
422 * Revision 1.19 1998/10/19 10:51:30 mhaveman
423 * -Made Bug fixes after simulation run
424 * -Renamed RlmtMAC... to RlmtPort...
425 * -Marked workarounds with Errata comments
427 * Revision 1.18 1998/10/14 07:50:08 mhaveman
428 * -For OID_SKGE_LINK_STATUS the link down detection has moved from RLMT
430 * -Provided all MEMCPY/MEMSET macros with (char *) pointers, because
431 * Solaris throwed warnings when mapping to bcopy/bset.
433 * Revision 1.17 1998/10/13 07:42:01 mhaveman
434 * -Added OIDs OID_SKGE_TRAP_NUMBER and OID_SKGE_ALL_DATA
435 * -Removed old cvs history entries
436 * -Renamed MacNumber to PortNumber
438 * Revision 1.16 1998/10/07 10:52:49 mhaveman
439 * -Inserted handling of some OID_GEN_ Ids for windows
440 * -Fixed problem with 803.2 statistic.
442 * Revision 1.15 1998/10/01 09:16:29 mhaveman
443 * Added Debug messages for function call and UpdateFlag tracing.
445 * Revision 1.14 1998/09/30 13:39:09 mhaveman
446 * -Reduced namings of 'MAC' by replacing them with 'PORT'.
447 * -Completed counting of OID_SKGE_RX_HW_ERROR_CTS,
448 * OID_SKGE_TX_HW_ERROR_CTS,
449 * OID_SKGE_IN_ERRORS_CTS, and OID_SKGE_OUT_ERROR_CTS.
450 * -SET check for RlmtMode
452 * Revision 1.13 1998/09/28 13:13:08 mhaveman
453 * Hide strcmp, strlen, and strncpy behind macros SK_STRCMP, SK_STRLEN,
454 * and SK_STRNCPY. (Same reasons as for mem.. and MEM..)
456 * Revision 1.12 1998/09/16 08:18:36 cgoos
457 * Fix: XM_INxx and XM_OUTxx called with different parameter order:
458 * sometimes IoC,Mac,... sometimes Mac,IoC,... Now always first variant.
459 * Fix: inserted "Pnmi." into some pAC->pDriverDescription / Version.
460 * Change: memset, memcpy to makros SK_MEMSET, SK_MEMCPY
462 * Revision 1.11 1998/09/04 17:01:45 mhaveman
463 * Added SyncCounter as macro and OID_SKGE_.._NO_DESCR_CTS to
464 * OID_SKGE_RX_NO_BUF_CTS.
466 * Revision 1.10 1998/09/04 14:35:35 mhaveman
467 * Added macro counters, that are counted by driver.
469 ****************************************************************************/
473 static const char SysKonnectFileId
[] =
474 "@(#) $Id: skgepnmi.c,v 1.109 2003/07/17 14:15:24 tschilli Exp $ (C) Marvell.";
477 #include "h/skdrv1st.h"
478 #include "h/sktypes.h"
479 #include "h/xmac_ii.h"
480 #include "h/skdebug.h"
481 #include "h/skqueue.h"
482 #include "h/skgepnmi.h"
483 #include "h/skgesirq.h"
484 #include "h/skcsum.h"
486 #include "h/skgehw.h"
487 #include "h/skgeinit.h"
488 #include "h/skdrv2nd.h"
489 #include "h/skgepnm2.h"
491 #include "h/skgepmgt.h"
493 /* defines *******************************************************************/
496 #define PNMI_STATIC static
502 * Public Function prototypes
504 int SkPnmiInit(SK_AC
*pAC
, SK_IOC IoC
, int level
);
505 int SkPnmiGetVar(SK_AC
*pAC
, SK_IOC IoC
, SK_U32 Id
, void *pBuf
,
506 unsigned int *pLen
, SK_U32 Instance
, SK_U32 NetIndex
);
507 int SkPnmiPreSetVar(SK_AC
*pAC
, SK_IOC IoC
, SK_U32 Id
, void *pBuf
,
508 unsigned int *pLen
, SK_U32 Instance
, SK_U32 NetIndex
);
509 int SkPnmiSetVar(SK_AC
*pAC
, SK_IOC IoC
, SK_U32 Id
, void *pBuf
,
510 unsigned int *pLen
, SK_U32 Instance
, SK_U32 NetIndex
);
511 int SkPnmiGetStruct(SK_AC
*pAC
, SK_IOC IoC
, void *pBuf
,
512 unsigned int *pLen
, SK_U32 NetIndex
);
513 int SkPnmiPreSetStruct(SK_AC
*pAC
, SK_IOC IoC
, void *pBuf
,
514 unsigned int *pLen
, SK_U32 NetIndex
);
515 int SkPnmiSetStruct(SK_AC
*pAC
, SK_IOC IoC
, void *pBuf
,
516 unsigned int *pLen
, SK_U32 NetIndex
);
517 int SkPnmiEvent(SK_AC
*pAC
, SK_IOC IoC
, SK_U32 Event
, SK_EVPARA Param
);
518 int SkPnmiGenIoctl(SK_AC
*pAC
, SK_IOC IoC
, void * pBuf
,
519 unsigned int * pLen
, SK_U32 NetIndex
);
523 * Private Function prototypes
526 PNMI_STATIC SK_U8
CalculateLinkModeStatus(SK_AC
*pAC
, SK_IOC IoC
, unsigned int
528 PNMI_STATIC SK_U8
CalculateLinkStatus(SK_AC
*pAC
, SK_IOC IoC
, unsigned int
530 PNMI_STATIC
void CopyMac(char *pDst
, SK_MAC_ADDR
*pMac
);
531 PNMI_STATIC
void CopyTrapQueue(SK_AC
*pAC
, char *pDstBuf
);
532 PNMI_STATIC SK_U64
GetPhysStatVal(SK_AC
*pAC
, SK_IOC IoC
,
533 unsigned int PhysPortIndex
, unsigned int StatIndex
);
534 PNMI_STATIC SK_U64
GetStatVal(SK_AC
*pAC
, SK_IOC IoC
, unsigned int LogPortIndex
,
535 unsigned int StatIndex
, SK_U32 NetIndex
);
536 PNMI_STATIC
char* GetTrapEntry(SK_AC
*pAC
, SK_U32 TrapId
, unsigned int Size
);
537 PNMI_STATIC
void GetTrapQueueLen(SK_AC
*pAC
, unsigned int *pLen
,
538 unsigned int *pEntries
);
539 PNMI_STATIC
int GetVpdKeyArr(SK_AC
*pAC
, SK_IOC IoC
, char *pKeyArr
,
540 unsigned int KeyArrLen
, unsigned int *pKeyNo
);
541 PNMI_STATIC
int LookupId(SK_U32 Id
);
542 PNMI_STATIC
int MacUpdate(SK_AC
*pAC
, SK_IOC IoC
, unsigned int FirstMac
,
543 unsigned int LastMac
);
544 PNMI_STATIC
int PnmiStruct(SK_AC
*pAC
, SK_IOC IoC
, int Action
, char *pBuf
,
545 unsigned int *pLen
, SK_U32 NetIndex
);
546 PNMI_STATIC
int PnmiVar(SK_AC
*pAC
, SK_IOC IoC
, int Action
, SK_U32 Id
,
547 char *pBuf
, unsigned int *pLen
, SK_U32 Instance
, SK_U32 NetIndex
);
548 PNMI_STATIC
void QueueRlmtNewMacTrap(SK_AC
*pAC
, unsigned int ActiveMac
);
549 PNMI_STATIC
void QueueRlmtPortTrap(SK_AC
*pAC
, SK_U32 TrapId
,
550 unsigned int PortIndex
);
551 PNMI_STATIC
void QueueSensorTrap(SK_AC
*pAC
, SK_U32 TrapId
,
552 unsigned int SensorIndex
);
553 PNMI_STATIC
void QueueSimpleTrap(SK_AC
*pAC
, SK_U32 TrapId
);
554 PNMI_STATIC
void ResetCounter(SK_AC
*pAC
, SK_IOC IoC
, SK_U32 NetIndex
);
555 PNMI_STATIC
int RlmtUpdate(SK_AC
*pAC
, SK_IOC IoC
, SK_U32 NetIndex
);
556 PNMI_STATIC
int SirqUpdate(SK_AC
*pAC
, SK_IOC IoC
);
557 PNMI_STATIC
void VirtualConf(SK_AC
*pAC
, SK_IOC IoC
, SK_U32 Id
, char *pBuf
);
558 PNMI_STATIC
int Vct(SK_AC
*pAC
, SK_IOC IoC
, int Action
, SK_U32 Id
, char *pBuf
,
559 unsigned int *pLen
, SK_U32 Instance
, unsigned int TableIndex
, SK_U32 NetIndex
);
560 PNMI_STATIC
void CheckVctStatus(SK_AC
*, SK_IOC
, char *, SK_U32
, SK_U32
);
563 * Table to correlate OID with handler function and index to
564 * hardware register stored in StatAddress if applicable.
568 /* global variables **********************************************************/
571 * Overflow status register bit table and corresponding counter
572 * dependent on MAC type - the number relates to the size of overflow
573 * mask returned by the pFnMacOverflow function
575 PNMI_STATIC
const SK_U16 StatOvrflwBit
[][SK_PNMI_MAC_TYPES
] = {
576 /* Bit0 */ { SK_PNMI_HTX
, SK_PNMI_HTX_UNICAST
},
577 /* Bit1 */ { SK_PNMI_HTX_OCTETHIGH
, SK_PNMI_HTX_BROADCAST
},
578 /* Bit2 */ { SK_PNMI_HTX_OCTETLOW
, SK_PNMI_HTX_PMACC
},
579 /* Bit3 */ { SK_PNMI_HTX_BROADCAST
, SK_PNMI_HTX_MULTICAST
},
580 /* Bit4 */ { SK_PNMI_HTX_MULTICAST
, SK_PNMI_HTX_OCTETLOW
},
581 /* Bit5 */ { SK_PNMI_HTX_UNICAST
, SK_PNMI_HTX_OCTETHIGH
},
582 /* Bit6 */ { SK_PNMI_HTX_LONGFRAMES
, SK_PNMI_HTX_64
},
583 /* Bit7 */ { SK_PNMI_HTX_BURST
, SK_PNMI_HTX_127
},
584 /* Bit8 */ { SK_PNMI_HTX_PMACC
, SK_PNMI_HTX_255
},
585 /* Bit9 */ { SK_PNMI_HTX_MACC
, SK_PNMI_HTX_511
},
586 /* Bit10 */ { SK_PNMI_HTX_SINGLE_COL
, SK_PNMI_HTX_1023
},
587 /* Bit11 */ { SK_PNMI_HTX_MULTI_COL
, SK_PNMI_HTX_MAX
},
588 /* Bit12 */ { SK_PNMI_HTX_EXCESS_COL
, SK_PNMI_HTX_LONGFRAMES
},
589 /* Bit13 */ { SK_PNMI_HTX_LATE_COL
, SK_PNMI_HTX_RESERVED
},
590 /* Bit14 */ { SK_PNMI_HTX_DEFFERAL
, SK_PNMI_HTX_COL
},
591 /* Bit15 */ { SK_PNMI_HTX_EXCESS_DEF
, SK_PNMI_HTX_LATE_COL
},
592 /* Bit16 */ { SK_PNMI_HTX_UNDERRUN
, SK_PNMI_HTX_EXCESS_COL
},
593 /* Bit17 */ { SK_PNMI_HTX_CARRIER
, SK_PNMI_HTX_MULTI_COL
},
594 /* Bit18 */ { SK_PNMI_HTX_UTILUNDER
, SK_PNMI_HTX_SINGLE_COL
},
595 /* Bit19 */ { SK_PNMI_HTX_UTILOVER
, SK_PNMI_HTX_UNDERRUN
},
596 /* Bit20 */ { SK_PNMI_HTX_64
, SK_PNMI_HTX_RESERVED
},
597 /* Bit21 */ { SK_PNMI_HTX_127
, SK_PNMI_HTX_RESERVED
},
598 /* Bit22 */ { SK_PNMI_HTX_255
, SK_PNMI_HTX_RESERVED
},
599 /* Bit23 */ { SK_PNMI_HTX_511
, SK_PNMI_HTX_RESERVED
},
600 /* Bit24 */ { SK_PNMI_HTX_1023
, SK_PNMI_HTX_RESERVED
},
601 /* Bit25 */ { SK_PNMI_HTX_MAX
, SK_PNMI_HTX_RESERVED
},
602 /* Bit26 */ { SK_PNMI_HTX_RESERVED
, SK_PNMI_HTX_RESERVED
},
603 /* Bit27 */ { SK_PNMI_HTX_RESERVED
, SK_PNMI_HTX_RESERVED
},
604 /* Bit28 */ { SK_PNMI_HTX_RESERVED
, SK_PNMI_HTX_RESERVED
},
605 /* Bit29 */ { SK_PNMI_HTX_RESERVED
, SK_PNMI_HTX_RESERVED
},
606 /* Bit30 */ { SK_PNMI_HTX_RESERVED
, SK_PNMI_HTX_RESERVED
},
607 /* Bit31 */ { SK_PNMI_HTX_RESERVED
, SK_PNMI_HTX_RESERVED
},
608 /* Bit32 */ { SK_PNMI_HRX
, SK_PNMI_HRX_UNICAST
},
609 /* Bit33 */ { SK_PNMI_HRX_OCTETHIGH
, SK_PNMI_HRX_BROADCAST
},
610 /* Bit34 */ { SK_PNMI_HRX_OCTETLOW
, SK_PNMI_HRX_PMACC
},
611 /* Bit35 */ { SK_PNMI_HRX_BROADCAST
, SK_PNMI_HRX_MULTICAST
},
612 /* Bit36 */ { SK_PNMI_HRX_MULTICAST
, SK_PNMI_HRX_FCS
},
613 /* Bit37 */ { SK_PNMI_HRX_UNICAST
, SK_PNMI_HRX_RESERVED
},
614 /* Bit38 */ { SK_PNMI_HRX_PMACC
, SK_PNMI_HRX_OCTETLOW
},
615 /* Bit39 */ { SK_PNMI_HRX_MACC
, SK_PNMI_HRX_OCTETHIGH
},
616 /* Bit40 */ { SK_PNMI_HRX_PMACC_ERR
, SK_PNMI_HRX_BADOCTETLOW
},
617 /* Bit41 */ { SK_PNMI_HRX_MACC_UNKWN
, SK_PNMI_HRX_BADOCTETHIGH
},
618 /* Bit42 */ { SK_PNMI_HRX_BURST
, SK_PNMI_HRX_UNDERSIZE
},
619 /* Bit43 */ { SK_PNMI_HRX_MISSED
, SK_PNMI_HRX_RUNT
},
620 /* Bit44 */ { SK_PNMI_HRX_FRAMING
, SK_PNMI_HRX_64
},
621 /* Bit45 */ { SK_PNMI_HRX_OVERFLOW
, SK_PNMI_HRX_127
},
622 /* Bit46 */ { SK_PNMI_HRX_JABBER
, SK_PNMI_HRX_255
},
623 /* Bit47 */ { SK_PNMI_HRX_CARRIER
, SK_PNMI_HRX_511
},
624 /* Bit48 */ { SK_PNMI_HRX_IRLENGTH
, SK_PNMI_HRX_1023
},
625 /* Bit49 */ { SK_PNMI_HRX_SYMBOL
, SK_PNMI_HRX_MAX
},
626 /* Bit50 */ { SK_PNMI_HRX_SHORTS
, SK_PNMI_HRX_LONGFRAMES
},
627 /* Bit51 */ { SK_PNMI_HRX_RUNT
, SK_PNMI_HRX_TOO_LONG
},
628 /* Bit52 */ { SK_PNMI_HRX_TOO_LONG
, SK_PNMI_HRX_JABBER
},
629 /* Bit53 */ { SK_PNMI_HRX_FCS
, SK_PNMI_HRX_RESERVED
},
630 /* Bit54 */ { SK_PNMI_HRX_RESERVED
, SK_PNMI_HRX_OVERFLOW
},
631 /* Bit55 */ { SK_PNMI_HRX_CEXT
, SK_PNMI_HRX_RESERVED
},
632 /* Bit56 */ { SK_PNMI_HRX_UTILUNDER
, SK_PNMI_HRX_RESERVED
},
633 /* Bit57 */ { SK_PNMI_HRX_UTILOVER
, SK_PNMI_HRX_RESERVED
},
634 /* Bit58 */ { SK_PNMI_HRX_64
, SK_PNMI_HRX_RESERVED
},
635 /* Bit59 */ { SK_PNMI_HRX_127
, SK_PNMI_HRX_RESERVED
},
636 /* Bit60 */ { SK_PNMI_HRX_255
, SK_PNMI_HRX_RESERVED
},
637 /* Bit61 */ { SK_PNMI_HRX_511
, SK_PNMI_HRX_RESERVED
},
638 /* Bit62 */ { SK_PNMI_HRX_1023
, SK_PNMI_HRX_RESERVED
},
639 /* Bit63 */ { SK_PNMI_HRX_MAX
, SK_PNMI_HRX_RESERVED
}
643 * Table for hardware register saving on resets and port switches
645 PNMI_STATIC
const SK_PNMI_STATADDR StatAddr
[SK_PNMI_MAX_IDX
][SK_PNMI_MAC_TYPES
] = {
647 {{XM_TXF_OK
, SK_TRUE
}, {0, SK_FALSE
}},
648 /* SK_PNMI_HTX_OCTETHIGH */
649 {{XM_TXO_OK_HI
, SK_TRUE
}, {GM_TXO_OK_HI
, SK_TRUE
}},
650 /* SK_PNMI_HTX_OCTETLOW */
651 {{XM_TXO_OK_LO
, SK_FALSE
}, {GM_TXO_OK_LO
, SK_FALSE
}},
652 /* SK_PNMI_HTX_BROADCAST */
653 {{XM_TXF_BC_OK
, SK_TRUE
}, {GM_TXF_BC_OK
, SK_TRUE
}},
654 /* SK_PNMI_HTX_MULTICAST */
655 {{XM_TXF_MC_OK
, SK_TRUE
}, {GM_TXF_MC_OK
, SK_TRUE
}},
656 /* SK_PNMI_HTX_UNICAST */
657 {{XM_TXF_UC_OK
, SK_TRUE
}, {GM_TXF_UC_OK
, SK_TRUE
}},
658 /* SK_PNMI_HTX_BURST */
659 {{XM_TXE_BURST
, SK_TRUE
}, {0, SK_FALSE
}},
660 /* SK_PNMI_HTX_PMACC */
661 {{XM_TXF_MPAUSE
, SK_TRUE
}, {GM_TXF_MPAUSE
, SK_TRUE
}},
662 /* SK_PNMI_HTX_MACC */
663 {{XM_TXF_MCTRL
, SK_TRUE
}, {0, SK_FALSE
}},
664 /* SK_PNMI_HTX_COL */
665 {{0, SK_FALSE
}, {GM_TXF_COL
, SK_TRUE
}},
666 /* SK_PNMI_HTX_SINGLE_COL */
667 {{XM_TXF_SNG_COL
, SK_TRUE
}, {GM_TXF_SNG_COL
, SK_TRUE
}},
668 /* SK_PNMI_HTX_MULTI_COL */
669 {{XM_TXF_MUL_COL
, SK_TRUE
}, {GM_TXF_MUL_COL
, SK_TRUE
}},
670 /* SK_PNMI_HTX_EXCESS_COL */
671 {{XM_TXF_ABO_COL
, SK_TRUE
}, {GM_TXF_ABO_COL
, SK_TRUE
}},
672 /* SK_PNMI_HTX_LATE_COL */
673 {{XM_TXF_LAT_COL
, SK_TRUE
}, {GM_TXF_LAT_COL
, SK_TRUE
}},
674 /* SK_PNMI_HTX_DEFFERAL */
675 {{XM_TXF_DEF
, SK_TRUE
}, {0, SK_FALSE
}},
676 /* SK_PNMI_HTX_EXCESS_DEF */
677 {{XM_TXF_EX_DEF
, SK_TRUE
}, {0, SK_FALSE
}},
678 /* SK_PNMI_HTX_UNDERRUN */
679 {{XM_TXE_FIFO_UR
, SK_TRUE
}, {GM_TXE_FIFO_UR
, SK_TRUE
}},
680 /* SK_PNMI_HTX_CARRIER */
681 {{XM_TXE_CS_ERR
, SK_TRUE
}, {0, SK_FALSE
}},
682 /* SK_PNMI_HTX_UTILUNDER */
683 {{0, SK_FALSE
}, {0, SK_FALSE
}},
684 /* SK_PNMI_HTX_UTILOVER */
685 {{0, SK_FALSE
}, {0, SK_FALSE
}},
687 {{XM_TXF_64B
, SK_TRUE
}, {GM_TXF_64B
, SK_TRUE
}},
688 /* SK_PNMI_HTX_127 */
689 {{XM_TXF_127B
, SK_TRUE
}, {GM_TXF_127B
, SK_TRUE
}},
690 /* SK_PNMI_HTX_255 */
691 {{XM_TXF_255B
, SK_TRUE
}, {GM_TXF_255B
, SK_TRUE
}},
692 /* SK_PNMI_HTX_511 */
693 {{XM_TXF_511B
, SK_TRUE
}, {GM_TXF_511B
, SK_TRUE
}},
694 /* SK_PNMI_HTX_1023 */
695 {{XM_TXF_1023B
, SK_TRUE
}, {GM_TXF_1023B
, SK_TRUE
}},
696 /* SK_PNMI_HTX_MAX */
697 {{XM_TXF_MAX_SZ
, SK_TRUE
}, {GM_TXF_1518B
, SK_TRUE
}},
698 /* SK_PNMI_HTX_LONGFRAMES */
699 {{XM_TXF_LONG
, SK_TRUE
}, {GM_TXF_MAX_SZ
, SK_TRUE
}},
700 /* SK_PNMI_HTX_SYNC */
701 {{0, SK_FALSE
}, {0, SK_FALSE
}},
702 /* SK_PNMI_HTX_SYNC_OCTET */
703 {{0, SK_FALSE
}, {0, SK_FALSE
}},
704 /* SK_PNMI_HTX_RESERVED */
705 {{0, SK_FALSE
}, {0, SK_FALSE
}},
707 {{XM_RXF_OK
, SK_TRUE
}, {0, SK_FALSE
}},
708 /* SK_PNMI_HRX_OCTETHIGH */
709 {{XM_RXO_OK_HI
, SK_TRUE
}, {GM_RXO_OK_HI
, SK_TRUE
}},
710 /* SK_PNMI_HRX_OCTETLOW */
711 {{XM_RXO_OK_LO
, SK_FALSE
}, {GM_RXO_OK_LO
, SK_FALSE
}},
712 /* SK_PNMI_HRX_BADOCTETHIGH */
713 {{0, SK_FALSE
}, {GM_RXO_ERR_HI
, SK_TRUE
}},
714 /* SK_PNMI_HRX_BADOCTETLOW */
715 {{0, SK_FALSE
}, {GM_RXO_ERR_LO
, SK_TRUE
}},
716 /* SK_PNMI_HRX_BROADCAST */
717 {{XM_RXF_BC_OK
, SK_TRUE
}, {GM_RXF_BC_OK
, SK_TRUE
}},
718 /* SK_PNMI_HRX_MULTICAST */
719 {{XM_RXF_MC_OK
, SK_TRUE
}, {GM_RXF_MC_OK
, SK_TRUE
}},
720 /* SK_PNMI_HRX_UNICAST */
721 {{XM_RXF_UC_OK
, SK_TRUE
}, {GM_RXF_UC_OK
, SK_TRUE
}},
722 /* SK_PNMI_HRX_PMACC */
723 {{XM_RXF_MPAUSE
, SK_TRUE
}, {GM_RXF_MPAUSE
, SK_TRUE
}},
724 /* SK_PNMI_HRX_MACC */
725 {{XM_RXF_MCTRL
, SK_TRUE
}, {0, SK_FALSE
}},
726 /* SK_PNMI_HRX_PMACC_ERR */
727 {{XM_RXF_INV_MP
, SK_TRUE
}, {0, SK_FALSE
}},
728 /* SK_PNMI_HRX_MACC_UNKWN */
729 {{XM_RXF_INV_MOC
, SK_TRUE
}, {0, SK_FALSE
}},
730 /* SK_PNMI_HRX_BURST */
731 {{XM_RXE_BURST
, SK_TRUE
}, {0, SK_FALSE
}},
732 /* SK_PNMI_HRX_MISSED */
733 {{XM_RXE_FMISS
, SK_TRUE
}, {0, SK_FALSE
}},
734 /* SK_PNMI_HRX_FRAMING */
735 {{XM_RXF_FRA_ERR
, SK_TRUE
}, {0, SK_FALSE
}},
736 /* SK_PNMI_HRX_UNDERSIZE */
737 {{0, SK_FALSE
}, {GM_RXF_SHT
, SK_TRUE
}},
738 /* SK_PNMI_HRX_OVERFLOW */
739 {{XM_RXE_FIFO_OV
, SK_TRUE
}, {GM_RXE_FIFO_OV
, SK_TRUE
}},
740 /* SK_PNMI_HRX_JABBER */
741 {{XM_RXF_JAB_PKT
, SK_TRUE
}, {GM_RXF_JAB_PKT
, SK_TRUE
}},
742 /* SK_PNMI_HRX_CARRIER */
743 {{XM_RXE_CAR_ERR
, SK_TRUE
}, {0, SK_FALSE
}},
744 /* SK_PNMI_HRX_IRLENGTH */
745 {{XM_RXF_LEN_ERR
, SK_TRUE
}, {0, SK_FALSE
}},
746 /* SK_PNMI_HRX_SYMBOL */
747 {{XM_RXE_SYM_ERR
, SK_TRUE
}, {0, SK_FALSE
}},
748 /* SK_PNMI_HRX_SHORTS */
749 {{XM_RXE_SHT_ERR
, SK_TRUE
}, {0, SK_FALSE
}},
750 /* SK_PNMI_HRX_RUNT */
751 {{XM_RXE_RUNT
, SK_TRUE
}, {GM_RXE_FRAG
, SK_TRUE
}},
752 /* SK_PNMI_HRX_TOO_LONG */
753 {{XM_RXF_LNG_ERR
, SK_TRUE
}, {GM_RXF_LNG_ERR
, SK_TRUE
}},
754 /* SK_PNMI_HRX_FCS */
755 {{XM_RXF_FCS_ERR
, SK_TRUE
}, {GM_RXF_FCS_ERR
, SK_TRUE
}},
756 /* SK_PNMI_HRX_CEXT */
757 {{XM_RXF_CEX_ERR
, SK_TRUE
}, {0, SK_FALSE
}},
758 /* SK_PNMI_HRX_UTILUNDER */
759 {{0, SK_FALSE
}, {0, SK_FALSE
}},
760 /* SK_PNMI_HRX_UTILOVER */
761 {{0, SK_FALSE
}, {0, SK_FALSE
}},
763 {{XM_RXF_64B
, SK_TRUE
}, {GM_RXF_64B
, SK_TRUE
}},
764 /* SK_PNMI_HRX_127 */
765 {{XM_RXF_127B
, SK_TRUE
}, {GM_RXF_127B
, SK_TRUE
}},
766 /* SK_PNMI_HRX_255 */
767 {{XM_RXF_255B
, SK_TRUE
}, {GM_RXF_255B
, SK_TRUE
}},
768 /* SK_PNMI_HRX_511 */
769 {{XM_RXF_511B
, SK_TRUE
}, {GM_RXF_511B
, SK_TRUE
}},
770 /* SK_PNMI_HRX_1023 */
771 {{XM_RXF_1023B
, SK_TRUE
}, {GM_RXF_1023B
, SK_TRUE
}},
772 /* SK_PNMI_HRX_MAX */
773 {{XM_RXF_MAX_SZ
, SK_TRUE
}, {GM_RXF_1518B
, SK_TRUE
}},
774 /* SK_PNMI_HRX_LONGFRAMES */
775 {{0, SK_FALSE
}, {GM_RXF_MAX_SZ
, SK_TRUE
}},
776 /* SK_PNMI_HRX_RESERVED */
777 {{0, SK_FALSE
}, {0, SK_FALSE
}}
781 /*****************************************************************************
787 /*****************************************************************************
789 * SkPnmiInit - Init function of PNMI
792 * SK_INIT_DATA: Initialises the data structures
793 * SK_INIT_IO: Resets the XMAC statistics, determines the device and
795 * SK_INIT_RUN: Starts a timer event for port switch per hour
802 SK_AC
*pAC
, /* Pointer to adapter context */
803 SK_IOC IoC
, /* IO context handle */
804 int Level
) /* Initialization level */
806 unsigned int PortMax
; /* Number of ports */
807 unsigned int PortIndex
; /* Current port index in loop */
808 SK_U16 Val16
; /* Multiple purpose 16 bit variable */
809 SK_U8 Val8
; /* Mulitple purpose 8 bit variable */
810 SK_EVPARA EventParam
; /* Event struct for timer event */
811 SK_PNMI_VCT
*pVctBackupData
;
814 SK_DBG_MSG(pAC
, SK_DBGMOD_PNMI
, SK_DBGCAT_CTRL
,
815 ("PNMI: SkPnmiInit: Called, level=%d\n", Level
));
820 SK_MEMSET((char *)&pAC
->Pnmi
, 0, sizeof(pAC
->Pnmi
));
821 pAC
->Pnmi
.TrapBufFree
= SK_PNMI_TRAP_QUEUE_LEN
;
822 pAC
->Pnmi
.StartUpTime
= SK_PNMI_HUNDREDS_SEC(SkOsGetTime(pAC
));
823 pAC
->Pnmi
.RlmtChangeThreshold
= SK_PNMI_DEF_RLMT_CHG_THRES
;
824 for (PortIndex
= 0; PortIndex
< SK_MAX_MACS
; PortIndex
++) {
826 pAC
->Pnmi
.Port
[PortIndex
].ActiveFlag
= SK_FALSE
;
827 pAC
->Pnmi
.DualNetActiveFlag
= SK_FALSE
;
831 if (SK_PNMI_MAX_IDX
!= SK_PNMI_CNT_NO
) {
833 SK_ERR_LOG(pAC
, SK_ERRCL_SW
, SK_PNMI_ERR049
, SK_PNMI_ERR049MSG
);
835 SK_DBG_MSG(pAC
, SK_DBGMOD_PNMI
, SK_DBGCAT_INIT
| SK_DBGCAT_FATAL
,
836 ("CounterOffset struct size (%d) differs from"
837 "SK_PNMI_MAX_IDX (%d)\n",
838 SK_PNMI_CNT_NO
, SK_PNMI_MAX_IDX
));
841 if (SK_PNMI_MAX_IDX
!=
842 (sizeof(StatAddr
) / (sizeof(SK_PNMI_STATADDR
) * SK_PNMI_MAC_TYPES
))) {
844 SK_ERR_LOG(pAC
, SK_ERRCL_SW
, SK_PNMI_ERR050
, SK_PNMI_ERR050MSG
);
846 SK_DBG_MSG(pAC
, SK_DBGMOD_PNMI
, SK_DBGCAT_INIT
| SK_DBGCAT_FATAL
,
847 ("StatAddr table size (%d) differs from "
848 "SK_PNMI_MAX_IDX (%d)\n",
850 (sizeof(SK_PNMI_STATADDR
) * SK_PNMI_MAC_TYPES
)),
853 #endif /* SK_PNMI_CHECK */
860 PortMax
= pAC
->GIni
.GIMacsFound
;
862 for (PortIndex
= 0; PortIndex
< PortMax
; PortIndex
++) {
864 pAC
->GIni
.GIFunc
.pFnMacResetCounter(pAC
, IoC
, PortIndex
);
867 /* Initialize DSP variables for Vct() to 0xff => Never written! */
868 for (PortIndex
= 0; PortIndex
< PortMax
; PortIndex
++) {
869 pAC
->GIni
.GP
[PortIndex
].PCableLen
= 0xff;
870 pVctBackupData
= &pAC
->Pnmi
.VctBackup
[PortIndex
];
871 pVctBackupData
->PCableLen
= 0xff;
877 SK_IN16(IoC
, B0_CTST
, &Val16
);
878 if ((Val16
& CS_BUS_CLOCK
) == 0) {
880 pAC
->Pnmi
.PciBusSpeed
= 33;
883 pAC
->Pnmi
.PciBusSpeed
= 66;
889 SK_IN16(IoC
, B0_CTST
, &Val16
);
890 if ((Val16
& CS_BUS_SLOT_SZ
) == 0) {
892 pAC
->Pnmi
.PciBusWidth
= 32;
895 pAC
->Pnmi
.PciBusWidth
= 64;
901 switch (pAC
->GIni
.GIChipId
) {
902 case CHIP_ID_GENESIS
:
903 pAC
->Pnmi
.Chipset
= SK_PNMI_CHIPSET_XMAC
;
907 pAC
->Pnmi
.Chipset
= SK_PNMI_CHIPSET_YUKON
;
915 * Get PMD and DeviceType
917 SK_IN8(IoC
, B2_PMD_TYP
, &Val8
);
921 if (pAC
->GIni
.GIMacsFound
> 1) {
923 pAC
->Pnmi
.DeviceType
= 0x00020002;
926 pAC
->Pnmi
.DeviceType
= 0x00020001;
932 if (pAC
->GIni
.GIMacsFound
> 1) {
934 pAC
->Pnmi
.DeviceType
= 0x00020004;
937 pAC
->Pnmi
.DeviceType
= 0x00020003;
943 if (pAC
->GIni
.GIMacsFound
> 1) {
945 pAC
->Pnmi
.DeviceType
= 0x00020006;
948 pAC
->Pnmi
.DeviceType
= 0x00020005;
954 if (pAC
->GIni
.GIMacsFound
> 1) {
956 pAC
->Pnmi
.DeviceType
= 0x00020008;
959 pAC
->Pnmi
.DeviceType
= 0x00020007;
965 pAC
->Pnmi
.DeviceType
= 0;
972 SK_IN8(IoC
, B2_CONN_TYP
, &Val8
);
975 pAC
->Pnmi
.Connector
= 2;
979 pAC
->Pnmi
.Connector
= 3;
983 pAC
->Pnmi
.Connector
= 4;
987 pAC
->Pnmi
.Connector
= 5;
991 pAC
->Pnmi
.Connector
= 6;
995 pAC
->Pnmi
.Connector
= 1;
1002 * Start timer for RLMT change counter
1004 SK_MEMSET((char *)&EventParam
, 0, sizeof(EventParam
));
1005 SkTimerStart(pAC
, IoC
, &pAC
->Pnmi
.RlmtChangeEstimate
.EstTimer
,
1006 28125000, SKGE_PNMI
, SK_PNMI_EVT_CHG_EST_TIMER
,
1011 break; /* Nothing todo */
1017 /*****************************************************************************
1019 * SkPnmiGetVar - Retrieves the value of a single OID
1022 * Calls a general sub-function for all this stuff. If the instance
1023 * -1 is passed, the values of all instances are returned in an
1027 * SK_PNMI_ERR_OK The request was successfully performed
1028 * SK_PNMI_ERR_GENERAL A general severe internal error occured
1029 * SK_PNMI_ERR_TOO_SHORT The passed buffer is too short to take
1031 * SK_PNMI_ERR_UNKNOWN_OID The requested OID is unknown
1032 * SK_PNMI_ERR_UNKNOWN_INST The requested instance of the OID doesn't
1033 * exist (e.g. port instance 3 on a two port
1037 SK_AC
*pAC
, /* Pointer to adapter context */
1038 SK_IOC IoC
, /* IO context handle */
1039 SK_U32 Id
, /* Object ID that is to be processed */
1040 void *pBuf
, /* Buffer to which the management data will be copied */
1041 unsigned int *pLen
, /* On call: buffer length. On return: used buffer */
1042 SK_U32 Instance
, /* Instance (1..n) that is to be queried or -1 */
1043 SK_U32 NetIndex
) /* NetIndex (0..n), in single net mode always zero */
1045 SK_DBG_MSG(pAC
, SK_DBGMOD_PNMI
, SK_DBGCAT_CTRL
,
1046 ("PNMI: SkPnmiGetVar: Called, Id=0x%x, BufLen=%d, Instance=%d, NetIndex=%d\n",
1047 Id
, *pLen
, Instance
, NetIndex
));
1049 return (PnmiVar(pAC
, IoC
, SK_PNMI_GET
, Id
, (char *)pBuf
, pLen
,
1050 Instance
, NetIndex
));
1053 /*****************************************************************************
1055 * SkPnmiPreSetVar - Presets the value of a single OID
1058 * Calls a general sub-function for all this stuff. The preset does
1059 * the same as a set, but returns just before finally setting the
1060 * new value. This is usefull to check if a set might be successfull.
1061 * If the instance -1 is passed, an array of values is supposed and
1062 * all instances of the OID will be set.
1065 * SK_PNMI_ERR_OK The request was successfully performed.
1066 * SK_PNMI_ERR_GENERAL A general severe internal error occured.
1067 * SK_PNMI_ERR_TOO_SHORT The passed buffer is too short to contain
1068 * the correct data (e.g. a 32bit value is
1069 * needed, but a 16 bit value was passed).
1070 * SK_PNMI_ERR_BAD_VALUE The passed value is not in the valid
1072 * SK_PNMI_ERR_READ_ONLY The OID is read-only and cannot be set.
1073 * SK_PNMI_ERR_UNKNOWN_OID The requested OID is unknown.
1074 * SK_PNMI_ERR_UNKNOWN_INST The requested instance of the OID doesn't
1075 * exist (e.g. port instance 3 on a two port
1078 int SkPnmiPreSetVar(
1079 SK_AC
*pAC
, /* Pointer to adapter context */
1080 SK_IOC IoC
, /* IO context handle */
1081 SK_U32 Id
, /* Object ID that is to be processed */
1082 void *pBuf
, /* Buffer to which the management data will be copied */
1083 unsigned int *pLen
, /* Total length of management data */
1084 SK_U32 Instance
, /* Instance (1..n) that is to be set or -1 */
1085 SK_U32 NetIndex
) /* NetIndex (0..n), in single net mode always zero */
1087 SK_DBG_MSG(pAC
, SK_DBGMOD_PNMI
, SK_DBGCAT_CTRL
,
1088 ("PNMI: SkPnmiPreSetVar: Called, Id=0x%x, BufLen=%d, Instance=%d, NetIndex=%d\n",
1089 Id
, *pLen
, Instance
, NetIndex
));
1092 return (PnmiVar(pAC
, IoC
, SK_PNMI_PRESET
, Id
, (char *)pBuf
, pLen
,
1093 Instance
, NetIndex
));
1096 /*****************************************************************************
1098 * SkPnmiSetVar - Sets the value of a single OID
1101 * Calls a general sub-function for all this stuff. The preset does
1102 * the same as a set, but returns just before finally setting the
1103 * new value. This is usefull to check if a set might be successfull.
1104 * If the instance -1 is passed, an array of values is supposed and
1105 * all instances of the OID will be set.
1108 * SK_PNMI_ERR_OK The request was successfully performed.
1109 * SK_PNMI_ERR_GENERAL A general severe internal error occured.
1110 * SK_PNMI_ERR_TOO_SHORT The passed buffer is too short to contain
1111 * the correct data (e.g. a 32bit value is
1112 * needed, but a 16 bit value was passed).
1113 * SK_PNMI_ERR_BAD_VALUE The passed value is not in the valid
1115 * SK_PNMI_ERR_READ_ONLY The OID is read-only and cannot be set.
1116 * SK_PNMI_ERR_UNKNOWN_OID The requested OID is unknown.
1117 * SK_PNMI_ERR_UNKNOWN_INST The requested instance of the OID doesn't
1118 * exist (e.g. port instance 3 on a two port
1122 SK_AC
*pAC
, /* Pointer to adapter context */
1123 SK_IOC IoC
, /* IO context handle */
1124 SK_U32 Id
, /* Object ID that is to be processed */
1125 void *pBuf
, /* Buffer to which the management data will be copied */
1126 unsigned int *pLen
, /* Total length of management data */
1127 SK_U32 Instance
, /* Instance (1..n) that is to be set or -1 */
1128 SK_U32 NetIndex
) /* NetIndex (0..n), in single net mode always zero */
1130 SK_DBG_MSG(pAC
, SK_DBGMOD_PNMI
, SK_DBGCAT_CTRL
,
1131 ("PNMI: SkPnmiSetVar: Called, Id=0x%x, BufLen=%d, Instance=%d, NetIndex=%d\n",
1132 Id
, *pLen
, Instance
, NetIndex
));
1134 return (PnmiVar(pAC
, IoC
, SK_PNMI_SET
, Id
, (char *)pBuf
, pLen
,
1135 Instance
, NetIndex
));
1138 /*****************************************************************************
1140 * SkPnmiGetStruct - Retrieves the management database in SK_PNMI_STRUCT_DATA
1143 * Runs through the IdTable, queries the single OIDs and stores the
1144 * returned data into the management database structure
1145 * SK_PNMI_STRUCT_DATA. The offset of the OID in the structure
1146 * is stored in the IdTable. The return value of the function will also
1147 * be stored in SK_PNMI_STRUCT_DATA if the passed buffer has the
1148 * minimum size of SK_PNMI_MIN_STRUCT_SIZE.
1151 * SK_PNMI_ERR_OK The request was successfully performed
1152 * SK_PNMI_ERR_GENERAL A general severe internal error occured
1153 * SK_PNMI_ERR_TOO_SHORT The passed buffer is too short to take
1155 * SK_PNMI_ERR_UNKNOWN_NET The requested NetIndex doesn't exist
1157 int SkPnmiGetStruct(
1158 SK_AC
*pAC
, /* Pointer to adapter context */
1159 SK_IOC IoC
, /* IO context handle */
1160 void *pBuf
, /* Buffer to which the management data will be copied. */
1161 unsigned int *pLen
, /* Length of buffer */
1162 SK_U32 NetIndex
) /* NetIndex (0..n), in single net mode always zero */
1165 unsigned int TableIndex
;
1166 unsigned int DstOffset
;
1167 unsigned int InstanceNo
;
1168 unsigned int InstanceCnt
;
1170 unsigned int TmpLen
;
1171 char KeyArr
[SK_PNMI_VPD_ENTRIES
][SK_PNMI_VPD_KEY_SIZE
];
1174 SK_DBG_MSG(pAC
, SK_DBGMOD_PNMI
, SK_DBGCAT_CTRL
,
1175 ("PNMI: SkPnmiGetStruct: Called, BufLen=%d, NetIndex=%d\n",
1178 if (*pLen
< SK_PNMI_STRUCT_SIZE
) {
1180 if (*pLen
>= SK_PNMI_MIN_STRUCT_SIZE
) {
1182 SK_PNMI_SET_STAT(pBuf
, SK_PNMI_ERR_TOO_SHORT
,
1186 *pLen
= SK_PNMI_STRUCT_SIZE
;
1187 return (SK_PNMI_ERR_TOO_SHORT
);
1193 if (NetIndex
>= pAC
->Rlmt
.NumNets
) {
1194 return (SK_PNMI_ERR_UNKNOWN_NET
);
1197 /* Update statistic */
1198 SK_PNMI_CHECKFLAGS("SkPnmiGetStruct: On call");
1200 if ((Ret
= MacUpdate(pAC
, IoC
, 0, pAC
->GIni
.GIMacsFound
- 1)) !=
1203 SK_PNMI_SET_STAT(pBuf
, Ret
, (SK_U32
)(-1));
1204 *pLen
= SK_PNMI_MIN_STRUCT_SIZE
;
1208 if ((Ret
= RlmtUpdate(pAC
, IoC
, NetIndex
)) != SK_PNMI_ERR_OK
) {
1210 SK_PNMI_SET_STAT(pBuf
, Ret
, (SK_U32
)(-1));
1211 *pLen
= SK_PNMI_MIN_STRUCT_SIZE
;
1215 if ((Ret
= SirqUpdate(pAC
, IoC
)) != SK_PNMI_ERR_OK
) {
1217 SK_PNMI_SET_STAT(pBuf
, Ret
, (SK_U32
)(-1));
1218 *pLen
= SK_PNMI_MIN_STRUCT_SIZE
;
1223 * Increment semaphores to indicate that an update was
1226 pAC
->Pnmi
.MacUpdatedFlag
++;
1227 pAC
->Pnmi
.RlmtUpdatedFlag
++;
1228 pAC
->Pnmi
.SirqUpdatedFlag
++;
1230 /* Get vpd keys for instance calculation */
1231 Ret
= GetVpdKeyArr(pAC
, IoC
, &KeyArr
[0][0], sizeof(KeyArr
), &TmpLen
);
1232 if (Ret
!= SK_PNMI_ERR_OK
) {
1234 pAC
->Pnmi
.MacUpdatedFlag
--;
1235 pAC
->Pnmi
.RlmtUpdatedFlag
--;
1236 pAC
->Pnmi
.SirqUpdatedFlag
--;
1238 SK_PNMI_CHECKFLAGS("SkPnmiGetStruct: On return");
1239 SK_PNMI_SET_STAT(pBuf
, Ret
, (SK_U32
)(-1));
1240 *pLen
= SK_PNMI_MIN_STRUCT_SIZE
;
1241 return (SK_PNMI_ERR_GENERAL
);
1244 /* Retrieve values */
1245 SK_MEMSET((char *)pBuf
, 0, SK_PNMI_STRUCT_SIZE
);
1246 for (TableIndex
= 0; TableIndex
< ID_TABLE_SIZE
; TableIndex
++) {
1248 InstanceNo
= IdTable
[TableIndex
].InstanceNo
;
1249 for (InstanceCnt
= 1; InstanceCnt
<= InstanceNo
;
1252 DstOffset
= IdTable
[TableIndex
].Offset
+
1254 IdTable
[TableIndex
].StructSize
;
1257 * For the VPD the instance is not an index number
1258 * but the key itself. Determin with the instance
1259 * counter the VPD key to be used.
1261 if (IdTable
[TableIndex
].Id
== OID_SKGE_VPD_KEY
||
1262 IdTable
[TableIndex
].Id
== OID_SKGE_VPD_VALUE
||
1263 IdTable
[TableIndex
].Id
== OID_SKGE_VPD_ACCESS
||
1264 IdTable
[TableIndex
].Id
== OID_SKGE_VPD_ACTION
) {
1266 SK_STRNCPY((char *)&Instance
, KeyArr
[InstanceCnt
- 1], 4);
1269 Instance
= (SK_U32
)InstanceCnt
;
1272 TmpLen
= *pLen
- DstOffset
;
1273 Ret
= IdTable
[TableIndex
].Func(pAC
, IoC
, SK_PNMI_GET
,
1274 IdTable
[TableIndex
].Id
, (char *)pBuf
+
1275 DstOffset
, &TmpLen
, Instance
, TableIndex
, NetIndex
);
1278 * An unknown instance error means that we reached
1279 * the last instance of that variable. Proceed with
1280 * the next OID in the table and ignore the return
1283 if (Ret
== SK_PNMI_ERR_UNKNOWN_INST
) {
1288 if (Ret
!= SK_PNMI_ERR_OK
) {
1290 pAC
->Pnmi
.MacUpdatedFlag
--;
1291 pAC
->Pnmi
.RlmtUpdatedFlag
--;
1292 pAC
->Pnmi
.SirqUpdatedFlag
--;
1294 SK_PNMI_CHECKFLAGS("SkPnmiGetStruct: On return");
1295 SK_PNMI_SET_STAT(pBuf
, Ret
, DstOffset
);
1296 *pLen
= SK_PNMI_MIN_STRUCT_SIZE
;
1302 pAC
->Pnmi
.MacUpdatedFlag
--;
1303 pAC
->Pnmi
.RlmtUpdatedFlag
--;
1304 pAC
->Pnmi
.SirqUpdatedFlag
--;
1306 *pLen
= SK_PNMI_STRUCT_SIZE
;
1307 SK_PNMI_CHECKFLAGS("SkPnmiGetStruct: On return");
1308 SK_PNMI_SET_STAT(pBuf
, SK_PNMI_ERR_OK
, (SK_U32
)(-1));
1309 return (SK_PNMI_ERR_OK
);
1312 /*****************************************************************************
1314 * SkPnmiPreSetStruct - Presets the management database in SK_PNMI_STRUCT_DATA
1317 * Calls a general sub-function for all this set stuff. The preset does
1318 * the same as a set, but returns just before finally setting the
1319 * new value. This is usefull to check if a set might be successfull.
1320 * The sub-function runs through the IdTable, checks which OIDs are able
1321 * to set, and calls the handler function of the OID to perform the
1322 * preset. The return value of the function will also be stored in
1323 * SK_PNMI_STRUCT_DATA if the passed buffer has the minimum size of
1324 * SK_PNMI_MIN_STRUCT_SIZE.
1327 * SK_PNMI_ERR_OK The request was successfully performed.
1328 * SK_PNMI_ERR_GENERAL A general severe internal error occured.
1329 * SK_PNMI_ERR_TOO_SHORT The passed buffer is too short to contain
1330 * the correct data (e.g. a 32bit value is
1331 * needed, but a 16 bit value was passed).
1332 * SK_PNMI_ERR_BAD_VALUE The passed value is not in the valid
1335 int SkPnmiPreSetStruct(
1336 SK_AC
*pAC
, /* Pointer to adapter context */
1337 SK_IOC IoC
, /* IO context handle */
1338 void *pBuf
, /* Buffer which contains the data to be set */
1339 unsigned int *pLen
, /* Length of buffer */
1340 SK_U32 NetIndex
) /* NetIndex (0..n), in single net mode always zero */
1342 SK_DBG_MSG(pAC
, SK_DBGMOD_PNMI
, SK_DBGCAT_CTRL
,
1343 ("PNMI: SkPnmiPreSetStruct: Called, BufLen=%d, NetIndex=%d\n",
1346 return (PnmiStruct(pAC
, IoC
, SK_PNMI_PRESET
, (char *)pBuf
,
1350 /*****************************************************************************
1352 * SkPnmiSetStruct - Sets the management database in SK_PNMI_STRUCT_DATA
1355 * Calls a general sub-function for all this set stuff. The return value
1356 * of the function will also be stored in SK_PNMI_STRUCT_DATA if the
1357 * passed buffer has the minimum size of SK_PNMI_MIN_STRUCT_SIZE.
1358 * The sub-function runs through the IdTable, checks which OIDs are able
1359 * to set, and calls the handler function of the OID to perform the
1360 * set. The return value of the function will also be stored in
1361 * SK_PNMI_STRUCT_DATA if the passed buffer has the minimum size of
1362 * SK_PNMI_MIN_STRUCT_SIZE.
1365 * SK_PNMI_ERR_OK The request was successfully performed.
1366 * SK_PNMI_ERR_GENERAL A general severe internal error occured.
1367 * SK_PNMI_ERR_TOO_SHORT The passed buffer is too short to contain
1368 * the correct data (e.g. a 32bit value is
1369 * needed, but a 16 bit value was passed).
1370 * SK_PNMI_ERR_BAD_VALUE The passed value is not in the valid
1373 int SkPnmiSetStruct(
1374 SK_AC
*pAC
, /* Pointer to adapter context */
1375 SK_IOC IoC
, /* IO context handle */
1376 void *pBuf
, /* Buffer which contains the data to be set */
1377 unsigned int *pLen
, /* Length of buffer */
1378 SK_U32 NetIndex
) /* NetIndex (0..n), in single net mode always zero */
1380 SK_DBG_MSG(pAC
, SK_DBGMOD_PNMI
, SK_DBGCAT_CTRL
,
1381 ("PNMI: SkPnmiSetStruct: Called, BufLen=%d, NetIndex=%d\n",
1384 return (PnmiStruct(pAC
, IoC
, SK_PNMI_SET
, (char *)pBuf
,
1388 /*****************************************************************************
1390 * SkPnmiEvent - Event handler
1393 * Handles the following events:
1394 * SK_PNMI_EVT_SIRQ_OVERFLOW When a hardware counter overflows an
1395 * interrupt will be generated which is
1396 * first handled by SIRQ which generates a
1397 * this event. The event increments the
1398 * upper 32 bit of the 64 bit counter.
1399 * SK_PNMI_EVT_SEN_XXX The event is generated by the I2C module
1400 * when a sensor reports a warning or
1401 * error. The event will store a trap
1402 * message in the trap buffer.
1403 * SK_PNMI_EVT_CHG_EST_TIMER The timer event was initiated by this
1404 * module and is used to calculate the
1405 * port switches per hour.
1406 * SK_PNMI_EVT_CLEAR_COUNTER The event clears all counters and
1408 * SK_PNMI_EVT_XMAC_RESET The event is generated by the driver
1409 * before a hard reset of the XMAC is
1410 * performed. All counters will be saved
1411 * and added to the hardware counter
1412 * values after reset to grant continuous
1414 * SK_PNMI_EVT_RLMT_PORT_UP Generated by RLMT to notify that a port
1415 * went logically up. A trap message will
1416 * be stored to the trap buffer.
1417 * SK_PNMI_EVT_RLMT_PORT_DOWN Generated by RLMT to notify that a port
1418 * went logically down. A trap message will
1419 * be stored to the trap buffer.
1420 * SK_PNMI_EVT_RLMT_SEGMENTATION Generated by RLMT to notify that two
1421 * spanning tree root bridges were
1422 * detected. A trap message will be stored
1423 * to the trap buffer.
1424 * SK_PNMI_EVT_RLMT_ACTIVE_DOWN Notifies PNMI that an active port went
1425 * down. PNMI will not further add the
1426 * statistic values to the virtual port.
1427 * SK_PNMI_EVT_RLMT_ACTIVE_UP Notifies PNMI that a port went up and
1428 * is now an active port. PNMI will now
1429 * add the statistic data of this port to
1431 * SK_PNMI_EVT_RLMT_SET_NETS Notifies PNMI about the net mode. The first parameter
1432 * contains the number of nets. 1 means single net, 2 means
1433 * dual net. The second parameter is -1
1439 SK_AC
*pAC
, /* Pointer to adapter context */
1440 SK_IOC IoC
, /* IO context handle */
1441 SK_U32 Event
, /* Event-Id */
1442 SK_EVPARA Param
) /* Event dependent parameter */
1444 unsigned int PhysPortIndex
;
1445 unsigned int MaxNetNumber
;
1449 SK_U64 OverflowStatus
;
1455 SK_EVPARA EventParam
;
1459 SK_PNMI_ESTIMATE
*pEst
;
1462 SK_PNMI_VCT
*pVctBackupData
;
1469 if (Event
!= SK_PNMI_EVT_XMAC_RESET
) {
1471 SK_DBG_MSG(pAC
, SK_DBGMOD_PNMI
, SK_DBGCAT_CTRL
,
1472 ("PNMI: SkPnmiEvent: Called, Event=0x%x, Param=0x%x\n",
1473 (unsigned int)Event
, (unsigned int)Param
.Para64
));
1476 SK_PNMI_CHECKFLAGS("SkPnmiEvent: On call");
1478 MacType
= pAC
->GIni
.GIMacType
;
1482 case SK_PNMI_EVT_SIRQ_OVERFLOW
:
1483 PhysPortIndex
= (int)Param
.Para32
[0];
1484 MacStatus
= (SK_U16
)Param
.Para32
[1];
1486 if (PhysPortIndex
>= SK_MAX_MACS
) {
1488 SK_DBG_MSG(pAC
, SK_DBGMOD_PNMI
, SK_DBGCAT_CTRL
,
1489 ("PNMI: ERR: SkPnmiEvent: SK_PNMI_EVT_SIRQ_OVERFLOW parameter"
1490 " wrong, PhysPortIndex=0x%x\n",
1498 * Check which source caused an overflow interrupt.
1500 if ((pAC
->GIni
.GIFunc
.pFnMacOverflow(pAC
, IoC
, PhysPortIndex
,
1501 MacStatus
, &OverflowStatus
) != 0) ||
1502 (OverflowStatus
== 0)) {
1504 SK_PNMI_CHECKFLAGS("SkPnmiEvent: On return");
1509 * Check the overflow status register and increment
1510 * the upper dword of corresponding counter.
1512 for (CounterIndex
= 0; CounterIndex
< sizeof(Mask
) * 8;
1515 Mask
= (SK_U64
)1 << CounterIndex
;
1516 if ((OverflowStatus
& Mask
) == 0) {
1521 switch (StatOvrflwBit
[CounterIndex
][MacType
]) {
1523 case SK_PNMI_HTX_UTILUNDER
:
1524 case SK_PNMI_HTX_UTILOVER
:
1525 if (MacType
== SK_MAC_XMAC
) {
1526 XM_IN16(IoC
, PhysPortIndex
, XM_TX_CMD
, &Register
);
1527 Register
|= XM_TX_SAM_LINE
;
1528 XM_OUT16(IoC
, PhysPortIndex
, XM_TX_CMD
, Register
);
1532 case SK_PNMI_HRX_UTILUNDER
:
1533 case SK_PNMI_HRX_UTILOVER
:
1534 if (MacType
== SK_MAC_XMAC
) {
1535 XM_IN16(IoC
, PhysPortIndex
, XM_RX_CMD
, &Register
);
1536 Register
|= XM_RX_SAM_LINE
;
1537 XM_OUT16(IoC
, PhysPortIndex
, XM_RX_CMD
, Register
);
1541 case SK_PNMI_HTX_OCTETHIGH
:
1542 case SK_PNMI_HTX_OCTETLOW
:
1543 case SK_PNMI_HTX_RESERVED
:
1544 case SK_PNMI_HRX_OCTETHIGH
:
1545 case SK_PNMI_HRX_OCTETLOW
:
1546 case SK_PNMI_HRX_IRLENGTH
:
1547 case SK_PNMI_HRX_RESERVED
:
1550 * the following counters aren't be handled (id > 63)
1552 case SK_PNMI_HTX_SYNC
:
1553 case SK_PNMI_HTX_SYNC_OCTET
:
1556 case SK_PNMI_HRX_LONGFRAMES
:
1557 if (MacType
== SK_MAC_GMAC
) {
1558 pAC
->Pnmi
.Port
[PhysPortIndex
].
1559 CounterHigh
[CounterIndex
] ++;
1564 pAC
->Pnmi
.Port
[PhysPortIndex
].
1565 CounterHigh
[CounterIndex
] ++;
1570 case SK_PNMI_EVT_SEN_WAR_LOW
:
1572 if ((unsigned int)Param
.Para64
>= (unsigned int)pAC
->I2c
.MaxSens
) {
1574 SK_DBG_MSG(pAC
, SK_DBGMOD_PNMI
, SK_DBGCAT_CTRL
,
1575 ("PNMI: ERR: SkPnmiEvent: SK_PNMI_EVT_SEN_WAR_LOW parameter wrong, SensorIndex=%d\n",
1576 (unsigned int)Param
.Para64
));
1582 * Store a trap message in the trap buffer and generate
1583 * an event for user space applications with the
1584 * SK_DRIVER_SENDEVENT macro.
1586 QueueSensorTrap(pAC
, OID_SKGE_TRAP_SEN_WAR_LOW
,
1587 (unsigned int)Param
.Para64
);
1588 (void)SK_DRIVER_SENDEVENT(pAC
, IoC
);
1591 case SK_PNMI_EVT_SEN_WAR_UPP
:
1593 if ((unsigned int)Param
.Para64
>= (unsigned int)pAC
->I2c
.MaxSens
) {
1595 SK_DBG_MSG(pAC
, SK_DBGMOD_PNMI
, SK_DBGCAT_CTRL
,
1596 ("PNMI: ERR: SkPnmiEvent: SK_PNMI_EVT_SEN_WAR_UPP parameter wrong, SensorIndex=%d\n",
1597 (unsigned int)Param
.Para64
));
1603 * Store a trap message in the trap buffer and generate
1604 * an event for user space applications with the
1605 * SK_DRIVER_SENDEVENT macro.
1607 QueueSensorTrap(pAC
, OID_SKGE_TRAP_SEN_WAR_UPP
,
1608 (unsigned int)Param
.Para64
);
1609 (void)SK_DRIVER_SENDEVENT(pAC
, IoC
);
1612 case SK_PNMI_EVT_SEN_ERR_LOW
:
1614 if ((unsigned int)Param
.Para64
>= (unsigned int)pAC
->I2c
.MaxSens
) {
1616 SK_DBG_MSG(pAC
, SK_DBGMOD_PNMI
, SK_DBGCAT_CTRL
,
1617 ("PNMI: ERR: SkPnmiEvent: SK_PNMI_EVT_SEN_ERR_LOW parameter wrong, SensorIndex=%d\n",
1618 (unsigned int)Param
.Para64
));
1624 * Store a trap message in the trap buffer and generate
1625 * an event for user space applications with the
1626 * SK_DRIVER_SENDEVENT macro.
1628 QueueSensorTrap(pAC
, OID_SKGE_TRAP_SEN_ERR_LOW
,
1629 (unsigned int)Param
.Para64
);
1630 (void)SK_DRIVER_SENDEVENT(pAC
, IoC
);
1633 case SK_PNMI_EVT_SEN_ERR_UPP
:
1635 if ((unsigned int)Param
.Para64
>= (unsigned int)pAC
->I2c
.MaxSens
) {
1637 SK_DBG_MSG(pAC
, SK_DBGMOD_PNMI
, SK_DBGCAT_CTRL
,
1638 ("PNMI: ERR: SkPnmiEvent: SK_PNMI_EVT_SEN_ERR_UPP parameter wrong, SensorIndex=%d\n",
1639 (unsigned int)Param
.Para64
));
1645 * Store a trap message in the trap buffer and generate
1646 * an event for user space applications with the
1647 * SK_DRIVER_SENDEVENT macro.
1649 QueueSensorTrap(pAC
, OID_SKGE_TRAP_SEN_ERR_UPP
,
1650 (unsigned int)Param
.Para64
);
1651 (void)SK_DRIVER_SENDEVENT(pAC
, IoC
);
1654 case SK_PNMI_EVT_CHG_EST_TIMER
:
1656 * Calculate port switch average on a per hour basis
1657 * Time interval for check : 28125 ms
1658 * Number of values for average : 8
1660 * Be careful in changing these values, on change check
1661 * - typedef of SK_PNMI_ESTIMATE (Size of EstValue
1662 * array one less than value number)
1663 * - Timer initialization SkTimerStart() in SkPnmiInit
1664 * - Delta value below must be multiplicated with
1668 pEst
= &pAC
->Pnmi
.RlmtChangeEstimate
;
1669 CounterIndex
= pEst
->EstValueIndex
+ 1;
1670 if (CounterIndex
== 7) {
1674 pEst
->EstValueIndex
= CounterIndex
;
1676 NewestValue
= pAC
->Pnmi
.RlmtChangeCts
;
1677 OldestValue
= pEst
->EstValue
[CounterIndex
];
1678 pEst
->EstValue
[CounterIndex
] = NewestValue
;
1681 * Calculate average. Delta stores the number of
1682 * port switches per 28125 * 8 = 225000 ms
1684 if (NewestValue
>= OldestValue
) {
1686 Delta
= NewestValue
- OldestValue
;
1689 /* Overflow situation */
1690 Delta
= (SK_U64
)(0 - OldestValue
) + NewestValue
;
1694 * Extrapolate delta to port switches per hour.
1695 * Estimate = Delta * (3600000 / 225000)
1699 pAC
->Pnmi
.RlmtChangeEstimate
.Estimate
= Delta
<< 4;
1702 * Check if threshold is exceeded. If the threshold is
1703 * permanently exceeded every 28125 ms an event will be
1704 * generated to remind the user of this condition.
1706 if ((pAC
->Pnmi
.RlmtChangeThreshold
!= 0) &&
1707 (pAC
->Pnmi
.RlmtChangeEstimate
.Estimate
>=
1708 pAC
->Pnmi
.RlmtChangeThreshold
)) {
1710 QueueSimpleTrap(pAC
, OID_SKGE_TRAP_RLMT_CHANGE_THRES
);
1711 (void)SK_DRIVER_SENDEVENT(pAC
, IoC
);
1714 SK_MEMSET((char *)&EventParam
, 0, sizeof(EventParam
));
1715 SkTimerStart(pAC
, IoC
, &pAC
->Pnmi
.RlmtChangeEstimate
.EstTimer
,
1716 28125000, SKGE_PNMI
, SK_PNMI_EVT_CHG_EST_TIMER
,
1720 case SK_PNMI_EVT_CLEAR_COUNTER
:
1722 * Param.Para32[0] contains the NetIndex (0 ..1).
1723 * Param.Para32[1] is reserved, contains -1.
1725 NetIndex
= (SK_U32
)Param
.Para32
[0];
1728 if (NetIndex
>= pAC
->Rlmt
.NumNets
) {
1730 SK_DBG_MSG(pAC
, SK_DBGMOD_PNMI
, SK_DBGCAT_CTRL
,
1731 ("PNMI: ERR: SkPnmiEvent: SK_PNMI_EVT_CLEAR_COUNTER parameter wrong, NetIndex=%d\n",
1739 * Set all counters and timestamps to zero.
1740 * The according NetIndex is required as a
1741 * parameter of the event.
1743 ResetCounter(pAC
, IoC
, NetIndex
);
1746 case SK_PNMI_EVT_XMAC_RESET
:
1748 * To grant continuous counter values store the current
1749 * XMAC statistic values to the entries 1..n of the
1750 * CounterOffset array. XMAC Errata #2
1753 if ((unsigned int)Param
.Para64
>= SK_MAX_MACS
) {
1755 SK_DBG_MSG(pAC
, SK_DBGMOD_PNMI
, SK_DBGCAT_CTRL
,
1756 ("PNMI: ERR: SkPnmiEvent: SK_PNMI_EVT_XMAC_RESET parameter wrong, PhysPortIndex=%d\n",
1757 (unsigned int)Param
.Para64
));
1761 PhysPortIndex
= (unsigned int)Param
.Para64
;
1764 * Update XMAC statistic to get fresh values
1766 Ret
= MacUpdate(pAC
, IoC
, 0, pAC
->GIni
.GIMacsFound
- 1);
1767 if (Ret
!= SK_PNMI_ERR_OK
) {
1769 SK_PNMI_CHECKFLAGS("SkPnmiEvent: On return");
1773 * Increment semaphore to indicate that an update was
1776 pAC
->Pnmi
.MacUpdatedFlag
++;
1778 for (CounterIndex
= 0; CounterIndex
< SK_PNMI_MAX_IDX
;
1781 if (!StatAddr
[CounterIndex
][MacType
].GetOffset
) {
1786 pAC
->Pnmi
.Port
[PhysPortIndex
].CounterOffset
[CounterIndex
] =
1787 GetPhysStatVal(pAC
, IoC
, PhysPortIndex
, CounterIndex
);
1789 pAC
->Pnmi
.Port
[PhysPortIndex
].CounterHigh
[CounterIndex
] = 0;
1792 pAC
->Pnmi
.MacUpdatedFlag
--;
1795 case SK_PNMI_EVT_RLMT_PORT_UP
:
1796 PhysPortIndex
= (unsigned int)Param
.Para32
[0];
1798 if (PhysPortIndex
>= SK_MAX_MACS
) {
1800 SK_DBG_MSG(pAC
, SK_DBGMOD_PNMI
, SK_DBGCAT_CTRL
,
1801 ("PNMI: ERR: SkPnmiEvent: SK_PNMI_EVT_RLMT_PORT_UP parameter"
1802 " wrong, PhysPortIndex=%d\n", PhysPortIndex
));
1809 * Store a trap message in the trap buffer and generate an event for
1810 * user space applications with the SK_DRIVER_SENDEVENT macro.
1812 QueueRlmtPortTrap(pAC
, OID_SKGE_TRAP_RLMT_PORT_UP
, PhysPortIndex
);
1813 (void)SK_DRIVER_SENDEVENT(pAC
, IoC
);
1815 /* Bugfix for XMAC errata (#10620)*/
1816 if (MacType
== SK_MAC_XMAC
) {
1817 /* Add incremental difference to offset (#10620)*/
1818 (void)pAC
->GIni
.GIFunc
.pFnMacStatistic(pAC
, IoC
, PhysPortIndex
,
1819 XM_RXE_SHT_ERR
, &Val32
);
1821 Value
= (((SK_U64
)pAC
->Pnmi
.Port
[PhysPortIndex
].
1822 CounterHigh
[SK_PNMI_HRX_SHORTS
] << 32) | (SK_U64
)Val32
);
1823 pAC
->Pnmi
.Port
[PhysPortIndex
].CounterOffset
[SK_PNMI_HRX_SHORTS
] +=
1824 Value
- pAC
->Pnmi
.Port
[PhysPortIndex
].RxShortZeroMark
;
1827 /* Tell VctStatus() that a link was up meanwhile. */
1828 pAC
->Pnmi
.VctStatus
[PhysPortIndex
] |= SK_PNMI_VCT_LINK
;
1831 case SK_PNMI_EVT_RLMT_PORT_DOWN
:
1832 PhysPortIndex
= (unsigned int)Param
.Para32
[0];
1835 if (PhysPortIndex
>= SK_MAX_MACS
) {
1837 SK_DBG_MSG(pAC
, SK_DBGMOD_PNMI
, SK_DBGCAT_CTRL
,
1838 ("PNMI: ERR: SkPnmiEvent: SK_PNMI_EVT_RLMT_PORT_DOWN parameter"
1839 " wrong, PhysPortIndex=%d\n", PhysPortIndex
));
1846 * Store a trap message in the trap buffer and generate an event for
1847 * user space applications with the SK_DRIVER_SENDEVENT macro.
1849 QueueRlmtPortTrap(pAC
, OID_SKGE_TRAP_RLMT_PORT_DOWN
, PhysPortIndex
);
1850 (void)SK_DRIVER_SENDEVENT(pAC
, IoC
);
1852 /* Bugfix #10620 - get zero level for incremental difference */
1853 if (MacType
== SK_MAC_XMAC
) {
1855 (void)pAC
->GIni
.GIFunc
.pFnMacStatistic(pAC
, IoC
, PhysPortIndex
,
1856 XM_RXE_SHT_ERR
, &Val32
);
1858 pAC
->Pnmi
.Port
[PhysPortIndex
].RxShortZeroMark
=
1859 (((SK_U64
)pAC
->Pnmi
.Port
[PhysPortIndex
].
1860 CounterHigh
[SK_PNMI_HRX_SHORTS
] << 32) | (SK_U64
)Val32
);
1864 case SK_PNMI_EVT_RLMT_ACTIVE_DOWN
:
1865 PhysPortIndex
= (unsigned int)Param
.Para32
[0];
1866 NetIndex
= (SK_U32
)Param
.Para32
[1];
1869 if (PhysPortIndex
>= SK_MAX_MACS
) {
1871 SK_DBG_MSG(pAC
, SK_DBGMOD_PNMI
, SK_DBGCAT_CTRL
,
1872 ("PNMI: ERR: SkPnmiEvent: SK_PNMI_EVT_RLMT_ACTIVE_DOWN parameter too high, PhysPort=%d\n",
1876 if (NetIndex
>= pAC
->Rlmt
.NumNets
) {
1878 SK_DBG_MSG(pAC
, SK_DBGMOD_PNMI
, SK_DBGCAT_CTRL
,
1879 ("PNMI: ERR: SkPnmiEvent: SK_PNMI_EVT_RLMT_ACTIVE_DOWN parameter too high, NetIndex=%d\n",
1885 * For now, ignore event if NetIndex != 0.
1887 if (Param
.Para32
[1] != 0) {
1893 * Nothing to do if port is already inactive
1895 if (!pAC
->Pnmi
.Port
[PhysPortIndex
].ActiveFlag
) {
1901 * Update statistic counters to calculate new offset for the virtual
1902 * port and increment semaphore to indicate that an update was already
1905 if (MacUpdate(pAC
, IoC
, 0, pAC
->GIni
.GIMacsFound
- 1) !=
1908 SK_PNMI_CHECKFLAGS("SkPnmiEvent: On return");
1911 pAC
->Pnmi
.MacUpdatedFlag
++;
1914 * Calculate new counter offset for virtual port to grant continous
1915 * counting on port switches. The virtual port consists of all currently
1916 * active ports. The port down event indicates that a port is removed
1917 * from the virtual port. Therefore add the counter value of the removed
1918 * port to the CounterOffset for the virtual port to grant the same
1921 for (CounterIndex
= 0; CounterIndex
< SK_PNMI_MAX_IDX
;
1924 if (!StatAddr
[CounterIndex
][MacType
].GetOffset
) {
1929 Value
= GetPhysStatVal(pAC
, IoC
, PhysPortIndex
, CounterIndex
);
1931 pAC
->Pnmi
.VirtualCounterOffset
[CounterIndex
] += Value
;
1935 * Set port to inactive
1937 pAC
->Pnmi
.Port
[PhysPortIndex
].ActiveFlag
= SK_FALSE
;
1939 pAC
->Pnmi
.MacUpdatedFlag
--;
1942 case SK_PNMI_EVT_RLMT_ACTIVE_UP
:
1943 PhysPortIndex
= (unsigned int)Param
.Para32
[0];
1944 NetIndex
= (SK_U32
)Param
.Para32
[1];
1947 if (PhysPortIndex
>= SK_MAX_MACS
) {
1949 SK_DBG_MSG(pAC
, SK_DBGMOD_PNMI
, SK_DBGCAT_CTRL
,
1950 ("PNMI: ERR: SkPnmiEvent: SK_PNMI_EVT_RLMT_ACTIVE_UP parameter too high, PhysPort=%d\n",
1954 if (NetIndex
>= pAC
->Rlmt
.NumNets
) {
1956 SK_DBG_MSG(pAC
, SK_DBGMOD_PNMI
, SK_DBGCAT_CTRL
,
1957 ("PNMI: ERR: SkPnmiEvent: SK_PNMI_EVT_RLMT_ACTIVE_UP parameter too high, NetIndex=%d\n",
1963 * For now, ignore event if NetIndex != 0.
1965 if (Param
.Para32
[1] != 0) {
1971 * Nothing to do if port is already active
1973 if (pAC
->Pnmi
.Port
[PhysPortIndex
].ActiveFlag
) {
1979 * Statistic maintenance
1981 pAC
->Pnmi
.RlmtChangeCts
++;
1982 pAC
->Pnmi
.RlmtChangeTime
= SK_PNMI_HUNDREDS_SEC(SkOsGetTime(pAC
));
1985 * Store a trap message in the trap buffer and generate an event for
1986 * user space applications with the SK_DRIVER_SENDEVENT macro.
1988 QueueRlmtNewMacTrap(pAC
, PhysPortIndex
);
1989 (void)SK_DRIVER_SENDEVENT(pAC
, IoC
);
1992 * Update statistic counters to calculate new offset for the virtual
1993 * port and increment semaphore to indicate that an update was
1996 if (MacUpdate(pAC
, IoC
, 0, pAC
->GIni
.GIMacsFound
- 1) !=
1999 SK_PNMI_CHECKFLAGS("SkPnmiEvent: On return");
2002 pAC
->Pnmi
.MacUpdatedFlag
++;
2005 * Calculate new counter offset for virtual port to grant continous
2006 * counting on port switches. A new port is added to the virtual port.
2007 * Therefore substract the counter value of the new port from the
2008 * CounterOffset for the virtual port to grant the same value.
2010 for (CounterIndex
= 0; CounterIndex
< SK_PNMI_MAX_IDX
;
2013 if (!StatAddr
[CounterIndex
][MacType
].GetOffset
) {
2018 Value
= GetPhysStatVal(pAC
, IoC
, PhysPortIndex
, CounterIndex
);
2020 pAC
->Pnmi
.VirtualCounterOffset
[CounterIndex
] -= Value
;
2023 /* Set port to active */
2024 pAC
->Pnmi
.Port
[PhysPortIndex
].ActiveFlag
= SK_TRUE
;
2026 pAC
->Pnmi
.MacUpdatedFlag
--;
2029 case SK_PNMI_EVT_RLMT_SEGMENTATION
:
2031 * Para.Para32[0] contains the NetIndex.
2035 * Store a trap message in the trap buffer and generate an event for
2036 * user space applications with the SK_DRIVER_SENDEVENT macro.
2038 QueueSimpleTrap(pAC
, OID_SKGE_TRAP_RLMT_SEGMENTATION
);
2039 (void)SK_DRIVER_SENDEVENT(pAC
, IoC
);
2042 case SK_PNMI_EVT_RLMT_SET_NETS
:
2044 * Param.Para32[0] contains the number of Nets.
2045 * Param.Para32[1] is reserved, contains -1.
2048 * Check number of nets
2050 MaxNetNumber
= pAC
->GIni
.GIMacsFound
;
2051 if (((unsigned int)Param
.Para32
[0] < 1)
2052 || ((unsigned int)Param
.Para32
[0] > MaxNetNumber
)) {
2053 return (SK_PNMI_ERR_UNKNOWN_NET
);
2056 if ((unsigned int)Param
.Para32
[0] == 1) { /* single net mode */
2057 pAC
->Pnmi
.DualNetActiveFlag
= SK_FALSE
;
2059 else { /* dual net mode */
2060 pAC
->Pnmi
.DualNetActiveFlag
= SK_TRUE
;
2064 case SK_PNMI_EVT_VCT_RESET
:
2065 PhysPortIndex
= Param
.Para32
[0];
2066 pPrt
= &pAC
->GIni
.GP
[PhysPortIndex
];
2067 pVctBackupData
= &pAC
->Pnmi
.VctBackup
[PhysPortIndex
];
2069 if (pAC
->Pnmi
.VctStatus
[PhysPortIndex
] & SK_PNMI_VCT_PENDING
) {
2070 RetCode
= SkGmCableDiagStatus(pAC
, IoC
, PhysPortIndex
, SK_FALSE
);
2073 * VCT test is still running.
2074 * Start VCT timer counter again.
2076 SK_MEMSET((char *) &Param
, 0, sizeof(Param
));
2077 Param
.Para32
[0] = PhysPortIndex
;
2078 Param
.Para32
[1] = -1;
2079 SkTimerStart(pAC
, IoC
,
2080 &pAC
->Pnmi
.VctTimeout
[PhysPortIndex
].VctTimer
,
2081 4000000, SKGE_PNMI
, SK_PNMI_EVT_VCT_RESET
, Param
);
2084 pAC
->Pnmi
.VctStatus
[PhysPortIndex
] &= ~SK_PNMI_VCT_PENDING
;
2085 pAC
->Pnmi
.VctStatus
[PhysPortIndex
] |=
2086 (SK_PNMI_VCT_NEW_VCT_DATA
| SK_PNMI_VCT_TEST_DONE
);
2088 /* Copy results for later use to PNMI struct. */
2089 for (i
= 0; i
< 4; i
++) {
2090 if (pPrt
->PMdiPairSts
[i
] == SK_PNMI_VCT_NORMAL_CABLE
) {
2091 if ((pPrt
->PMdiPairLen
[i
] > 35) &&
2092 (pPrt
->PMdiPairLen
[i
] < 0xff)) {
2093 pPrt
->PMdiPairSts
[i
] = SK_PNMI_VCT_IMPEDANCE_MISMATCH
;
2096 if ((pPrt
->PMdiPairLen
[i
] > 35) &&
2097 (pPrt
->PMdiPairLen
[i
] != 0xff)) {
2098 CableLength
= 1000 *
2099 (((175 * pPrt
->PMdiPairLen
[i
]) / 210) - 28);
2104 pVctBackupData
->PMdiPairLen
[i
] = CableLength
;
2105 pVctBackupData
->PMdiPairSts
[i
] = pPrt
->PMdiPairSts
[i
];
2108 Param
.Para32
[0] = PhysPortIndex
;
2109 Param
.Para32
[1] = -1;
2110 SkEventQueue(pAC
, SKGE_DRV
, SK_DRV_PORT_RESET
, Param
);
2111 SkEventDispatcher(pAC
, IoC
);
2120 SK_PNMI_CHECKFLAGS("SkPnmiEvent: On return");
2125 /******************************************************************************
2131 /*****************************************************************************
2133 * PnmiVar - Gets, presets, and sets single OIDs
2136 * Looks up the requested OID, calls the corresponding handler
2137 * function, and passes the parameters with the get, preset, or
2138 * set command. The function is called by SkGePnmiGetVar,
2139 * SkGePnmiPreSetVar, or SkGePnmiSetVar.
2142 * SK_PNMI_ERR_XXX. For details have a look at the description of the
2143 * calling functions.
2144 * SK_PNMI_ERR_UNKNOWN_NET The requested NetIndex doesn't exist
2146 PNMI_STATIC
int PnmiVar(
2147 SK_AC
*pAC
, /* Pointer to adapter context */
2148 SK_IOC IoC
, /* IO context handle */
2149 int Action
, /* GET/PRESET/SET action */
2150 SK_U32 Id
, /* Object ID that is to be processed */
2151 char *pBuf
, /* Buffer used for the management data transfer */
2152 unsigned int *pLen
, /* Total length of pBuf management data */
2153 SK_U32 Instance
, /* Instance (1..n) that is to be set or -1 */
2154 SK_U32 NetIndex
) /* NetIndex (0..n), in single net mode always zero */
2156 unsigned int TableIndex
;
2160 if ((TableIndex
= LookupId(Id
)) == (unsigned int)(-1)) {
2163 return (SK_PNMI_ERR_UNKNOWN_OID
);
2166 /* Check NetIndex */
2167 if (NetIndex
>= pAC
->Rlmt
.NumNets
) {
2168 return (SK_PNMI_ERR_UNKNOWN_NET
);
2171 SK_PNMI_CHECKFLAGS("PnmiVar: On call");
2173 Ret
= IdTable
[TableIndex
].Func(pAC
, IoC
, Action
, Id
, pBuf
, pLen
,
2174 Instance
, TableIndex
, NetIndex
);
2176 SK_PNMI_CHECKFLAGS("PnmiVar: On return");
2181 /*****************************************************************************
2183 * PnmiStruct - Presets and Sets data in structure SK_PNMI_STRUCT_DATA
2186 * The return value of the function will also be stored in
2187 * SK_PNMI_STRUCT_DATA if the passed buffer has the minimum size of
2188 * SK_PNMI_MIN_STRUCT_SIZE. The sub-function runs through the IdTable,
2189 * checks which OIDs are able to set, and calls the handler function of
2190 * the OID to perform the set. The return value of the function will
2191 * also be stored in SK_PNMI_STRUCT_DATA if the passed buffer has the
2192 * minimum size of SK_PNMI_MIN_STRUCT_SIZE. The function is called
2193 * by SkGePnmiPreSetStruct and SkGePnmiSetStruct.
2196 * SK_PNMI_ERR_XXX. The codes are described in the calling functions.
2197 * SK_PNMI_ERR_UNKNOWN_NET The requested NetIndex doesn't exist
2199 PNMI_STATIC
int PnmiStruct(
2200 SK_AC
*pAC
, /* Pointer to adapter context */
2201 SK_IOC IoC
, /* IO context handle */
2202 int Action
, /* PRESET/SET action to be performed */
2203 char *pBuf
, /* Buffer used for the management data transfer */
2204 unsigned int *pLen
, /* Length of pBuf management data buffer */
2205 SK_U32 NetIndex
) /* NetIndex (0..n), in single net mode always zero */
2208 unsigned int TableIndex
;
2209 unsigned int DstOffset
;
2211 unsigned int InstanceNo
;
2212 unsigned int InstanceCnt
;
2217 /* Check if the passed buffer has the right size */
2218 if (*pLen
< SK_PNMI_STRUCT_SIZE
) {
2220 /* Check if we can return the error within the buffer */
2221 if (*pLen
>= SK_PNMI_MIN_STRUCT_SIZE
) {
2223 SK_PNMI_SET_STAT(pBuf
, SK_PNMI_ERR_TOO_SHORT
,
2227 *pLen
= SK_PNMI_STRUCT_SIZE
;
2228 return (SK_PNMI_ERR_TOO_SHORT
);
2231 /* Check NetIndex */
2232 if (NetIndex
>= pAC
->Rlmt
.NumNets
) {
2233 return (SK_PNMI_ERR_UNKNOWN_NET
);
2236 SK_PNMI_CHECKFLAGS("PnmiStruct: On call");
2239 * Update the values of RLMT and SIRQ and increment semaphores to
2240 * indicate that an update was already done.
2242 if ((Ret
= RlmtUpdate(pAC
, IoC
, NetIndex
)) != SK_PNMI_ERR_OK
) {
2244 SK_PNMI_SET_STAT(pBuf
, Ret
, (SK_U32
)(-1));
2245 *pLen
= SK_PNMI_MIN_STRUCT_SIZE
;
2249 if ((Ret
= SirqUpdate(pAC
, IoC
)) != SK_PNMI_ERR_OK
) {
2251 SK_PNMI_SET_STAT(pBuf
, Ret
, (SK_U32
)(-1));
2252 *pLen
= SK_PNMI_MIN_STRUCT_SIZE
;
2256 pAC
->Pnmi
.RlmtUpdatedFlag
++;
2257 pAC
->Pnmi
.SirqUpdatedFlag
++;
2259 /* Preset/Set values */
2260 for (TableIndex
= 0; TableIndex
< ID_TABLE_SIZE
; TableIndex
++) {
2262 if ((IdTable
[TableIndex
].Access
!= SK_PNMI_RW
) &&
2263 (IdTable
[TableIndex
].Access
!= SK_PNMI_WO
)) {
2268 InstanceNo
= IdTable
[TableIndex
].InstanceNo
;
2269 Id
= IdTable
[TableIndex
].Id
;
2271 for (InstanceCnt
= 1; InstanceCnt
<= InstanceNo
;
2274 DstOffset
= IdTable
[TableIndex
].Offset
+
2276 IdTable
[TableIndex
].StructSize
;
2279 * Because VPD multiple instance variables are
2280 * not setable we do not need to evaluate VPD
2281 * instances. Have a look to VPD instance
2282 * calculation in SkPnmiGetStruct().
2284 Instance
= (SK_U32
)InstanceCnt
;
2287 * Evaluate needed buffer length
2290 Ret
= IdTable
[TableIndex
].Func(pAC
, IoC
,
2291 SK_PNMI_GET
, IdTable
[TableIndex
].Id
,
2292 NULL
, &Len
, Instance
, TableIndex
, NetIndex
);
2294 if (Ret
== SK_PNMI_ERR_UNKNOWN_INST
) {
2298 if (Ret
!= SK_PNMI_ERR_TOO_SHORT
) {
2300 pAC
->Pnmi
.RlmtUpdatedFlag
--;
2301 pAC
->Pnmi
.SirqUpdatedFlag
--;
2303 SK_PNMI_CHECKFLAGS("PnmiStruct: On return");
2304 SK_PNMI_SET_STAT(pBuf
,
2305 SK_PNMI_ERR_GENERAL
, DstOffset
);
2306 *pLen
= SK_PNMI_MIN_STRUCT_SIZE
;
2307 return (SK_PNMI_ERR_GENERAL
);
2309 if (Id
== OID_SKGE_VPD_ACTION
) {
2311 switch (*(pBuf
+ DstOffset
)) {
2313 case SK_PNMI_VPD_CREATE
:
2314 Len
= 3 + *(pBuf
+ DstOffset
+ 3);
2317 case SK_PNMI_VPD_DELETE
:
2327 /* Call the OID handler function */
2328 Ret
= IdTable
[TableIndex
].Func(pAC
, IoC
, Action
,
2329 IdTable
[TableIndex
].Id
, pBuf
+ DstOffset
,
2330 &Len
, Instance
, TableIndex
, NetIndex
);
2332 if (Ret
!= SK_PNMI_ERR_OK
) {
2334 pAC
->Pnmi
.RlmtUpdatedFlag
--;
2335 pAC
->Pnmi
.SirqUpdatedFlag
--;
2337 SK_PNMI_CHECKFLAGS("PnmiStruct: On return");
2338 SK_PNMI_SET_STAT(pBuf
, SK_PNMI_ERR_BAD_VALUE
,
2340 *pLen
= SK_PNMI_MIN_STRUCT_SIZE
;
2341 return (SK_PNMI_ERR_BAD_VALUE
);
2346 pAC
->Pnmi
.RlmtUpdatedFlag
--;
2347 pAC
->Pnmi
.SirqUpdatedFlag
--;
2349 SK_PNMI_CHECKFLAGS("PnmiStruct: On return");
2350 SK_PNMI_SET_STAT(pBuf
, SK_PNMI_ERR_OK
, (SK_U32
)(-1));
2351 return (SK_PNMI_ERR_OK
);
2354 /*****************************************************************************
2356 * LookupId - Lookup an OID in the IdTable
2359 * Scans the IdTable to find the table entry of an OID.
2362 * The table index or -1 if not found.
2364 PNMI_STATIC
int LookupId(
2365 SK_U32 Id
) /* Object identifier to be searched */
2369 for (i
= 0; i
< ID_TABLE_SIZE
; i
++) {
2371 if (IdTable
[i
].Id
== Id
) {
2380 /*****************************************************************************
2382 * OidStruct - Handler of OID_SKGE_ALL_DATA
2385 * This OID performs a Get/Preset/SetStruct call and returns all data
2386 * in a SK_PNMI_STRUCT_DATA structure.
2389 * SK_PNMI_ERR_OK The request was successfully performed.
2390 * SK_PNMI_ERR_GENERAL A general severe internal error occured.
2391 * SK_PNMI_ERR_TOO_SHORT The passed buffer is too short to contain
2392 * the correct data (e.g. a 32bit value is
2393 * needed, but a 16 bit value was passed).
2394 * SK_PNMI_ERR_BAD_VALUE The passed value is not in the valid
2396 * SK_PNMI_ERR_READ_ONLY The OID is read-only and cannot be set.
2397 * SK_PNMI_ERR_UNKNOWN_INST The requested instance of the OID doesn't
2398 * exist (e.g. port instance 3 on a two port
2401 PNMI_STATIC
int OidStruct(
2402 SK_AC
*pAC
, /* Pointer to adapter context */
2403 SK_IOC IoC
, /* IO context handle */
2404 int Action
, /* GET/PRESET/SET action */
2405 SK_U32 Id
, /* Object ID that is to be processed */
2406 char *pBuf
, /* Buffer used for the management data transfer */
2407 unsigned int *pLen
, /* On call: pBuf buffer length. On return: used buffer */
2408 SK_U32 Instance
, /* Instance (1..n) that is to be queried or -1 */
2409 unsigned int TableIndex
, /* Index to the Id table */
2410 SK_U32 NetIndex
) /* NetIndex (0..n), in single net mode always zero */
2412 if (Id
!= OID_SKGE_ALL_DATA
) {
2414 SK_ERR_LOG(pAC
, SK_ERRCL_SW
, SK_PNMI_ERR003
,
2418 return (SK_PNMI_ERR_GENERAL
);
2422 * Check instance. We only handle single instance variables
2424 if (Instance
!= (SK_U32
)(-1) && Instance
!= 1) {
2427 return (SK_PNMI_ERR_UNKNOWN_INST
);
2433 return (SkPnmiGetStruct(pAC
, IoC
, pBuf
, pLen
, NetIndex
));
2435 case SK_PNMI_PRESET
:
2436 return (SkPnmiPreSetStruct(pAC
, IoC
, pBuf
, pLen
, NetIndex
));
2439 return (SkPnmiSetStruct(pAC
, IoC
, pBuf
, pLen
, NetIndex
));
2442 SK_ERR_LOG(pAC
, SK_ERRCL_SW
, SK_PNMI_ERR004
, SK_PNMI_ERR004MSG
);
2445 return (SK_PNMI_ERR_GENERAL
);
2448 /*****************************************************************************
2450 * Perform - OID handler of OID_SKGE_ACTION
2456 * SK_PNMI_ERR_OK The request was successfully performed.
2457 * SK_PNMI_ERR_GENERAL A general severe internal error occured.
2458 * SK_PNMI_ERR_TOO_SHORT The passed buffer is too short to contain
2459 * the correct data (e.g. a 32bit value is
2460 * needed, but a 16 bit value was passed).
2461 * SK_PNMI_ERR_BAD_VALUE The passed value is not in the valid
2463 * SK_PNMI_ERR_READ_ONLY The OID is read-only and cannot be set.
2464 * SK_PNMI_ERR_UNKNOWN_INST The requested instance of the OID doesn't
2465 * exist (e.g. port instance 3 on a two port
2468 PNMI_STATIC
int Perform(
2469 SK_AC
*pAC
, /* Pointer to adapter context */
2470 SK_IOC IoC
, /* IO context handle */
2471 int Action
, /* GET/PRESET/SET action */
2472 SK_U32 Id
, /* Object ID that is to be processed */
2473 char *pBuf
, /* Buffer used for the management data transfer */
2474 unsigned int *pLen
, /* On call: pBuf buffer length. On return: used buffer */
2475 SK_U32 Instance
, /* Instance (1..n) that is to be queried or -1 */
2476 unsigned int TableIndex
, /* Index to the Id table */
2477 SK_U32 NetIndex
) /* NetIndex (0..n), in single net mode always zero */
2484 * Check instance. We only handle single instance variables
2486 if (Instance
!= (SK_U32
)(-1) && Instance
!= 1) {
2489 return (SK_PNMI_ERR_UNKNOWN_INST
);
2492 if (*pLen
< sizeof(SK_U32
)) {
2494 *pLen
= sizeof(SK_U32
);
2495 return (SK_PNMI_ERR_TOO_SHORT
);
2498 /* Check if a get should be performed */
2499 if (Action
== SK_PNMI_GET
) {
2501 /* A get is easy. We always return the same value */
2502 ActionOp
= (SK_U32
)SK_PNMI_ACT_IDLE
;
2503 SK_PNMI_STORE_U32(pBuf
, ActionOp
);
2504 *pLen
= sizeof(SK_U32
);
2506 return (SK_PNMI_ERR_OK
);
2509 /* Continue with PRESET/SET action */
2510 if (*pLen
> sizeof(SK_U32
)) {
2512 return (SK_PNMI_ERR_BAD_VALUE
);
2515 /* Check if the command is a known one */
2516 SK_PNMI_READ_U32(pBuf
, ActionOp
);
2517 if (*pLen
> sizeof(SK_U32
) ||
2518 (ActionOp
!= SK_PNMI_ACT_IDLE
&&
2519 ActionOp
!= SK_PNMI_ACT_RESET
&&
2520 ActionOp
!= SK_PNMI_ACT_SELFTEST
&&
2521 ActionOp
!= SK_PNMI_ACT_RESETCNT
)) {
2524 return (SK_PNMI_ERR_BAD_VALUE
);
2527 /* A preset ends here */
2528 if (Action
== SK_PNMI_PRESET
) {
2530 return (SK_PNMI_ERR_OK
);
2535 case SK_PNMI_ACT_IDLE
:
2539 case SK_PNMI_ACT_RESET
:
2541 * Perform a driver reset or something that comes near
2544 Ret
= SK_DRIVER_RESET(pAC
, IoC
);
2547 SK_ERR_LOG(pAC
, SK_ERRCL_SW
, SK_PNMI_ERR005
,
2550 return (SK_PNMI_ERR_GENERAL
);
2554 case SK_PNMI_ACT_SELFTEST
:
2556 * Perform a driver selftest or something similar to this.
2557 * Currently this feature is not used and will probably
2558 * implemented in another way.
2560 Ret
= SK_DRIVER_SELFTEST(pAC
, IoC
);
2561 pAC
->Pnmi
.TestResult
= Ret
;
2564 case SK_PNMI_ACT_RESETCNT
:
2565 /* Set all counters and timestamps to zero */
2566 ResetCounter(pAC
, IoC
, NetIndex
);
2570 SK_ERR_LOG(pAC
, SK_ERRCL_SW
, SK_PNMI_ERR006
,
2573 return (SK_PNMI_ERR_GENERAL
);
2576 return (SK_PNMI_ERR_OK
);
2579 /*****************************************************************************
2581 * Mac8023Stat - OID handler of OID_GEN_XXX and OID_802_3_XXX
2584 * Retrieves the statistic values of the virtual port (logical
2585 * index 0). Only special OIDs of NDIS are handled which consist
2586 * of a 32 bit instead of a 64 bit value. The OIDs are public
2587 * because perhaps some other platform can use them too.
2590 * SK_PNMI_ERR_OK The request was successfully performed.
2591 * SK_PNMI_ERR_GENERAL A general severe internal error occured.
2592 * SK_PNMI_ERR_TOO_SHORT The passed buffer is too short to contain
2593 * the correct data (e.g. a 32bit value is
2594 * needed, but a 16 bit value was passed).
2595 * SK_PNMI_ERR_UNKNOWN_INST The requested instance of the OID doesn't
2596 * exist (e.g. port instance 3 on a two port
2599 PNMI_STATIC
int Mac8023Stat(
2600 SK_AC
*pAC
, /* Pointer to adapter context */
2601 SK_IOC IoC
, /* IO context handle */
2602 int Action
, /* GET/PRESET/SET action */
2603 SK_U32 Id
, /* Object ID that is to be processed */
2604 char *pBuf
, /* Buffer used for the management data transfer */
2605 unsigned int *pLen
, /* On call: pBuf buffer length. On return: used buffer */
2606 SK_U32 Instance
, /* Instance (1..n) that is to be queried or -1 */
2607 unsigned int TableIndex
, /* Index to the Id table */
2608 SK_U32 NetIndex
) /* NetIndex (0..n), in single net mode always zero */
2613 SK_BOOL Is64BitReq
= SK_FALSE
;
2616 * Only the active Mac is returned
2618 if (Instance
!= (SK_U32
)(-1) && Instance
!= 1) {
2621 return (SK_PNMI_ERR_UNKNOWN_INST
);
2627 if (Action
!= SK_PNMI_GET
) {
2630 return (SK_PNMI_ERR_READ_ONLY
);
2636 case OID_802_3_PERMANENT_ADDRESS
:
2637 case OID_802_3_CURRENT_ADDRESS
:
2638 if (*pLen
< sizeof(SK_MAC_ADDR
)) {
2640 *pLen
= sizeof(SK_MAC_ADDR
);
2641 return (SK_PNMI_ERR_TOO_SHORT
);
2646 #ifndef SK_NDIS_64BIT_CTR
2647 if (*pLen
< sizeof(SK_U32
)) {
2648 *pLen
= sizeof(SK_U32
);
2649 return (SK_PNMI_ERR_TOO_SHORT
);
2652 #else /* SK_NDIS_64BIT_CTR */
2654 /* for compatibility, at least 32bit are required for OID */
2655 if (*pLen
< sizeof(SK_U32
)) {
2657 * but indicate handling for 64bit values,
2658 * if insufficient space is provided
2660 *pLen
= sizeof(SK_U64
);
2661 return (SK_PNMI_ERR_TOO_SHORT
);
2664 Is64BitReq
= (*pLen
< sizeof(SK_U64
)) ? SK_FALSE
: SK_TRUE
;
2665 #endif /* SK_NDIS_64BIT_CTR */
2670 * Update all statistics, because we retrieve virtual MAC, which
2671 * consists of multiple physical statistics and increment semaphore
2672 * to indicate that an update was already done.
2674 Ret
= MacUpdate(pAC
, IoC
, 0, pAC
->GIni
.GIMacsFound
- 1);
2675 if ( Ret
!= SK_PNMI_ERR_OK
) {
2680 pAC
->Pnmi
.MacUpdatedFlag
++;
2683 * Get value (MAC Index 0 identifies the virtual MAC)
2687 case OID_802_3_PERMANENT_ADDRESS
:
2688 CopyMac(pBuf
, &pAC
->Addr
.Net
[NetIndex
].PermanentMacAddress
);
2689 *pLen
= sizeof(SK_MAC_ADDR
);
2692 case OID_802_3_CURRENT_ADDRESS
:
2693 CopyMac(pBuf
, &pAC
->Addr
.Net
[NetIndex
].CurrentMacAddress
);
2694 *pLen
= sizeof(SK_MAC_ADDR
);
2698 StatVal
= GetStatVal(pAC
, IoC
, 0, IdTable
[TableIndex
].Param
, NetIndex
);
2700 /* by default 32bit values are evaluated */
2702 StatVal32
= (SK_U32
)StatVal
;
2703 SK_PNMI_STORE_U32(pBuf
, StatVal32
);
2704 *pLen
= sizeof(SK_U32
);
2707 SK_PNMI_STORE_U64(pBuf
, StatVal
);
2708 *pLen
= sizeof(SK_U64
);
2713 pAC
->Pnmi
.MacUpdatedFlag
--;
2715 return (SK_PNMI_ERR_OK
);
2718 /*****************************************************************************
2720 * MacPrivateStat - OID handler function of OID_SKGE_STAT_XXX
2723 * Retrieves the MAC statistic data.
2726 * SK_PNMI_ERR_OK The request was successfully performed.
2727 * SK_PNMI_ERR_GENERAL A general severe internal error occured.
2728 * SK_PNMI_ERR_TOO_SHORT The passed buffer is too short to contain
2729 * the correct data (e.g. a 32bit value is
2730 * needed, but a 16 bit value was passed).
2731 * SK_PNMI_ERR_UNKNOWN_INST The requested instance of the OID doesn't
2732 * exist (e.g. port instance 3 on a two port
2735 PNMI_STATIC
int MacPrivateStat(
2736 SK_AC
*pAC
, /* Pointer to adapter context */
2737 SK_IOC IoC
, /* IO context handle */
2738 int Action
, /* GET/PRESET/SET action */
2739 SK_U32 Id
, /* Object ID that is to be processed */
2740 char *pBuf
, /* Buffer used for the management data transfer */
2741 unsigned int *pLen
, /* On call: pBuf buffer length. On return: used buffer */
2742 SK_U32 Instance
, /* Instance (1..n) that is to be queried or -1 */
2743 unsigned int TableIndex
, /* Index to the Id table */
2744 SK_U32 NetIndex
) /* NetIndex (0..n), in single net mode always zero */
2746 unsigned int LogPortMax
;
2747 unsigned int LogPortIndex
;
2748 unsigned int PhysPortMax
;
2750 unsigned int Offset
;
2757 /* Calculate instance if wished. MAC index 0 is the virtual MAC */
2758 PhysPortMax
= pAC
->GIni
.GIMacsFound
;
2759 LogPortMax
= SK_PNMI_PORT_PHYS2LOG(PhysPortMax
);
2761 MacType
= pAC
->GIni
.GIMacType
;
2763 if (pAC
->Pnmi
.DualNetActiveFlag
== SK_TRUE
) { /* Dual net mode */
2767 if ((Instance
!= (SK_U32
)(-1))) { /* Only one specific instance is queried */
2768 /* Check instance range */
2769 if ((Instance
< 1) || (Instance
> LogPortMax
)) {
2772 return (SK_PNMI_ERR_UNKNOWN_INST
);
2774 LogPortIndex
= SK_PNMI_PORT_INST2LOG(Instance
);
2775 Limit
= LogPortIndex
+ 1;
2778 else { /* Instance == (SK_U32)(-1), get all Instances of that OID */
2785 if (Action
!= SK_PNMI_GET
) {
2788 return (SK_PNMI_ERR_READ_ONLY
);
2792 if (*pLen
< (Limit
- LogPortIndex
) * sizeof(SK_U64
)) {
2794 *pLen
= (Limit
- LogPortIndex
) * sizeof(SK_U64
);
2795 return (SK_PNMI_ERR_TOO_SHORT
);
2799 * Update MAC statistic and increment semaphore to indicate that
2800 * an update was already done.
2802 Ret
= MacUpdate(pAC
, IoC
, 0, pAC
->GIni
.GIMacsFound
- 1);
2803 if (Ret
!= SK_PNMI_ERR_OK
) {
2808 pAC
->Pnmi
.MacUpdatedFlag
++;
2812 for (; LogPortIndex
< Limit
; LogPortIndex
++) {
2816 /* XXX not yet implemented due to XMAC problems
2817 case OID_SKGE_STAT_TX_UTIL:
2818 return (SK_PNMI_ERR_GENERAL);
2820 /* XXX not yet implemented due to XMAC problems
2821 case OID_SKGE_STAT_RX_UTIL:
2822 return (SK_PNMI_ERR_GENERAL);
2824 case OID_SKGE_STAT_RX
:
2825 if (MacType
== SK_MAC_GMAC
) {
2827 GetStatVal(pAC
, IoC
, LogPortIndex
,
2828 SK_PNMI_HRX_BROADCAST
, NetIndex
) +
2829 GetStatVal(pAC
, IoC
, LogPortIndex
,
2830 SK_PNMI_HRX_MULTICAST
, NetIndex
) +
2831 GetStatVal(pAC
, IoC
, LogPortIndex
,
2832 SK_PNMI_HRX_UNICAST
, NetIndex
) +
2833 GetStatVal(pAC
, IoC
, LogPortIndex
,
2834 SK_PNMI_HRX_UNDERSIZE
, NetIndex
);
2837 StatVal
= GetStatVal(pAC
, IoC
, LogPortIndex
,
2838 IdTable
[TableIndex
].Param
, NetIndex
);
2842 case OID_SKGE_STAT_TX
:
2843 if (MacType
== SK_MAC_GMAC
) {
2845 GetStatVal(pAC
, IoC
, LogPortIndex
,
2846 SK_PNMI_HTX_BROADCAST
, NetIndex
) +
2847 GetStatVal(pAC
, IoC
, LogPortIndex
,
2848 SK_PNMI_HTX_MULTICAST
, NetIndex
) +
2849 GetStatVal(pAC
, IoC
, LogPortIndex
,
2850 SK_PNMI_HTX_UNICAST
, NetIndex
);
2853 StatVal
= GetStatVal(pAC
, IoC
, LogPortIndex
,
2854 IdTable
[TableIndex
].Param
, NetIndex
);
2859 StatVal
= GetStatVal(pAC
, IoC
, LogPortIndex
,
2860 IdTable
[TableIndex
].Param
, NetIndex
);
2862 SK_PNMI_STORE_U64(pBuf
+ Offset
, StatVal
);
2864 Offset
+= sizeof(SK_U64
);
2868 pAC
->Pnmi
.MacUpdatedFlag
--;
2870 return (SK_PNMI_ERR_OK
);
2873 /*****************************************************************************
2875 * Addr - OID handler function of OID_SKGE_PHYS_CUR_ADDR and _FAC_ADDR
2878 * Get/Presets/Sets the current and factory MAC address. The MAC
2879 * address of the virtual port, which is reported to the OS, may
2880 * not be changed, but the physical ones. A set to the virtual port
2881 * will be ignored. No error should be reported because otherwise
2882 * a multiple instance set (-1) would always fail.
2885 * SK_PNMI_ERR_OK The request was successfully performed.
2886 * SK_PNMI_ERR_GENERAL A general severe internal error occured.
2887 * SK_PNMI_ERR_TOO_SHORT The passed buffer is too short to contain
2888 * the correct data (e.g. a 32bit value is
2889 * needed, but a 16 bit value was passed).
2890 * SK_PNMI_ERR_BAD_VALUE The passed value is not in the valid
2892 * SK_PNMI_ERR_READ_ONLY The OID is read-only and cannot be set.
2893 * SK_PNMI_ERR_UNKNOWN_INST The requested instance of the OID doesn't
2894 * exist (e.g. port instance 3 on a two port
2897 PNMI_STATIC
int Addr(
2898 SK_AC
*pAC
, /* Pointer to adapter context */
2899 SK_IOC IoC
, /* IO context handle */
2900 int Action
, /* GET/PRESET/SET action */
2901 SK_U32 Id
, /* Object ID that is to be processed */
2902 char *pBuf
, /* Buffer used for the management data transfer */
2903 unsigned int *pLen
, /* On call: pBuf buffer length. On return: used buffer */
2904 SK_U32 Instance
, /* Instance (1..n) that is to be queried or -1 */
2905 unsigned int TableIndex
, /* Index to the Id table */
2906 SK_U32 NetIndex
) /* NetIndex (0..n), in single net mode always zero */
2909 unsigned int LogPortMax
;
2910 unsigned int PhysPortMax
;
2911 unsigned int LogPortIndex
;
2912 unsigned int PhysPortIndex
;
2914 unsigned int Offset
= 0;
2917 * Calculate instance if wished. MAC index 0 is the virtual
2920 PhysPortMax
= pAC
->GIni
.GIMacsFound
;
2921 LogPortMax
= SK_PNMI_PORT_PHYS2LOG(PhysPortMax
);
2923 if (pAC
->Pnmi
.DualNetActiveFlag
== SK_TRUE
) { /* Dual net mode */
2927 if ((Instance
!= (SK_U32
)(-1))) { /* Only one specific instance is queried */
2928 /* Check instance range */
2929 if ((Instance
< 1) || (Instance
> LogPortMax
)) {
2932 return (SK_PNMI_ERR_UNKNOWN_INST
);
2934 LogPortIndex
= SK_PNMI_PORT_INST2LOG(Instance
);
2935 Limit
= LogPortIndex
+ 1;
2937 else { /* Instance == (SK_U32)(-1), get all Instances of that OID */
2946 if (Action
== SK_PNMI_GET
) {
2949 if (*pLen
< (Limit
- LogPortIndex
) * 6) {
2951 *pLen
= (Limit
- LogPortIndex
) * 6;
2952 return (SK_PNMI_ERR_TOO_SHORT
);
2958 for (; LogPortIndex
< Limit
; LogPortIndex
++) {
2962 case OID_SKGE_PHYS_CUR_ADDR
:
2963 if (LogPortIndex
== 0) {
2964 CopyMac(pBuf
+ Offset
, &pAC
->Addr
.Net
[NetIndex
].CurrentMacAddress
);
2967 PhysPortIndex
= SK_PNMI_PORT_LOG2PHYS(pAC
, LogPortIndex
);
2969 CopyMac(pBuf
+ Offset
,
2970 &pAC
->Addr
.Port
[PhysPortIndex
].CurrentMacAddress
);
2975 case OID_SKGE_PHYS_FAC_ADDR
:
2976 if (LogPortIndex
== 0) {
2977 CopyMac(pBuf
+ Offset
,
2978 &pAC
->Addr
.Net
[NetIndex
].PermanentMacAddress
);
2981 PhysPortIndex
= SK_PNMI_PORT_LOG2PHYS(
2984 CopyMac(pBuf
+ Offset
,
2985 &pAC
->Addr
.Port
[PhysPortIndex
].PermanentMacAddress
);
2991 SK_ERR_LOG(pAC
, SK_ERRCL_SW
, SK_PNMI_ERR008
,
2995 return (SK_PNMI_ERR_GENERAL
);
3003 * The logical MAC address may not be changed only
3006 if (Id
== OID_SKGE_PHYS_FAC_ADDR
) {
3009 return (SK_PNMI_ERR_READ_ONLY
);
3013 * Only the current address may be changed
3015 if (Id
!= OID_SKGE_PHYS_CUR_ADDR
) {
3017 SK_ERR_LOG(pAC
, SK_ERRCL_SW
, SK_PNMI_ERR009
,
3021 return (SK_PNMI_ERR_GENERAL
);
3025 if (*pLen
< (Limit
- LogPortIndex
) * 6) {
3027 *pLen
= (Limit
- LogPortIndex
) * 6;
3028 return (SK_PNMI_ERR_TOO_SHORT
);
3030 if (*pLen
> (Limit
- LogPortIndex
) * 6) {
3033 return (SK_PNMI_ERR_BAD_VALUE
);
3039 if (Action
== SK_PNMI_PRESET
) {
3042 return (SK_PNMI_ERR_OK
);
3046 * Set OID_SKGE_MAC_CUR_ADDR
3048 for (; LogPortIndex
< Limit
; LogPortIndex
++, Offset
+= 6) {
3051 * A set to virtual port and set of broadcast
3052 * address will be ignored
3054 if (LogPortIndex
== 0 || SK_MEMCMP(pBuf
+ Offset
,
3055 "\xff\xff\xff\xff\xff\xff", 6) == 0) {
3060 PhysPortIndex
= SK_PNMI_PORT_LOG2PHYS(pAC
,
3063 Ret
= SkAddrOverride(pAC
, IoC
, PhysPortIndex
,
3064 (SK_MAC_ADDR
*)(pBuf
+ Offset
),
3065 (LogPortIndex
== 0 ? SK_ADDR_VIRTUAL_ADDRESS
:
3066 SK_ADDR_PHYSICAL_ADDRESS
));
3067 if (Ret
!= SK_ADDR_OVERRIDE_SUCCESS
) {
3069 return (SK_PNMI_ERR_GENERAL
);
3075 return (SK_PNMI_ERR_OK
);
3078 /*****************************************************************************
3080 * CsumStat - OID handler function of OID_SKGE_CHKSM_XXX
3083 * Retrieves the statistic values of the CSUM module. The CSUM data
3084 * structure must be available in the SK_AC even if the CSUM module
3085 * is not included, because PNMI reads the statistic data from the
3086 * CSUM part of SK_AC directly.
3089 * SK_PNMI_ERR_OK The request was successfully performed.
3090 * SK_PNMI_ERR_GENERAL A general severe internal error occured.
3091 * SK_PNMI_ERR_TOO_SHORT The passed buffer is too short to contain
3092 * the correct data (e.g. a 32bit value is
3093 * needed, but a 16 bit value was passed).
3094 * SK_PNMI_ERR_UNKNOWN_INST The requested instance of the OID doesn't
3095 * exist (e.g. port instance 3 on a two port
3098 PNMI_STATIC
int CsumStat(
3099 SK_AC
*pAC
, /* Pointer to adapter context */
3100 SK_IOC IoC
, /* IO context handle */
3101 int Action
, /* GET/PRESET/SET action */
3102 SK_U32 Id
, /* Object ID that is to be processed */
3103 char *pBuf
, /* Buffer used for the management data transfer */
3104 unsigned int *pLen
, /* On call: pBuf buffer length. On return: used buffer */
3105 SK_U32 Instance
, /* Instance (1..n) that is to be queried or -1 */
3106 unsigned int TableIndex
, /* Index to the Id table */
3107 SK_U32 NetIndex
) /* NetIndex (0..n), in single net mode always zero */
3111 unsigned int Offset
= 0;
3116 * Calculate instance if wished
3118 if (Instance
!= (SK_U32
)(-1)) {
3120 if ((Instance
< 1) || (Instance
> SKCS_NUM_PROTOCOLS
)) {
3123 return (SK_PNMI_ERR_UNKNOWN_INST
);
3125 Index
= (unsigned int)Instance
- 1;
3130 Limit
= SKCS_NUM_PROTOCOLS
;
3136 if (Action
!= SK_PNMI_GET
) {
3139 return (SK_PNMI_ERR_READ_ONLY
);
3143 if (*pLen
< (Limit
- Index
) * sizeof(SK_U64
)) {
3145 *pLen
= (Limit
- Index
) * sizeof(SK_U64
);
3146 return (SK_PNMI_ERR_TOO_SHORT
);
3152 for (; Index
< Limit
; Index
++) {
3156 case OID_SKGE_CHKSM_RX_OK_CTS
:
3157 StatVal
= pAC
->Csum
.ProtoStats
[NetIndex
][Index
].RxOkCts
;
3160 case OID_SKGE_CHKSM_RX_UNABLE_CTS
:
3161 StatVal
= pAC
->Csum
.ProtoStats
[NetIndex
][Index
].RxUnableCts
;
3164 case OID_SKGE_CHKSM_RX_ERR_CTS
:
3165 StatVal
= pAC
->Csum
.ProtoStats
[NetIndex
][Index
].RxErrCts
;
3168 case OID_SKGE_CHKSM_TX_OK_CTS
:
3169 StatVal
= pAC
->Csum
.ProtoStats
[NetIndex
][Index
].TxOkCts
;
3172 case OID_SKGE_CHKSM_TX_UNABLE_CTS
:
3173 StatVal
= pAC
->Csum
.ProtoStats
[NetIndex
][Index
].TxUnableCts
;
3177 SK_ERR_LOG(pAC
, SK_ERRCL_SW
, SK_PNMI_ERR010
,
3181 return (SK_PNMI_ERR_GENERAL
);
3184 SK_PNMI_STORE_U64(pBuf
+ Offset
, StatVal
);
3185 Offset
+= sizeof(SK_U64
);
3189 * Store used buffer space
3193 return (SK_PNMI_ERR_OK
);
3196 /*****************************************************************************
3198 * SensorStat - OID handler function of OID_SKGE_SENSOR_XXX
3201 * Retrieves the statistic values of the I2C module, which handles
3202 * the temperature and voltage sensors.
3205 * SK_PNMI_ERR_OK The request was successfully performed.
3206 * SK_PNMI_ERR_GENERAL A general severe internal error occured.
3207 * SK_PNMI_ERR_TOO_SHORT The passed buffer is too short to contain
3208 * the correct data (e.g. a 32bit value is
3209 * needed, but a 16 bit value was passed).
3210 * SK_PNMI_ERR_UNKNOWN_INST The requested instance of the OID doesn't
3211 * exist (e.g. port instance 3 on a two port
3214 PNMI_STATIC
int SensorStat(
3215 SK_AC
*pAC
, /* Pointer to adapter context */
3216 SK_IOC IoC
, /* IO context handle */
3217 int Action
, /* GET/PRESET/SET action */
3218 SK_U32 Id
, /* Object ID that is to be processed */
3219 char *pBuf
, /* Buffer used for the management data transfer */
3220 unsigned int *pLen
, /* On call: pBuf buffer length. On return: used buffer */
3221 SK_U32 Instance
, /* Instance (1..n) that is to be queried or -1 */
3222 unsigned int TableIndex
, /* Index to the Id table */
3223 SK_U32 NetIndex
) /* NetIndex (0..n), in single net mode always zero */
3228 unsigned int Offset
;
3235 * Calculate instance if wished
3237 if ((Instance
!= (SK_U32
)(-1))) {
3239 if ((Instance
< 1) || (Instance
> (SK_U32
)pAC
->I2c
.MaxSens
)) {
3242 return (SK_PNMI_ERR_UNKNOWN_INST
);
3245 Index
= (unsigned int)Instance
-1;
3246 Limit
= (unsigned int)Instance
;
3250 Limit
= (unsigned int) pAC
->I2c
.MaxSens
;
3256 if (Action
!= SK_PNMI_GET
) {
3259 return (SK_PNMI_ERR_READ_ONLY
);
3265 case OID_SKGE_SENSOR_VALUE
:
3266 case OID_SKGE_SENSOR_WAR_THRES_LOW
:
3267 case OID_SKGE_SENSOR_WAR_THRES_UPP
:
3268 case OID_SKGE_SENSOR_ERR_THRES_LOW
:
3269 case OID_SKGE_SENSOR_ERR_THRES_UPP
:
3270 if (*pLen
< (Limit
- Index
) * sizeof(SK_U32
)) {
3272 *pLen
= (Limit
- Index
) * sizeof(SK_U32
);
3273 return (SK_PNMI_ERR_TOO_SHORT
);
3277 case OID_SKGE_SENSOR_DESCR
:
3278 for (Offset
= 0, i
= Index
; i
< Limit
; i
++) {
3280 Len
= (unsigned int)
3281 SK_STRLEN(pAC
->I2c
.SenTable
[i
].SenDesc
) + 1;
3282 if (Len
>= SK_PNMI_STRINGLEN2
) {
3284 SK_ERR_LOG(pAC
, SK_ERRCL_SW
, SK_PNMI_ERR011
,
3288 return (SK_PNMI_ERR_GENERAL
);
3292 if (*pLen
< Offset
) {
3295 return (SK_PNMI_ERR_TOO_SHORT
);
3299 case OID_SKGE_SENSOR_INDEX
:
3300 case OID_SKGE_SENSOR_TYPE
:
3301 case OID_SKGE_SENSOR_STATUS
:
3302 if (*pLen
< Limit
- Index
) {
3304 *pLen
= Limit
- Index
;
3305 return (SK_PNMI_ERR_TOO_SHORT
);
3309 case OID_SKGE_SENSOR_WAR_CTS
:
3310 case OID_SKGE_SENSOR_WAR_TIME
:
3311 case OID_SKGE_SENSOR_ERR_CTS
:
3312 case OID_SKGE_SENSOR_ERR_TIME
:
3313 if (*pLen
< (Limit
- Index
) * sizeof(SK_U64
)) {
3315 *pLen
= (Limit
- Index
) * sizeof(SK_U64
);
3316 return (SK_PNMI_ERR_TOO_SHORT
);
3321 SK_ERR_LOG(pAC
, SK_ERRCL_SW
, SK_PNMI_ERR012
,
3325 return (SK_PNMI_ERR_GENERAL
);
3332 for (Offset
= 0; Index
< Limit
; Index
++) {
3336 case OID_SKGE_SENSOR_INDEX
:
3337 *(pBuf
+ Offset
) = (char)Index
;
3338 Offset
+= sizeof(char);
3341 case OID_SKGE_SENSOR_DESCR
:
3342 Len
= SK_STRLEN(pAC
->I2c
.SenTable
[Index
].SenDesc
);
3343 SK_MEMCPY(pBuf
+ Offset
+ 1,
3344 pAC
->I2c
.SenTable
[Index
].SenDesc
, Len
);
3345 *(pBuf
+ Offset
) = (char)Len
;
3349 case OID_SKGE_SENSOR_TYPE
:
3351 (char)pAC
->I2c
.SenTable
[Index
].SenType
;
3352 Offset
+= sizeof(char);
3355 case OID_SKGE_SENSOR_VALUE
:
3356 Val32
= (SK_U32
)pAC
->I2c
.SenTable
[Index
].SenValue
;
3357 SK_PNMI_STORE_U32(pBuf
+ Offset
, Val32
);
3358 Offset
+= sizeof(SK_U32
);
3361 case OID_SKGE_SENSOR_WAR_THRES_LOW
:
3362 Val32
= (SK_U32
)pAC
->I2c
.SenTable
[Index
].
3364 SK_PNMI_STORE_U32(pBuf
+ Offset
, Val32
);
3365 Offset
+= sizeof(SK_U32
);
3368 case OID_SKGE_SENSOR_WAR_THRES_UPP
:
3369 Val32
= (SK_U32
)pAC
->I2c
.SenTable
[Index
].
3371 SK_PNMI_STORE_U32(pBuf
+ Offset
, Val32
);
3372 Offset
+= sizeof(SK_U32
);
3375 case OID_SKGE_SENSOR_ERR_THRES_LOW
:
3376 Val32
= (SK_U32
)pAC
->I2c
.SenTable
[Index
].
3378 SK_PNMI_STORE_U32(pBuf
+ Offset
, Val32
);
3379 Offset
+= sizeof(SK_U32
);
3382 case OID_SKGE_SENSOR_ERR_THRES_UPP
:
3383 Val32
= pAC
->I2c
.SenTable
[Index
].SenThreErrHigh
;
3384 SK_PNMI_STORE_U32(pBuf
+ Offset
, Val32
);
3385 Offset
+= sizeof(SK_U32
);
3388 case OID_SKGE_SENSOR_STATUS
:
3390 (char)pAC
->I2c
.SenTable
[Index
].SenErrFlag
;
3391 Offset
+= sizeof(char);
3394 case OID_SKGE_SENSOR_WAR_CTS
:
3395 Val64
= pAC
->I2c
.SenTable
[Index
].SenWarnCts
;
3396 SK_PNMI_STORE_U64(pBuf
+ Offset
, Val64
);
3397 Offset
+= sizeof(SK_U64
);
3400 case OID_SKGE_SENSOR_ERR_CTS
:
3401 Val64
= pAC
->I2c
.SenTable
[Index
].SenErrCts
;
3402 SK_PNMI_STORE_U64(pBuf
+ Offset
, Val64
);
3403 Offset
+= sizeof(SK_U64
);
3406 case OID_SKGE_SENSOR_WAR_TIME
:
3407 Val64
= SK_PNMI_HUNDREDS_SEC(pAC
->I2c
.SenTable
[Index
].
3409 SK_PNMI_STORE_U64(pBuf
+ Offset
, Val64
);
3410 Offset
+= sizeof(SK_U64
);
3413 case OID_SKGE_SENSOR_ERR_TIME
:
3414 Val64
= SK_PNMI_HUNDREDS_SEC(pAC
->I2c
.SenTable
[Index
].
3416 SK_PNMI_STORE_U64(pBuf
+ Offset
, Val64
);
3417 Offset
+= sizeof(SK_U64
);
3421 SK_DBG_MSG(pAC
, SK_DBGMOD_PNMI
, SK_DBGCAT_ERR
,
3422 ("SensorStat: Unknown OID should be handled before"));
3424 return (SK_PNMI_ERR_GENERAL
);
3429 * Store used buffer space
3433 return (SK_PNMI_ERR_OK
);
3436 /*****************************************************************************
3438 * Vpd - OID handler function of OID_SKGE_VPD_XXX
3441 * Get/preset/set of VPD data. As instance the name of a VPD key
3442 * can be passed. The Instance parameter is a SK_U32 and can be
3443 * used as a string buffer for the VPD key, because their maximum
3447 * SK_PNMI_ERR_OK The request was successfully performed.
3448 * SK_PNMI_ERR_GENERAL A general severe internal error occured.
3449 * SK_PNMI_ERR_TOO_SHORT The passed buffer is too short to contain
3450 * the correct data (e.g. a 32bit value is
3451 * needed, but a 16 bit value was passed).
3452 * SK_PNMI_ERR_BAD_VALUE The passed value is not in the valid
3454 * SK_PNMI_ERR_READ_ONLY The OID is read-only and cannot be set.
3455 * SK_PNMI_ERR_UNKNOWN_INST The requested instance of the OID doesn't
3456 * exist (e.g. port instance 3 on a two port
3459 PNMI_STATIC
int Vpd(
3460 SK_AC
*pAC
, /* Pointer to adapter context */
3461 SK_IOC IoC
, /* IO context handle */
3462 int Action
, /* GET/PRESET/SET action */
3463 SK_U32 Id
, /* Object ID that is to be processed */
3464 char *pBuf
, /* Buffer used for the management data transfer */
3465 unsigned int *pLen
, /* On call: pBuf buffer length. On return: used buffer */
3466 SK_U32 Instance
, /* Instance (1..n) that is to be queried or -1 */
3467 unsigned int TableIndex
, /* Index to the Id table */
3468 SK_U32 NetIndex
) /* NetIndex (0..n), in single net mode always zero */
3470 SK_VPD_STATUS
*pVpdStatus
;
3471 unsigned int BufLen
;
3473 char KeyArr
[SK_PNMI_VPD_ENTRIES
][SK_PNMI_VPD_KEY_SIZE
];
3474 char KeyStr
[SK_PNMI_VPD_KEY_SIZE
];
3476 unsigned int Offset
;
3478 unsigned int FirstIndex
;
3479 unsigned int LastIndex
;
3485 * Get array of all currently stored VPD keys
3487 Ret
= GetVpdKeyArr(pAC
, IoC
, &KeyArr
[0][0], sizeof(KeyArr
), &KeyNo
);
3488 if (Ret
!= SK_PNMI_ERR_OK
) {
3494 * If instance is not -1, try to find the requested VPD key for
3495 * the multiple instance variables. The other OIDs as for example
3496 * OID VPD_ACTION are single instance variables and must be
3497 * handled separatly.
3502 if ((Instance
!= (SK_U32
)(-1))) {
3504 if (Id
== OID_SKGE_VPD_KEY
|| Id
== OID_SKGE_VPD_VALUE
||
3505 Id
== OID_SKGE_VPD_ACCESS
) {
3507 SK_STRNCPY(KeyStr
, (char *)&Instance
, 4);
3510 for (Index
= 0; Index
< KeyNo
; Index
++) {
3512 if (SK_STRCMP(KeyStr
, KeyArr
[Index
]) == 0) {
3514 LastIndex
= Index
+1;
3518 if (Index
== KeyNo
) {
3521 return (SK_PNMI_ERR_UNKNOWN_INST
);
3524 else if (Instance
!= 1) {
3527 return (SK_PNMI_ERR_UNKNOWN_INST
);
3532 * Get value, if a query should be performed
3534 if (Action
== SK_PNMI_GET
) {
3538 case OID_SKGE_VPD_FREE_BYTES
:
3539 /* Check length of buffer */
3540 if (*pLen
< sizeof(SK_U32
)) {
3542 *pLen
= sizeof(SK_U32
);
3543 return (SK_PNMI_ERR_TOO_SHORT
);
3545 /* Get number of free bytes */
3546 pVpdStatus
= VpdStat(pAC
, IoC
);
3547 if (pVpdStatus
== NULL
) {
3549 SK_ERR_LOG(pAC
, SK_ERRCL_SW
, SK_PNMI_ERR017
,
3553 return (SK_PNMI_ERR_GENERAL
);
3555 if ((pVpdStatus
->vpd_status
& VPD_VALID
) == 0) {
3557 SK_ERR_LOG(pAC
, SK_ERRCL_SW
, SK_PNMI_ERR018
,
3561 return (SK_PNMI_ERR_GENERAL
);
3564 Val32
= (SK_U32
)pVpdStatus
->vpd_free_rw
;
3565 SK_PNMI_STORE_U32(pBuf
, Val32
);
3566 *pLen
= sizeof(SK_U32
);
3569 case OID_SKGE_VPD_ENTRIES_LIST
:
3571 for (Len
= 0, Index
= 0; Index
< KeyNo
; Index
++) {
3573 Len
+= SK_STRLEN(KeyArr
[Index
]) + 1;
3578 return (SK_PNMI_ERR_TOO_SHORT
);
3582 *(pBuf
) = (char)Len
- 1;
3583 for (Offset
= 1, Index
= 0; Index
< KeyNo
; Index
++) {
3585 Len
= SK_STRLEN(KeyArr
[Index
]);
3586 SK_MEMCPY(pBuf
+ Offset
, KeyArr
[Index
], Len
);
3590 if (Index
< KeyNo
- 1) {
3592 *(pBuf
+ Offset
) = ' ';
3599 case OID_SKGE_VPD_ENTRIES_NUMBER
:
3601 if (*pLen
< sizeof(SK_U32
)) {
3603 *pLen
= sizeof(SK_U32
);
3604 return (SK_PNMI_ERR_TOO_SHORT
);
3607 Val32
= (SK_U32
)KeyNo
;
3608 SK_PNMI_STORE_U32(pBuf
, Val32
);
3609 *pLen
= sizeof(SK_U32
);
3612 case OID_SKGE_VPD_KEY
:
3613 /* Check buffer length, if it is large enough */
3614 for (Len
= 0, Index
= FirstIndex
;
3615 Index
< LastIndex
; Index
++) {
3617 Len
+= SK_STRLEN(KeyArr
[Index
]) + 1;
3622 return (SK_PNMI_ERR_TOO_SHORT
);
3626 * Get the key to an intermediate buffer, because
3627 * we have to prepend a length byte.
3629 for (Offset
= 0, Index
= FirstIndex
;
3630 Index
< LastIndex
; Index
++) {
3632 Len
= SK_STRLEN(KeyArr
[Index
]);
3634 *(pBuf
+ Offset
) = (char)Len
;
3635 SK_MEMCPY(pBuf
+ Offset
+ 1, KeyArr
[Index
],
3642 case OID_SKGE_VPD_VALUE
:
3643 /* Check the buffer length if it is large enough */
3644 for (Offset
= 0, Index
= FirstIndex
;
3645 Index
< LastIndex
; Index
++) {
3648 if (VpdRead(pAC
, IoC
, KeyArr
[Index
], Buf
,
3649 (int *)&BufLen
) > 0 ||
3650 BufLen
>= SK_PNMI_VPD_DATALEN
) {
3652 SK_ERR_LOG(pAC
, SK_ERRCL_SW
,
3656 return (SK_PNMI_ERR_GENERAL
);
3658 Offset
+= BufLen
+ 1;
3660 if (*pLen
< Offset
) {
3663 return (SK_PNMI_ERR_TOO_SHORT
);
3667 * Get the value to an intermediate buffer, because
3668 * we have to prepend a length byte.
3670 for (Offset
= 0, Index
= FirstIndex
;
3671 Index
< LastIndex
; Index
++) {
3674 if (VpdRead(pAC
, IoC
, KeyArr
[Index
], Buf
,
3675 (int *)&BufLen
) > 0 ||
3676 BufLen
>= SK_PNMI_VPD_DATALEN
) {
3678 SK_ERR_LOG(pAC
, SK_ERRCL_SW
,
3683 return (SK_PNMI_ERR_GENERAL
);
3686 *(pBuf
+ Offset
) = (char)BufLen
;
3687 SK_MEMCPY(pBuf
+ Offset
+ 1, Buf
, BufLen
);
3688 Offset
+= BufLen
+ 1;
3693 case OID_SKGE_VPD_ACCESS
:
3694 if (*pLen
< LastIndex
- FirstIndex
) {
3696 *pLen
= LastIndex
- FirstIndex
;
3697 return (SK_PNMI_ERR_TOO_SHORT
);
3700 for (Offset
= 0, Index
= FirstIndex
;
3701 Index
< LastIndex
; Index
++) {
3703 if (VpdMayWrite(KeyArr
[Index
])) {
3705 *(pBuf
+ Offset
) = SK_PNMI_VPD_RW
;
3708 *(pBuf
+ Offset
) = SK_PNMI_VPD_RO
;
3715 case OID_SKGE_VPD_ACTION
:
3716 Offset
= LastIndex
- FirstIndex
;
3717 if (*pLen
< Offset
) {
3720 return (SK_PNMI_ERR_TOO_SHORT
);
3722 SK_MEMSET(pBuf
, 0, Offset
);
3727 SK_ERR_LOG(pAC
, SK_ERRCL_SW
, SK_PNMI_ERR023
,
3731 return (SK_PNMI_ERR_GENERAL
);
3735 /* The only OID which can be set is VPD_ACTION */
3736 if (Id
!= OID_SKGE_VPD_ACTION
) {
3738 if (Id
== OID_SKGE_VPD_FREE_BYTES
||
3739 Id
== OID_SKGE_VPD_ENTRIES_LIST
||
3740 Id
== OID_SKGE_VPD_ENTRIES_NUMBER
||
3741 Id
== OID_SKGE_VPD_KEY
||
3742 Id
== OID_SKGE_VPD_VALUE
||
3743 Id
== OID_SKGE_VPD_ACCESS
) {
3746 return (SK_PNMI_ERR_READ_ONLY
);
3749 SK_ERR_LOG(pAC
, SK_ERRCL_SW
, SK_PNMI_ERR024
,
3753 return (SK_PNMI_ERR_GENERAL
);
3757 * From this point we handle VPD_ACTION. Check the buffer
3758 * length. It should at least have the size of one byte.
3763 return (SK_PNMI_ERR_TOO_SHORT
);
3767 * The first byte contains the VPD action type we should
3772 case SK_PNMI_VPD_IGNORE
:
3776 case SK_PNMI_VPD_CREATE
:
3778 * We have to create a new VPD entry or we modify
3779 * an existing one. Check first the buffer length.
3784 return (SK_PNMI_ERR_TOO_SHORT
);
3786 KeyStr
[0] = pBuf
[1];
3787 KeyStr
[1] = pBuf
[2];
3791 * Is the entry writable or does it belong to the
3794 if (!VpdMayWrite(KeyStr
)) {
3797 return (SK_PNMI_ERR_BAD_VALUE
);
3800 Offset
= (int)pBuf
[3] & 0xFF;
3802 SK_MEMCPY(Buf
, pBuf
+ 4, Offset
);
3805 /* A preset ends here */
3806 if (Action
== SK_PNMI_PRESET
) {
3808 return (SK_PNMI_ERR_OK
);
3811 /* Write the new entry or modify an existing one */
3812 Ret
= VpdWrite(pAC
, IoC
, KeyStr
, Buf
);
3813 if (Ret
== SK_PNMI_VPD_NOWRITE
) {
3816 return (SK_PNMI_ERR_BAD_VALUE
);
3818 else if (Ret
!= SK_PNMI_VPD_OK
) {
3820 SK_ERR_LOG(pAC
, SK_ERRCL_SW
, SK_PNMI_ERR025
,
3824 return (SK_PNMI_ERR_GENERAL
);
3828 * Perform an update of the VPD data. This is
3829 * not mandantory, but just to be sure.
3831 Ret
= VpdUpdate(pAC
, IoC
);
3832 if (Ret
!= SK_PNMI_VPD_OK
) {
3834 SK_ERR_LOG(pAC
, SK_ERRCL_SW
, SK_PNMI_ERR026
,
3838 return (SK_PNMI_ERR_GENERAL
);
3842 case SK_PNMI_VPD_DELETE
:
3843 /* Check if the buffer size is plausible */
3847 return (SK_PNMI_ERR_TOO_SHORT
);
3852 return (SK_PNMI_ERR_BAD_VALUE
);
3854 KeyStr
[0] = pBuf
[1];
3855 KeyStr
[1] = pBuf
[2];
3858 /* Find the passed key in the array */
3859 for (Index
= 0; Index
< KeyNo
; Index
++) {
3861 if (SK_STRCMP(KeyStr
, KeyArr
[Index
]) == 0) {
3867 * If we cannot find the key it is wrong, so we
3868 * return an appropriate error value.
3870 if (Index
== KeyNo
) {
3873 return (SK_PNMI_ERR_BAD_VALUE
);
3876 if (Action
== SK_PNMI_PRESET
) {
3878 return (SK_PNMI_ERR_OK
);
3881 /* Ok, you wanted it and you will get it */
3882 Ret
= VpdDelete(pAC
, IoC
, KeyStr
);
3883 if (Ret
!= SK_PNMI_VPD_OK
) {
3885 SK_ERR_LOG(pAC
, SK_ERRCL_SW
, SK_PNMI_ERR027
,
3889 return (SK_PNMI_ERR_GENERAL
);
3893 * Perform an update of the VPD data. This is
3894 * not mandantory, but just to be sure.
3896 Ret
= VpdUpdate(pAC
, IoC
);
3897 if (Ret
!= SK_PNMI_VPD_OK
) {
3899 SK_ERR_LOG(pAC
, SK_ERRCL_SW
, SK_PNMI_ERR028
,
3903 return (SK_PNMI_ERR_GENERAL
);
3909 return (SK_PNMI_ERR_BAD_VALUE
);
3913 return (SK_PNMI_ERR_OK
);
3916 /*****************************************************************************
3918 * General - OID handler function of various single instance OIDs
3921 * The code is simple. No description necessary.
3924 * SK_PNMI_ERR_OK The request was successfully performed.
3925 * SK_PNMI_ERR_GENERAL A general severe internal error occured.
3926 * SK_PNMI_ERR_TOO_SHORT The passed buffer is too short to contain
3927 * the correct data (e.g. a 32bit value is
3928 * needed, but a 16 bit value was passed).
3929 * SK_PNMI_ERR_UNKNOWN_INST The requested instance of the OID doesn't
3930 * exist (e.g. port instance 3 on a two port
3933 PNMI_STATIC
int General(
3934 SK_AC
*pAC
, /* Pointer to adapter context */
3935 SK_IOC IoC
, /* IO context handle */
3936 int Action
, /* GET/PRESET/SET action */
3937 SK_U32 Id
, /* Object ID that is to be processed */
3938 char *pBuf
, /* Buffer used for the management data transfer */
3939 unsigned int *pLen
, /* On call: buffer length. On return: used buffer */
3940 SK_U32 Instance
, /* Instance (1..n) that is to be queried or -1 */
3941 unsigned int TableIndex
, /* Index to the Id table */
3942 SK_U32 NetIndex
) /* NetIndex (0..n), in single net mode always zero */
3947 unsigned int Offset
;
3953 SK_U64 Val64RxHwErrs
= 0;
3954 SK_U64 Val64TxHwErrs
= 0;
3955 SK_BOOL Is64BitReq
= SK_FALSE
;
3960 * Check instance. We only handle single instance variables.
3962 if (Instance
!= (SK_U32
)(-1) && Instance
!= 1) {
3965 return (SK_PNMI_ERR_UNKNOWN_INST
);
3969 * Check action. We only allow get requests.
3971 if (Action
!= SK_PNMI_GET
) {
3974 return (SK_PNMI_ERR_READ_ONLY
);
3977 MacType
= pAC
->GIni
.GIMacType
;
3980 * Check length for the various supported OIDs
3984 case OID_GEN_XMIT_ERROR
:
3985 case OID_GEN_RCV_ERROR
:
3986 case OID_GEN_RCV_NO_BUFFER
:
3987 #ifndef SK_NDIS_64BIT_CTR
3988 if (*pLen
< sizeof(SK_U32
)) {
3989 *pLen
= sizeof(SK_U32
);
3990 return (SK_PNMI_ERR_TOO_SHORT
);
3993 #else /* SK_NDIS_64BIT_CTR */
3996 * for compatibility, at least 32bit are required for oid
3998 if (*pLen
< sizeof(SK_U32
)) {
4000 * but indicate handling for 64bit values,
4001 * if insufficient space is provided
4003 *pLen
= sizeof(SK_U64
);
4004 return (SK_PNMI_ERR_TOO_SHORT
);
4007 Is64BitReq
= (*pLen
< sizeof(SK_U64
)) ? SK_FALSE
: SK_TRUE
;
4008 #endif /* SK_NDIS_64BIT_CTR */
4011 case OID_SKGE_BOARDLEVEL
:
4012 if (*pLen
< sizeof(SK_U32
)) {
4014 *pLen
= sizeof(SK_U32
);
4015 return (SK_PNMI_ERR_TOO_SHORT
);
4019 case OID_SKGE_PORT_NUMBER
:
4020 case OID_SKGE_DEVICE_TYPE
:
4021 case OID_SKGE_RESULT
:
4022 case OID_SKGE_RLMT_MONITOR_NUMBER
:
4023 case OID_GEN_TRANSMIT_QUEUE_LENGTH
:
4024 case OID_SKGE_TRAP_NUMBER
:
4025 case OID_SKGE_MDB_VERSION
:
4026 if (*pLen
< sizeof(SK_U32
)) {
4028 *pLen
= sizeof(SK_U32
);
4029 return (SK_PNMI_ERR_TOO_SHORT
);
4033 case OID_SKGE_CHIPSET
:
4034 if (*pLen
< sizeof(SK_U16
)) {
4036 *pLen
= sizeof(SK_U16
);
4037 return (SK_PNMI_ERR_TOO_SHORT
);
4041 case OID_SKGE_BUS_TYPE
:
4042 case OID_SKGE_BUS_SPEED
:
4043 case OID_SKGE_BUS_WIDTH
:
4044 case OID_SKGE_SENSOR_NUMBER
:
4045 case OID_SKGE_CHKSM_NUMBER
:
4046 if (*pLen
< sizeof(SK_U8
)) {
4048 *pLen
= sizeof(SK_U8
);
4049 return (SK_PNMI_ERR_TOO_SHORT
);
4053 case OID_SKGE_TX_SW_QUEUE_LEN
:
4054 case OID_SKGE_TX_SW_QUEUE_MAX
:
4055 case OID_SKGE_TX_RETRY
:
4056 case OID_SKGE_RX_INTR_CTS
:
4057 case OID_SKGE_TX_INTR_CTS
:
4058 case OID_SKGE_RX_NO_BUF_CTS
:
4059 case OID_SKGE_TX_NO_BUF_CTS
:
4060 case OID_SKGE_TX_USED_DESCR_NO
:
4061 case OID_SKGE_RX_DELIVERED_CTS
:
4062 case OID_SKGE_RX_OCTETS_DELIV_CTS
:
4063 case OID_SKGE_RX_HW_ERROR_CTS
:
4064 case OID_SKGE_TX_HW_ERROR_CTS
:
4065 case OID_SKGE_IN_ERRORS_CTS
:
4066 case OID_SKGE_OUT_ERROR_CTS
:
4067 case OID_SKGE_ERR_RECOVERY_CTS
:
4068 case OID_SKGE_SYSUPTIME
:
4069 if (*pLen
< sizeof(SK_U64
)) {
4071 *pLen
= sizeof(SK_U64
);
4072 return (SK_PNMI_ERR_TOO_SHORT
);
4081 /* Update statistic */
4082 if (Id
== OID_SKGE_RX_HW_ERROR_CTS
||
4083 Id
== OID_SKGE_TX_HW_ERROR_CTS
||
4084 Id
== OID_SKGE_IN_ERRORS_CTS
||
4085 Id
== OID_SKGE_OUT_ERROR_CTS
||
4086 Id
== OID_GEN_XMIT_ERROR
||
4087 Id
== OID_GEN_RCV_ERROR
) {
4089 /* Force the XMAC to update its statistic counters and
4090 * Increment semaphore to indicate that an update was
4093 Ret
= MacUpdate(pAC
, IoC
, 0, pAC
->GIni
.GIMacsFound
- 1);
4094 if (Ret
!= SK_PNMI_ERR_OK
) {
4099 pAC
->Pnmi
.MacUpdatedFlag
++;
4102 * Some OIDs consist of multiple hardware counters. Those
4103 * values which are contained in all of them will be added
4108 case OID_SKGE_RX_HW_ERROR_CTS
:
4109 case OID_SKGE_IN_ERRORS_CTS
:
4110 case OID_GEN_RCV_ERROR
:
4112 GetStatVal(pAC
, IoC
, 0, SK_PNMI_HRX_MISSED
, NetIndex
) +
4113 GetStatVal(pAC
, IoC
, 0, SK_PNMI_HRX_FRAMING
, NetIndex
) +
4114 GetStatVal(pAC
, IoC
, 0, SK_PNMI_HRX_OVERFLOW
, NetIndex
) +
4115 GetStatVal(pAC
, IoC
, 0, SK_PNMI_HRX_JABBER
, NetIndex
) +
4116 GetStatVal(pAC
, IoC
, 0, SK_PNMI_HRX_CARRIER
, NetIndex
) +
4117 GetStatVal(pAC
, IoC
, 0, SK_PNMI_HRX_IRLENGTH
, NetIndex
) +
4118 GetStatVal(pAC
, IoC
, 0, SK_PNMI_HRX_SYMBOL
, NetIndex
) +
4119 GetStatVal(pAC
, IoC
, 0, SK_PNMI_HRX_SHORTS
, NetIndex
) +
4120 GetStatVal(pAC
, IoC
, 0, SK_PNMI_HRX_RUNT
, NetIndex
) +
4121 GetStatVal(pAC
, IoC
, 0, SK_PNMI_HRX_TOO_LONG
, NetIndex
) +
4122 GetStatVal(pAC
, IoC
, 0, SK_PNMI_HRX_FCS
, NetIndex
) +
4123 GetStatVal(pAC
, IoC
, 0, SK_PNMI_HRX_CEXT
, NetIndex
);
4126 case OID_SKGE_TX_HW_ERROR_CTS
:
4127 case OID_SKGE_OUT_ERROR_CTS
:
4128 case OID_GEN_XMIT_ERROR
:
4130 GetStatVal(pAC
, IoC
, 0, SK_PNMI_HTX_EXCESS_COL
, NetIndex
) +
4131 GetStatVal(pAC
, IoC
, 0, SK_PNMI_HTX_LATE_COL
, NetIndex
) +
4132 GetStatVal(pAC
, IoC
, 0, SK_PNMI_HTX_UNDERRUN
, NetIndex
) +
4133 GetStatVal(pAC
, IoC
, 0, SK_PNMI_HTX_CARRIER
, NetIndex
);
4143 case OID_SKGE_SUPPORTED_LIST
:
4144 Len
= ID_TABLE_SIZE
* sizeof(SK_U32
);
4148 return (SK_PNMI_ERR_TOO_SHORT
);
4150 for (Offset
= 0, Index
= 0; Offset
< Len
;
4151 Offset
+= sizeof(SK_U32
), Index
++) {
4153 Val32
= (SK_U32
)IdTable
[Index
].Id
;
4154 SK_PNMI_STORE_U32(pBuf
+ Offset
, Val32
);
4159 case OID_SKGE_BOARDLEVEL
:
4160 Val32
= (SK_U32
)pAC
->GIni
.GILevel
;
4161 SK_PNMI_STORE_U32(pBuf
, Val32
);
4162 *pLen
= sizeof(SK_U32
);
4165 case OID_SKGE_PORT_NUMBER
:
4166 Val32
= (SK_U32
)pAC
->GIni
.GIMacsFound
;
4167 SK_PNMI_STORE_U32(pBuf
, Val32
);
4168 *pLen
= sizeof(SK_U32
);
4171 case OID_SKGE_DEVICE_TYPE
:
4172 Val32
= (SK_U32
)pAC
->Pnmi
.DeviceType
;
4173 SK_PNMI_STORE_U32(pBuf
, Val32
);
4174 *pLen
= sizeof(SK_U32
);
4177 case OID_SKGE_DRIVER_DESCR
:
4178 if (pAC
->Pnmi
.pDriverDescription
== NULL
) {
4180 SK_ERR_LOG(pAC
, SK_ERRCL_SW
, SK_PNMI_ERR007
,
4184 return (SK_PNMI_ERR_GENERAL
);
4187 Len
= SK_STRLEN(pAC
->Pnmi
.pDriverDescription
) + 1;
4188 if (Len
> SK_PNMI_STRINGLEN1
) {
4190 SK_ERR_LOG(pAC
, SK_ERRCL_SW
, SK_PNMI_ERR029
,
4194 return (SK_PNMI_ERR_GENERAL
);
4200 return (SK_PNMI_ERR_TOO_SHORT
);
4202 *pBuf
= (char)(Len
- 1);
4203 SK_MEMCPY(pBuf
+ 1, pAC
->Pnmi
.pDriverDescription
, Len
- 1);
4207 case OID_SKGE_DRIVER_VERSION
:
4208 if (pAC
->Pnmi
.pDriverVersion
== NULL
) {
4210 SK_ERR_LOG(pAC
, SK_ERRCL_SW
, SK_PNMI_ERR030
,
4214 return (SK_PNMI_ERR_GENERAL
);
4217 Len
= SK_STRLEN(pAC
->Pnmi
.pDriverVersion
) + 1;
4218 if (Len
> SK_PNMI_STRINGLEN1
) {
4220 SK_ERR_LOG(pAC
, SK_ERRCL_SW
, SK_PNMI_ERR031
,
4224 return (SK_PNMI_ERR_GENERAL
);
4230 return (SK_PNMI_ERR_TOO_SHORT
);
4232 *pBuf
= (char)(Len
- 1);
4233 SK_MEMCPY(pBuf
+ 1, pAC
->Pnmi
.pDriverVersion
, Len
- 1);
4237 case OID_SKGE_HW_DESCR
:
4239 * The hardware description is located in the VPD. This
4240 * query may move to the initialisation routine. But
4241 * the VPD data is cached and therefore a call here
4242 * will not make much difference.
4245 if (VpdRead(pAC
, IoC
, VPD_NAME
, Buf
, (int *)&Len
) > 0) {
4247 SK_ERR_LOG(pAC
, SK_ERRCL_SW
, SK_PNMI_ERR032
,
4251 return (SK_PNMI_ERR_GENERAL
);
4254 if (Len
> SK_PNMI_STRINGLEN1
) {
4256 SK_ERR_LOG(pAC
, SK_ERRCL_SW
, SK_PNMI_ERR033
,
4260 return (SK_PNMI_ERR_GENERAL
);
4265 return (SK_PNMI_ERR_TOO_SHORT
);
4267 *pBuf
= (char)(Len
- 1);
4268 SK_MEMCPY(pBuf
+ 1, Buf
, Len
- 1);
4272 case OID_SKGE_HW_VERSION
:
4273 /* Oh, I love to do some string manipulation */
4277 return (SK_PNMI_ERR_TOO_SHORT
);
4279 Val8
= (SK_U8
)pAC
->GIni
.GIPciHwRev
;
4282 pBuf
[2] = (char)(0x30 | ((Val8
>> 4) & 0x0F));
4284 pBuf
[4] = (char)(0x30 | (Val8
& 0x0F));
4288 case OID_SKGE_CHIPSET
:
4289 Val16
= pAC
->Pnmi
.Chipset
;
4290 SK_PNMI_STORE_U16(pBuf
, Val16
);
4291 *pLen
= sizeof(SK_U16
);
4294 case OID_SKGE_BUS_TYPE
:
4295 *pBuf
= (char)SK_PNMI_BUS_PCI
;
4296 *pLen
= sizeof(char);
4299 case OID_SKGE_BUS_SPEED
:
4300 *pBuf
= pAC
->Pnmi
.PciBusSpeed
;
4301 *pLen
= sizeof(char);
4304 case OID_SKGE_BUS_WIDTH
:
4305 *pBuf
= pAC
->Pnmi
.PciBusWidth
;
4306 *pLen
= sizeof(char);
4309 case OID_SKGE_RESULT
:
4310 Val32
= pAC
->Pnmi
.TestResult
;
4311 SK_PNMI_STORE_U32(pBuf
, Val32
);
4312 *pLen
= sizeof(SK_U32
);
4315 case OID_SKGE_SENSOR_NUMBER
:
4316 *pBuf
= (char)pAC
->I2c
.MaxSens
;
4317 *pLen
= sizeof(char);
4320 case OID_SKGE_CHKSM_NUMBER
:
4321 *pBuf
= SKCS_NUM_PROTOCOLS
;
4322 *pLen
= sizeof(char);
4325 case OID_SKGE_TRAP_NUMBER
:
4326 GetTrapQueueLen(pAC
, &Len
, &Val
);
4327 Val32
= (SK_U32
)Val
;
4328 SK_PNMI_STORE_U32(pBuf
, Val32
);
4329 *pLen
= sizeof(SK_U32
);
4333 GetTrapQueueLen(pAC
, &Len
, &Val
);
4337 return (SK_PNMI_ERR_TOO_SHORT
);
4339 CopyTrapQueue(pAC
, pBuf
);
4343 case OID_SKGE_RLMT_MONITOR_NUMBER
:
4344 /* XXX Not yet implemented by RLMT therefore we return zero elements */
4346 SK_PNMI_STORE_U32(pBuf
, Val32
);
4347 *pLen
= sizeof(SK_U32
);
4350 case OID_SKGE_TX_SW_QUEUE_LEN
:
4351 /* 2002-09-17 pweber: For XMAC, use the frozen SW counters (BufPort) */
4352 if (MacType
== SK_MAC_XMAC
) {
4354 if (pAC
->Pnmi
.DualNetActiveFlag
== SK_TRUE
) {
4355 Val64
= pAC
->Pnmi
.BufPort
[NetIndex
].TxSwQueueLen
;
4357 /* Single net mode */
4359 Val64
= pAC
->Pnmi
.BufPort
[0].TxSwQueueLen
+
4360 pAC
->Pnmi
.BufPort
[1].TxSwQueueLen
;
4365 if (pAC
->Pnmi
.DualNetActiveFlag
== SK_TRUE
) {
4366 Val64
= pAC
->Pnmi
.Port
[NetIndex
].TxSwQueueLen
;
4368 /* Single net mode */
4370 Val64
= pAC
->Pnmi
.Port
[0].TxSwQueueLen
+
4371 pAC
->Pnmi
.Port
[1].TxSwQueueLen
;
4374 SK_PNMI_STORE_U64(pBuf
, Val64
);
4375 *pLen
= sizeof(SK_U64
);
4379 case OID_SKGE_TX_SW_QUEUE_MAX
:
4380 /* 2002-09-17 pweber: For XMAC, use the frozen SW counters (BufPort) */
4381 if (MacType
== SK_MAC_XMAC
) {
4383 if (pAC
->Pnmi
.DualNetActiveFlag
== SK_TRUE
) {
4384 Val64
= pAC
->Pnmi
.BufPort
[NetIndex
].TxSwQueueMax
;
4386 /* Single net mode */
4388 Val64
= pAC
->Pnmi
.BufPort
[0].TxSwQueueMax
+
4389 pAC
->Pnmi
.BufPort
[1].TxSwQueueMax
;
4394 if (pAC
->Pnmi
.DualNetActiveFlag
== SK_TRUE
) {
4395 Val64
= pAC
->Pnmi
.Port
[NetIndex
].TxSwQueueMax
;
4397 /* Single net mode */
4399 Val64
= pAC
->Pnmi
.Port
[0].TxSwQueueMax
+
4400 pAC
->Pnmi
.Port
[1].TxSwQueueMax
;
4403 SK_PNMI_STORE_U64(pBuf
, Val64
);
4404 *pLen
= sizeof(SK_U64
);
4407 case OID_SKGE_TX_RETRY
:
4408 /* 2002-09-17 pweber: For XMAC, use the frozen SW counters (BufPort) */
4409 if (MacType
== SK_MAC_XMAC
) {
4411 if (pAC
->Pnmi
.DualNetActiveFlag
== SK_TRUE
) {
4412 Val64
= pAC
->Pnmi
.BufPort
[NetIndex
].TxRetryCts
;
4414 /* Single net mode */
4416 Val64
= pAC
->Pnmi
.BufPort
[0].TxRetryCts
+
4417 pAC
->Pnmi
.BufPort
[1].TxRetryCts
;
4422 if (pAC
->Pnmi
.DualNetActiveFlag
== SK_TRUE
) {
4423 Val64
= pAC
->Pnmi
.Port
[NetIndex
].TxRetryCts
;
4425 /* Single net mode */
4427 Val64
= pAC
->Pnmi
.Port
[0].TxRetryCts
+
4428 pAC
->Pnmi
.Port
[1].TxRetryCts
;
4431 SK_PNMI_STORE_U64(pBuf
, Val64
);
4432 *pLen
= sizeof(SK_U64
);
4435 case OID_SKGE_RX_INTR_CTS
:
4436 /* 2002-09-17 pweber: For XMAC, use the frozen SW counters (BufPort) */
4437 if (MacType
== SK_MAC_XMAC
) {
4439 if (pAC
->Pnmi
.DualNetActiveFlag
== SK_TRUE
) {
4440 Val64
= pAC
->Pnmi
.BufPort
[NetIndex
].RxIntrCts
;
4442 /* Single net mode */
4444 Val64
= pAC
->Pnmi
.BufPort
[0].RxIntrCts
+
4445 pAC
->Pnmi
.BufPort
[1].RxIntrCts
;
4450 if (pAC
->Pnmi
.DualNetActiveFlag
== SK_TRUE
) {
4451 Val64
= pAC
->Pnmi
.Port
[NetIndex
].RxIntrCts
;
4453 /* Single net mode */
4455 Val64
= pAC
->Pnmi
.Port
[0].RxIntrCts
+
4456 pAC
->Pnmi
.Port
[1].RxIntrCts
;
4459 SK_PNMI_STORE_U64(pBuf
, Val64
);
4460 *pLen
= sizeof(SK_U64
);
4463 case OID_SKGE_TX_INTR_CTS
:
4464 /* 2002-09-17 pweber: For XMAC, use the frozen SW counters (BufPort) */
4465 if (MacType
== SK_MAC_XMAC
) {
4467 if (pAC
->Pnmi
.DualNetActiveFlag
== SK_TRUE
) {
4468 Val64
= pAC
->Pnmi
.BufPort
[NetIndex
].TxIntrCts
;
4470 /* Single net mode */
4472 Val64
= pAC
->Pnmi
.BufPort
[0].TxIntrCts
+
4473 pAC
->Pnmi
.BufPort
[1].TxIntrCts
;
4478 if (pAC
->Pnmi
.DualNetActiveFlag
== SK_TRUE
) {
4479 Val64
= pAC
->Pnmi
.Port
[NetIndex
].TxIntrCts
;
4481 /* Single net mode */
4483 Val64
= pAC
->Pnmi
.Port
[0].TxIntrCts
+
4484 pAC
->Pnmi
.Port
[1].TxIntrCts
;
4487 SK_PNMI_STORE_U64(pBuf
, Val64
);
4488 *pLen
= sizeof(SK_U64
);
4491 case OID_SKGE_RX_NO_BUF_CTS
:
4492 /* 2002-09-17 pweber: For XMAC, use the frozen SW counters (BufPort) */
4493 if (MacType
== SK_MAC_XMAC
) {
4495 if (pAC
->Pnmi
.DualNetActiveFlag
== SK_TRUE
) {
4496 Val64
= pAC
->Pnmi
.BufPort
[NetIndex
].RxNoBufCts
;
4498 /* Single net mode */
4500 Val64
= pAC
->Pnmi
.BufPort
[0].RxNoBufCts
+
4501 pAC
->Pnmi
.BufPort
[1].RxNoBufCts
;
4506 if (pAC
->Pnmi
.DualNetActiveFlag
== SK_TRUE
) {
4507 Val64
= pAC
->Pnmi
.Port
[NetIndex
].RxNoBufCts
;
4509 /* Single net mode */
4511 Val64
= pAC
->Pnmi
.Port
[0].RxNoBufCts
+
4512 pAC
->Pnmi
.Port
[1].RxNoBufCts
;
4515 SK_PNMI_STORE_U64(pBuf
, Val64
);
4516 *pLen
= sizeof(SK_U64
);
4519 case OID_SKGE_TX_NO_BUF_CTS
:
4520 /* 2002-09-17 pweber: For XMAC, use the frozen SW counters (BufPort) */
4521 if (MacType
== SK_MAC_XMAC
) {
4523 if (pAC
->Pnmi
.DualNetActiveFlag
== SK_TRUE
) {
4524 Val64
= pAC
->Pnmi
.BufPort
[NetIndex
].TxNoBufCts
;
4526 /* Single net mode */
4528 Val64
= pAC
->Pnmi
.BufPort
[0].TxNoBufCts
+
4529 pAC
->Pnmi
.BufPort
[1].TxNoBufCts
;
4534 if (pAC
->Pnmi
.DualNetActiveFlag
== SK_TRUE
) {
4535 Val64
= pAC
->Pnmi
.Port
[NetIndex
].TxNoBufCts
;
4537 /* Single net mode */
4539 Val64
= pAC
->Pnmi
.Port
[0].TxNoBufCts
+
4540 pAC
->Pnmi
.Port
[1].TxNoBufCts
;
4543 SK_PNMI_STORE_U64(pBuf
, Val64
);
4544 *pLen
= sizeof(SK_U64
);
4547 case OID_SKGE_TX_USED_DESCR_NO
:
4548 /* 2002-09-17 pweber: For XMAC, use the frozen SW counters (BufPort) */
4549 if (MacType
== SK_MAC_XMAC
) {
4551 if (pAC
->Pnmi
.DualNetActiveFlag
== SK_TRUE
) {
4552 Val64
= pAC
->Pnmi
.BufPort
[NetIndex
].TxUsedDescrNo
;
4554 /* Single net mode */
4556 Val64
= pAC
->Pnmi
.BufPort
[0].TxUsedDescrNo
+
4557 pAC
->Pnmi
.BufPort
[1].TxUsedDescrNo
;
4562 if (pAC
->Pnmi
.DualNetActiveFlag
== SK_TRUE
) {
4563 Val64
= pAC
->Pnmi
.Port
[NetIndex
].TxUsedDescrNo
;
4565 /* Single net mode */
4567 Val64
= pAC
->Pnmi
.Port
[0].TxUsedDescrNo
+
4568 pAC
->Pnmi
.Port
[1].TxUsedDescrNo
;
4571 SK_PNMI_STORE_U64(pBuf
, Val64
);
4572 *pLen
= sizeof(SK_U64
);
4575 case OID_SKGE_RX_DELIVERED_CTS
:
4576 /* 2002-09-17 pweber: For XMAC, use the frozen SW counters (BufPort) */
4577 if (MacType
== SK_MAC_XMAC
) {
4579 if (pAC
->Pnmi
.DualNetActiveFlag
== SK_TRUE
) {
4580 Val64
= pAC
->Pnmi
.BufPort
[NetIndex
].RxDeliveredCts
;
4582 /* Single net mode */
4584 Val64
= pAC
->Pnmi
.BufPort
[0].RxDeliveredCts
+
4585 pAC
->Pnmi
.BufPort
[1].RxDeliveredCts
;
4590 if (pAC
->Pnmi
.DualNetActiveFlag
== SK_TRUE
) {
4591 Val64
= pAC
->Pnmi
.Port
[NetIndex
].RxDeliveredCts
;
4593 /* Single net mode */
4595 Val64
= pAC
->Pnmi
.Port
[0].RxDeliveredCts
+
4596 pAC
->Pnmi
.Port
[1].RxDeliveredCts
;
4599 SK_PNMI_STORE_U64(pBuf
, Val64
);
4600 *pLen
= sizeof(SK_U64
);
4603 case OID_SKGE_RX_OCTETS_DELIV_CTS
:
4604 /* 2002-09-17 pweber: For XMAC, use the frozen SW counters (BufPort) */
4605 if (MacType
== SK_MAC_XMAC
) {
4607 if (pAC
->Pnmi
.DualNetActiveFlag
== SK_TRUE
) {
4608 Val64
= pAC
->Pnmi
.BufPort
[NetIndex
].RxOctetsDeliveredCts
;
4610 /* Single net mode */
4612 Val64
= pAC
->Pnmi
.BufPort
[0].RxOctetsDeliveredCts
+
4613 pAC
->Pnmi
.BufPort
[1].RxOctetsDeliveredCts
;
4618 if (pAC
->Pnmi
.DualNetActiveFlag
== SK_TRUE
) {
4619 Val64
= pAC
->Pnmi
.Port
[NetIndex
].RxOctetsDeliveredCts
;
4621 /* Single net mode */
4623 Val64
= pAC
->Pnmi
.Port
[0].RxOctetsDeliveredCts
+
4624 pAC
->Pnmi
.Port
[1].RxOctetsDeliveredCts
;
4627 SK_PNMI_STORE_U64(pBuf
, Val64
);
4628 *pLen
= sizeof(SK_U64
);
4631 case OID_SKGE_RX_HW_ERROR_CTS
:
4632 SK_PNMI_STORE_U64(pBuf
, Val64RxHwErrs
);
4633 *pLen
= sizeof(SK_U64
);
4636 case OID_SKGE_TX_HW_ERROR_CTS
:
4637 SK_PNMI_STORE_U64(pBuf
, Val64TxHwErrs
);
4638 *pLen
= sizeof(SK_U64
);
4641 case OID_SKGE_IN_ERRORS_CTS
:
4642 /* 2002-09-17 pweber: For XMAC, use the frozen SW counters (BufPort) */
4643 if (MacType
== SK_MAC_XMAC
) {
4645 if (pAC
->Pnmi
.DualNetActiveFlag
== SK_TRUE
) {
4646 Val64
= Val64RxHwErrs
+ pAC
->Pnmi
.BufPort
[NetIndex
].RxNoBufCts
;
4648 /* Single net mode */
4650 Val64
= Val64RxHwErrs
+
4651 pAC
->Pnmi
.BufPort
[0].RxNoBufCts
+
4652 pAC
->Pnmi
.BufPort
[1].RxNoBufCts
;
4657 if (pAC
->Pnmi
.DualNetActiveFlag
== SK_TRUE
) {
4658 Val64
= Val64RxHwErrs
+ pAC
->Pnmi
.Port
[NetIndex
].RxNoBufCts
;
4660 /* Single net mode */
4662 Val64
= Val64RxHwErrs
+
4663 pAC
->Pnmi
.Port
[0].RxNoBufCts
+
4664 pAC
->Pnmi
.Port
[1].RxNoBufCts
;
4667 SK_PNMI_STORE_U64(pBuf
, Val64
);
4668 *pLen
= sizeof(SK_U64
);
4671 case OID_SKGE_OUT_ERROR_CTS
:
4672 /* 2002-09-17 pweber: For XMAC, use the frozen SW counters (BufPort) */
4673 if (MacType
== SK_MAC_XMAC
) {
4675 if (pAC
->Pnmi
.DualNetActiveFlag
== SK_TRUE
) {
4676 Val64
= Val64TxHwErrs
+ pAC
->Pnmi
.BufPort
[NetIndex
].TxNoBufCts
;
4678 /* Single net mode */
4680 Val64
= Val64TxHwErrs
+
4681 pAC
->Pnmi
.BufPort
[0].TxNoBufCts
+
4682 pAC
->Pnmi
.BufPort
[1].TxNoBufCts
;
4687 if (pAC
->Pnmi
.DualNetActiveFlag
== SK_TRUE
) {
4688 Val64
= Val64TxHwErrs
+ pAC
->Pnmi
.Port
[NetIndex
].TxNoBufCts
;
4690 /* Single net mode */
4692 Val64
= Val64TxHwErrs
+
4693 pAC
->Pnmi
.Port
[0].TxNoBufCts
+
4694 pAC
->Pnmi
.Port
[1].TxNoBufCts
;
4697 SK_PNMI_STORE_U64(pBuf
, Val64
);
4698 *pLen
= sizeof(SK_U64
);
4701 case OID_SKGE_ERR_RECOVERY_CTS
:
4702 /* 2002-09-17 pweber: For XMAC, use the frozen SW counters (BufPort) */
4703 if (MacType
== SK_MAC_XMAC
) {
4705 if (pAC
->Pnmi
.DualNetActiveFlag
== SK_TRUE
) {
4706 Val64
= pAC
->Pnmi
.BufPort
[NetIndex
].ErrRecoveryCts
;
4708 /* Single net mode */
4710 Val64
= pAC
->Pnmi
.BufPort
[0].ErrRecoveryCts
+
4711 pAC
->Pnmi
.BufPort
[1].ErrRecoveryCts
;
4716 if (pAC
->Pnmi
.DualNetActiveFlag
== SK_TRUE
) {
4717 Val64
= pAC
->Pnmi
.Port
[NetIndex
].ErrRecoveryCts
;
4719 /* Single net mode */
4721 Val64
= pAC
->Pnmi
.Port
[0].ErrRecoveryCts
+
4722 pAC
->Pnmi
.Port
[1].ErrRecoveryCts
;
4725 SK_PNMI_STORE_U64(pBuf
, Val64
);
4726 *pLen
= sizeof(SK_U64
);
4729 case OID_SKGE_SYSUPTIME
:
4730 Val64
= SK_PNMI_HUNDREDS_SEC(SkOsGetTime(pAC
));
4731 Val64
-= pAC
->Pnmi
.StartUpTime
;
4732 SK_PNMI_STORE_U64(pBuf
, Val64
);
4733 *pLen
= sizeof(SK_U64
);
4736 case OID_SKGE_MDB_VERSION
:
4737 Val32
= SK_PNMI_MDB_VERSION
;
4738 SK_PNMI_STORE_U32(pBuf
, Val32
);
4739 *pLen
= sizeof(SK_U32
);
4742 case OID_GEN_RCV_ERROR
:
4743 /* 2002-09-17 pweber: For XMAC, use the frozen SW counters (BufPort) */
4744 if (MacType
== SK_MAC_XMAC
) {
4745 Val64
= Val64RxHwErrs
+ pAC
->Pnmi
.BufPort
[NetIndex
].RxNoBufCts
;
4748 Val64
= Val64RxHwErrs
+ pAC
->Pnmi
.Port
[NetIndex
].RxNoBufCts
;
4752 * by default 32bit values are evaluated
4755 Val32
= (SK_U32
)Val64
;
4756 SK_PNMI_STORE_U32(pBuf
, Val32
);
4757 *pLen
= sizeof(SK_U32
);
4760 SK_PNMI_STORE_U64(pBuf
, Val64
);
4761 *pLen
= sizeof(SK_U64
);
4765 case OID_GEN_XMIT_ERROR
:
4766 /* 2002-09-17 pweber: For XMAC, use the frozen SW counters (BufPort) */
4767 if (MacType
== SK_MAC_XMAC
) {
4768 Val64
= Val64TxHwErrs
+ pAC
->Pnmi
.BufPort
[NetIndex
].TxNoBufCts
;
4771 Val64
= Val64TxHwErrs
+ pAC
->Pnmi
.Port
[NetIndex
].TxNoBufCts
;
4775 * by default 32bit values are evaluated
4778 Val32
= (SK_U32
)Val64
;
4779 SK_PNMI_STORE_U32(pBuf
, Val32
);
4780 *pLen
= sizeof(SK_U32
);
4783 SK_PNMI_STORE_U64(pBuf
, Val64
);
4784 *pLen
= sizeof(SK_U64
);
4788 case OID_GEN_RCV_NO_BUFFER
:
4789 /* 2002-09-17 pweber: For XMAC, use the frozen SW counters (BufPort) */
4790 if (MacType
== SK_MAC_XMAC
) {
4791 Val64
= pAC
->Pnmi
.BufPort
[NetIndex
].RxNoBufCts
;
4794 Val64
= pAC
->Pnmi
.Port
[NetIndex
].RxNoBufCts
;
4798 * by default 32bit values are evaluated
4801 Val32
= (SK_U32
)Val64
;
4802 SK_PNMI_STORE_U32(pBuf
, Val32
);
4803 *pLen
= sizeof(SK_U32
);
4806 SK_PNMI_STORE_U64(pBuf
, Val64
);
4807 *pLen
= sizeof(SK_U64
);
4811 case OID_GEN_TRANSMIT_QUEUE_LENGTH
:
4812 Val32
= (SK_U32
)pAC
->Pnmi
.Port
[NetIndex
].TxSwQueueLen
;
4813 SK_PNMI_STORE_U32(pBuf
, Val32
);
4814 *pLen
= sizeof(SK_U32
);
4818 SK_ERR_LOG(pAC
, SK_ERRCL_SW
, SK_PNMI_ERR034
,
4822 return (SK_PNMI_ERR_GENERAL
);
4825 if (Id
== OID_SKGE_RX_HW_ERROR_CTS
||
4826 Id
== OID_SKGE_TX_HW_ERROR_CTS
||
4827 Id
== OID_SKGE_IN_ERRORS_CTS
||
4828 Id
== OID_SKGE_OUT_ERROR_CTS
||
4829 Id
== OID_GEN_XMIT_ERROR
||
4830 Id
== OID_GEN_RCV_ERROR
) {
4832 pAC
->Pnmi
.MacUpdatedFlag
--;
4835 return (SK_PNMI_ERR_OK
);
4838 /*****************************************************************************
4840 * Rlmt - OID handler function of OID_SKGE_RLMT_XXX single instance.
4843 * Get/Presets/Sets the RLMT OIDs.
4846 * SK_PNMI_ERR_OK The request was successfully performed.
4847 * SK_PNMI_ERR_GENERAL A general severe internal error occured.
4848 * SK_PNMI_ERR_TOO_SHORT The passed buffer is too short to contain
4849 * the correct data (e.g. a 32bit value is
4850 * needed, but a 16 bit value was passed).
4851 * SK_PNMI_ERR_BAD_VALUE The passed value is not in the valid
4853 * SK_PNMI_ERR_READ_ONLY The OID is read-only and cannot be set.
4854 * SK_PNMI_ERR_UNKNOWN_INST The requested instance of the OID doesn't
4855 * exist (e.g. port instance 3 on a two port
4858 PNMI_STATIC
int Rlmt(
4859 SK_AC
*pAC
, /* Pointer to adapter context */
4860 SK_IOC IoC
, /* IO context handle */
4861 int Action
, /* GET/PRESET/SET action */
4862 SK_U32 Id
, /* Object ID that is to be processed */
4863 char *pBuf
, /* Buffer used for the management data transfer */
4864 unsigned int *pLen
, /* On call: pBuf buffer length. On return: used buffer */
4865 SK_U32 Instance
, /* Instance (1..n) that is to be queried or -1 */
4866 unsigned int TableIndex
, /* Index to the Id table */
4867 SK_U32 NetIndex
) /* NetIndex (0..n), in single net mode always zero */
4870 unsigned int PhysPortIndex
;
4871 unsigned int PhysPortMax
;
4872 SK_EVPARA EventParam
;
4878 * Check instance. Only single instance OIDs are allowed here.
4880 if (Instance
!= (SK_U32
)(-1) && Instance
!= 1) {
4883 return (SK_PNMI_ERR_UNKNOWN_INST
);
4887 * Perform the requested action.
4889 if (Action
== SK_PNMI_GET
) {
4892 * Check if the buffer length is large enough.
4897 case OID_SKGE_RLMT_MODE
:
4898 case OID_SKGE_RLMT_PORT_ACTIVE
:
4899 case OID_SKGE_RLMT_PORT_PREFERRED
:
4900 if (*pLen
< sizeof(SK_U8
)) {
4902 *pLen
= sizeof(SK_U8
);
4903 return (SK_PNMI_ERR_TOO_SHORT
);
4907 case OID_SKGE_RLMT_PORT_NUMBER
:
4908 if (*pLen
< sizeof(SK_U32
)) {
4910 *pLen
= sizeof(SK_U32
);
4911 return (SK_PNMI_ERR_TOO_SHORT
);
4915 case OID_SKGE_RLMT_CHANGE_CTS
:
4916 case OID_SKGE_RLMT_CHANGE_TIME
:
4917 case OID_SKGE_RLMT_CHANGE_ESTIM
:
4918 case OID_SKGE_RLMT_CHANGE_THRES
:
4919 if (*pLen
< sizeof(SK_U64
)) {
4921 *pLen
= sizeof(SK_U64
);
4922 return (SK_PNMI_ERR_TOO_SHORT
);
4927 SK_ERR_LOG(pAC
, SK_ERRCL_SW
, SK_PNMI_ERR035
,
4931 return (SK_PNMI_ERR_GENERAL
);
4935 * Update RLMT statistic and increment semaphores to indicate
4936 * that an update was already done. Maybe RLMT will hold its
4937 * statistic always up to date some time. Then we can
4938 * remove this type of call.
4940 if ((Ret
= RlmtUpdate(pAC
, IoC
, NetIndex
)) != SK_PNMI_ERR_OK
) {
4945 pAC
->Pnmi
.RlmtUpdatedFlag
++;
4952 case OID_SKGE_RLMT_MODE
:
4953 *pBuf
= (char)pAC
->Rlmt
.Net
[0].RlmtMode
;
4954 *pLen
= sizeof(char);
4957 case OID_SKGE_RLMT_PORT_NUMBER
:
4958 Val32
= (SK_U32
)pAC
->GIni
.GIMacsFound
;
4959 SK_PNMI_STORE_U32(pBuf
, Val32
);
4960 *pLen
= sizeof(SK_U32
);
4963 case OID_SKGE_RLMT_PORT_ACTIVE
:
4966 * If multiple ports may become active this OID
4967 * doesn't make sense any more. A new variable in
4968 * the port structure should be created. However,
4969 * for this variable the first active port is
4972 PhysPortMax
= pAC
->GIni
.GIMacsFound
;
4974 for (PhysPortIndex
= 0; PhysPortIndex
< PhysPortMax
;
4977 if (pAC
->Pnmi
.Port
[PhysPortIndex
].ActiveFlag
) {
4979 *pBuf
= (char)SK_PNMI_PORT_PHYS2LOG(PhysPortIndex
);
4983 *pLen
= sizeof(char);
4986 case OID_SKGE_RLMT_PORT_PREFERRED
:
4987 *pBuf
= (char)SK_PNMI_PORT_PHYS2LOG(pAC
->Rlmt
.Net
[NetIndex
].Preference
);
4988 *pLen
= sizeof(char);
4991 case OID_SKGE_RLMT_CHANGE_CTS
:
4992 Val64
= pAC
->Pnmi
.RlmtChangeCts
;
4993 SK_PNMI_STORE_U64(pBuf
, Val64
);
4994 *pLen
= sizeof(SK_U64
);
4997 case OID_SKGE_RLMT_CHANGE_TIME
:
4998 Val64
= pAC
->Pnmi
.RlmtChangeTime
;
4999 SK_PNMI_STORE_U64(pBuf
, Val64
);
5000 *pLen
= sizeof(SK_U64
);
5003 case OID_SKGE_RLMT_CHANGE_ESTIM
:
5004 Val64
= pAC
->Pnmi
.RlmtChangeEstimate
.Estimate
;
5005 SK_PNMI_STORE_U64(pBuf
, Val64
);
5006 *pLen
= sizeof(SK_U64
);
5009 case OID_SKGE_RLMT_CHANGE_THRES
:
5010 Val64
= pAC
->Pnmi
.RlmtChangeThreshold
;
5011 SK_PNMI_STORE_U64(pBuf
, Val64
);
5012 *pLen
= sizeof(SK_U64
);
5016 SK_DBG_MSG(pAC
, SK_DBGMOD_PNMI
, SK_DBGCAT_ERR
,
5017 ("Rlmt: Unknown OID should be handled before"));
5019 pAC
->Pnmi
.RlmtUpdatedFlag
--;
5021 return (SK_PNMI_ERR_GENERAL
);
5024 pAC
->Pnmi
.RlmtUpdatedFlag
--;
5027 /* Perform a preset or set */
5030 case OID_SKGE_RLMT_MODE
:
5031 /* Check if the buffer length is plausible */
5032 if (*pLen
< sizeof(char)) {
5034 *pLen
= sizeof(char);
5035 return (SK_PNMI_ERR_TOO_SHORT
);
5037 /* Check if the value range is correct */
5038 if (*pLen
!= sizeof(char) ||
5039 (*pBuf
& SK_PNMI_RLMT_MODE_CHK_LINK
) == 0 ||
5040 *(SK_U8
*)pBuf
> 15) {
5043 return (SK_PNMI_ERR_BAD_VALUE
);
5045 /* The preset ends here */
5046 if (Action
== SK_PNMI_PRESET
) {
5049 return (SK_PNMI_ERR_OK
);
5051 /* Send an event to RLMT to change the mode */
5052 SK_MEMSET((char *)&EventParam
, 0, sizeof(EventParam
));
5053 EventParam
.Para32
[0] |= (SK_U32
)(*pBuf
);
5054 EventParam
.Para32
[1] = 0;
5055 if (SkRlmtEvent(pAC
, IoC
, SK_RLMT_MODE_CHANGE
,
5058 SK_ERR_LOG(pAC
, SK_ERRCL_SW
, SK_PNMI_ERR037
,
5062 return (SK_PNMI_ERR_GENERAL
);
5066 case OID_SKGE_RLMT_PORT_PREFERRED
:
5067 /* Check if the buffer length is plausible */
5068 if (*pLen
< sizeof(char)) {
5070 *pLen
= sizeof(char);
5071 return (SK_PNMI_ERR_TOO_SHORT
);
5073 /* Check if the value range is correct */
5074 if (*pLen
!= sizeof(char) || *(SK_U8
*)pBuf
>
5075 (SK_U8
)pAC
->GIni
.GIMacsFound
) {
5078 return (SK_PNMI_ERR_BAD_VALUE
);
5080 /* The preset ends here */
5081 if (Action
== SK_PNMI_PRESET
) {
5084 return (SK_PNMI_ERR_OK
);
5088 * Send an event to RLMT change the preferred port.
5089 * A param of -1 means automatic mode. RLMT will
5090 * make the decision which is the preferred port.
5092 SK_MEMSET((char *)&EventParam
, 0, sizeof(EventParam
));
5093 EventParam
.Para32
[0] = (SK_U32
)(*pBuf
) - 1;
5094 EventParam
.Para32
[1] = NetIndex
;
5095 if (SkRlmtEvent(pAC
, IoC
, SK_RLMT_PREFPORT_CHANGE
,
5098 SK_ERR_LOG(pAC
, SK_ERRCL_SW
, SK_PNMI_ERR038
,
5102 return (SK_PNMI_ERR_GENERAL
);
5106 case OID_SKGE_RLMT_CHANGE_THRES
:
5107 /* Check if the buffer length is plausible */
5108 if (*pLen
< sizeof(SK_U64
)) {
5110 *pLen
= sizeof(SK_U64
);
5111 return (SK_PNMI_ERR_TOO_SHORT
);
5114 * There are not many restrictions to the
5117 if (*pLen
!= sizeof(SK_U64
)) {
5120 return (SK_PNMI_ERR_BAD_VALUE
);
5122 /* A preset ends here */
5123 if (Action
== SK_PNMI_PRESET
) {
5126 return (SK_PNMI_ERR_OK
);
5129 * Store the new threshold, which will be taken
5130 * on the next timer event.
5132 SK_PNMI_READ_U64(pBuf
, Val64
);
5133 pAC
->Pnmi
.RlmtChangeThreshold
= Val64
;
5137 /* The other OIDs are not be able for set */
5139 return (SK_PNMI_ERR_READ_ONLY
);
5143 return (SK_PNMI_ERR_OK
);
5146 /*****************************************************************************
5148 * RlmtStat - OID handler function of OID_SKGE_RLMT_XXX multiple instance.
5151 * Performs get requests on multiple instance variables.
5154 * SK_PNMI_ERR_OK The request was successfully performed.
5155 * SK_PNMI_ERR_GENERAL A general severe internal error occured.
5156 * SK_PNMI_ERR_TOO_SHORT The passed buffer is too short to contain
5157 * the correct data (e.g. a 32bit value is
5158 * needed, but a 16 bit value was passed).
5159 * SK_PNMI_ERR_UNKNOWN_INST The requested instance of the OID doesn't
5160 * exist (e.g. port instance 3 on a two port
5163 PNMI_STATIC
int RlmtStat(
5164 SK_AC
*pAC
, /* Pointer to adapter context */
5165 SK_IOC IoC
, /* IO context handle */
5166 int Action
, /* GET/PRESET/SET action */
5167 SK_U32 Id
, /* Object ID that is to be processed */
5168 char *pBuf
, /* Buffer used for the management data transfer */
5169 unsigned int *pLen
, /* On call: pBuf buffer length. On return: used buffer */
5170 SK_U32 Instance
, /* Instance (1..n) that is to be queried or -1 */
5171 unsigned int TableIndex
, /* Index to the Id table */
5172 SK_U32 NetIndex
) /* NetIndex (0..n), in single net mode always zero */
5174 unsigned int PhysPortMax
;
5175 unsigned int PhysPortIndex
;
5177 unsigned int Offset
;
5183 * Calculate the port indexes from the instance.
5185 PhysPortMax
= pAC
->GIni
.GIMacsFound
;
5187 if ((Instance
!= (SK_U32
)(-1))) {
5188 /* Check instance range */
5189 if ((Instance
< 1) || (Instance
> PhysPortMax
)) {
5192 return (SK_PNMI_ERR_UNKNOWN_INST
);
5195 /* Single net mode */
5196 PhysPortIndex
= Instance
- 1;
5199 if (pAC
->Pnmi
.DualNetActiveFlag
== SK_TRUE
) {
5200 PhysPortIndex
= NetIndex
;
5203 /* Both net modes */
5204 Limit
= PhysPortIndex
+ 1;
5207 /* Single net mode */
5209 Limit
= PhysPortMax
;
5212 if (pAC
->Pnmi
.DualNetActiveFlag
== SK_TRUE
) {
5213 PhysPortIndex
= NetIndex
;
5214 Limit
= PhysPortIndex
+ 1;
5219 * Currently only get requests are allowed.
5221 if (Action
!= SK_PNMI_GET
) {
5224 return (SK_PNMI_ERR_READ_ONLY
);
5228 * Check if the buffer length is large enough.
5232 case OID_SKGE_RLMT_PORT_INDEX
:
5233 case OID_SKGE_RLMT_STATUS
:
5234 if (*pLen
< (Limit
- PhysPortIndex
) * sizeof(SK_U32
)) {
5236 *pLen
= (Limit
- PhysPortIndex
) * sizeof(SK_U32
);
5237 return (SK_PNMI_ERR_TOO_SHORT
);
5241 case OID_SKGE_RLMT_TX_HELLO_CTS
:
5242 case OID_SKGE_RLMT_RX_HELLO_CTS
:
5243 case OID_SKGE_RLMT_TX_SP_REQ_CTS
:
5244 case OID_SKGE_RLMT_RX_SP_CTS
:
5245 if (*pLen
< (Limit
- PhysPortIndex
) * sizeof(SK_U64
)) {
5247 *pLen
= (Limit
- PhysPortIndex
) * sizeof(SK_U64
);
5248 return (SK_PNMI_ERR_TOO_SHORT
);
5253 SK_ERR_LOG(pAC
, SK_ERRCL_SW
, SK_PNMI_ERR039
,
5257 return (SK_PNMI_ERR_GENERAL
);
5262 * Update statistic and increment semaphores to indicate that
5263 * an update was already done.
5265 if ((Ret
= RlmtUpdate(pAC
, IoC
, NetIndex
)) != SK_PNMI_ERR_OK
) {
5270 pAC
->Pnmi
.RlmtUpdatedFlag
++;
5276 for (; PhysPortIndex
< Limit
; PhysPortIndex
++) {
5280 case OID_SKGE_RLMT_PORT_INDEX
:
5281 Val32
= PhysPortIndex
;
5282 SK_PNMI_STORE_U32(pBuf
+ Offset
, Val32
);
5283 Offset
+= sizeof(SK_U32
);
5286 case OID_SKGE_RLMT_STATUS
:
5287 if (pAC
->Rlmt
.Port
[PhysPortIndex
].PortState
==
5289 pAC
->Rlmt
.Port
[PhysPortIndex
].PortState
==
5292 Val32
= SK_PNMI_RLMT_STATUS_ERROR
;
5294 else if (pAC
->Pnmi
.Port
[PhysPortIndex
].ActiveFlag
) {
5296 Val32
= SK_PNMI_RLMT_STATUS_ACTIVE
;
5299 Val32
= SK_PNMI_RLMT_STATUS_STANDBY
;
5301 SK_PNMI_STORE_U32(pBuf
+ Offset
, Val32
);
5302 Offset
+= sizeof(SK_U32
);
5305 case OID_SKGE_RLMT_TX_HELLO_CTS
:
5306 Val64
= pAC
->Rlmt
.Port
[PhysPortIndex
].TxHelloCts
;
5307 SK_PNMI_STORE_U64(pBuf
+ Offset
, Val64
);
5308 Offset
+= sizeof(SK_U64
);
5311 case OID_SKGE_RLMT_RX_HELLO_CTS
:
5312 Val64
= pAC
->Rlmt
.Port
[PhysPortIndex
].RxHelloCts
;
5313 SK_PNMI_STORE_U64(pBuf
+ Offset
, Val64
);
5314 Offset
+= sizeof(SK_U64
);
5317 case OID_SKGE_RLMT_TX_SP_REQ_CTS
:
5318 Val64
= pAC
->Rlmt
.Port
[PhysPortIndex
].TxSpHelloReqCts
;
5319 SK_PNMI_STORE_U64(pBuf
+ Offset
, Val64
);
5320 Offset
+= sizeof(SK_U64
);
5323 case OID_SKGE_RLMT_RX_SP_CTS
:
5324 Val64
= pAC
->Rlmt
.Port
[PhysPortIndex
].RxSpHelloCts
;
5325 SK_PNMI_STORE_U64(pBuf
+ Offset
, Val64
);
5326 Offset
+= sizeof(SK_U64
);
5330 SK_DBG_MSG(pAC
, SK_DBGMOD_PNMI
, SK_DBGCAT_ERR
,
5331 ("RlmtStat: Unknown OID should be errored before"));
5333 pAC
->Pnmi
.RlmtUpdatedFlag
--;
5335 return (SK_PNMI_ERR_GENERAL
);
5340 pAC
->Pnmi
.RlmtUpdatedFlag
--;
5342 return (SK_PNMI_ERR_OK
);
5345 /*****************************************************************************
5347 * MacPrivateConf - OID handler function of OIDs concerning the configuration
5350 * Get/Presets/Sets the OIDs concerning the configuration.
5353 * SK_PNMI_ERR_OK The request was successfully performed.
5354 * SK_PNMI_ERR_GENERAL A general severe internal error occured.
5355 * SK_PNMI_ERR_TOO_SHORT The passed buffer is too short to contain
5356 * the correct data (e.g. a 32bit value is
5357 * needed, but a 16 bit value was passed).
5358 * SK_PNMI_ERR_BAD_VALUE The passed value is not in the valid
5360 * SK_PNMI_ERR_READ_ONLY The OID is read-only and cannot be set.
5361 * SK_PNMI_ERR_UNKNOWN_INST The requested instance of the OID doesn't
5362 * exist (e.g. port instance 3 on a two port
5365 PNMI_STATIC
int MacPrivateConf(
5366 SK_AC
*pAC
, /* Pointer to adapter context */
5367 SK_IOC IoC
, /* IO context handle */
5368 int Action
, /* GET/PRESET/SET action */
5369 SK_U32 Id
, /* Object ID that is to be processed */
5370 char *pBuf
, /* Buffer used for the management data transfer */
5371 unsigned int *pLen
, /* On call: pBuf buffer length. On return: used buffer */
5372 SK_U32 Instance
, /* Instance (1..n) that is to be queried or -1 */
5373 unsigned int TableIndex
, /* Index to the Id table */
5374 SK_U32 NetIndex
) /* NetIndex (0..n), in single net mode always zero */
5376 unsigned int PhysPortMax
;
5377 unsigned int PhysPortIndex
;
5378 unsigned int LogPortMax
;
5379 unsigned int LogPortIndex
;
5381 unsigned int Offset
;
5385 SK_EVPARA EventParam
;
5389 * Calculate instance if wished. MAC index 0 is the virtual MAC.
5391 PhysPortMax
= pAC
->GIni
.GIMacsFound
;
5392 LogPortMax
= SK_PNMI_PORT_PHYS2LOG(PhysPortMax
);
5394 if (pAC
->Pnmi
.DualNetActiveFlag
== SK_TRUE
) { /* Dual net mode */
5398 if ((Instance
!= (SK_U32
)(-1))) { /* Only one specific instance is queried */
5399 /* Check instance range */
5400 if ((Instance
< 1) || (Instance
> LogPortMax
)) {
5403 return (SK_PNMI_ERR_UNKNOWN_INST
);
5405 LogPortIndex
= SK_PNMI_PORT_INST2LOG(Instance
);
5406 Limit
= LogPortIndex
+ 1;
5409 else { /* Instance == (SK_U32)(-1), get all Instances of that OID */
5418 if (Action
== SK_PNMI_GET
) {
5424 case OID_SKGE_CONNECTOR
:
5425 case OID_SKGE_LINK_CAP
:
5426 case OID_SKGE_LINK_MODE
:
5427 case OID_SKGE_LINK_MODE_STATUS
:
5428 case OID_SKGE_LINK_STATUS
:
5429 case OID_SKGE_FLOWCTRL_CAP
:
5430 case OID_SKGE_FLOWCTRL_MODE
:
5431 case OID_SKGE_FLOWCTRL_STATUS
:
5432 case OID_SKGE_PHY_OPERATION_CAP
:
5433 case OID_SKGE_PHY_OPERATION_MODE
:
5434 case OID_SKGE_PHY_OPERATION_STATUS
:
5435 case OID_SKGE_SPEED_CAP
:
5436 case OID_SKGE_SPEED_MODE
:
5437 case OID_SKGE_SPEED_STATUS
:
5438 if (*pLen
< (Limit
- LogPortIndex
) * sizeof(SK_U8
)) {
5440 *pLen
= (Limit
- LogPortIndex
) * sizeof(SK_U8
);
5441 return (SK_PNMI_ERR_TOO_SHORT
);
5446 if (*pLen
< (Limit
- LogPortIndex
) * sizeof(SK_U32
)) {
5448 *pLen
= (Limit
- LogPortIndex
) * sizeof(SK_U32
);
5449 return (SK_PNMI_ERR_TOO_SHORT
);
5454 SK_ERR_LOG(pAC
, SK_ERRCL_SW
, SK_PNMI_ERR041
,
5457 return (SK_PNMI_ERR_GENERAL
);
5461 * Update statistic and increment semaphore to indicate
5462 * that an update was already done.
5464 if ((Ret
= SirqUpdate(pAC
, IoC
)) != SK_PNMI_ERR_OK
) {
5469 pAC
->Pnmi
.SirqUpdatedFlag
++;
5475 for (; LogPortIndex
< Limit
; LogPortIndex
++) {
5477 pBufPtr
= pBuf
+ Offset
;
5482 *pBufPtr
= pAC
->Pnmi
.PMD
;
5483 Offset
+= sizeof(char);
5486 case OID_SKGE_CONNECTOR
:
5487 *pBufPtr
= pAC
->Pnmi
.Connector
;
5488 Offset
+= sizeof(char);
5491 case OID_SKGE_LINK_CAP
:
5492 if (!pAC
->Pnmi
.DualNetActiveFlag
) { /* SingleNetMode */
5493 if (LogPortIndex
== 0) {
5494 /* Get value for virtual port */
5495 VirtualConf(pAC
, IoC
, Id
, pBufPtr
);
5498 /* Get value for physical ports */
5499 PhysPortIndex
= SK_PNMI_PORT_LOG2PHYS(
5502 *pBufPtr
= pAC
->GIni
.GP
[PhysPortIndex
].PLinkCap
;
5505 else { /* DualNetMode */
5507 *pBufPtr
= pAC
->GIni
.GP
[NetIndex
].PLinkCap
;
5509 Offset
+= sizeof(char);
5512 case OID_SKGE_LINK_MODE
:
5513 if (!pAC
->Pnmi
.DualNetActiveFlag
) { /* SingleNetMode */
5514 if (LogPortIndex
== 0) {
5515 /* Get value for virtual port */
5516 VirtualConf(pAC
, IoC
, Id
, pBufPtr
);
5519 /* Get value for physical ports */
5520 PhysPortIndex
= SK_PNMI_PORT_LOG2PHYS(
5523 *pBufPtr
= pAC
->GIni
.GP
[PhysPortIndex
].PLinkModeConf
;
5526 else { /* DualNetMode */
5528 *pBufPtr
= pAC
->GIni
.GP
[NetIndex
].PLinkModeConf
;
5530 Offset
+= sizeof(char);
5533 case OID_SKGE_LINK_MODE_STATUS
:
5534 if (!pAC
->Pnmi
.DualNetActiveFlag
) { /* SingleNetMode */
5535 if (LogPortIndex
== 0) {
5536 /* Get value for virtual port */
5537 VirtualConf(pAC
, IoC
, Id
, pBufPtr
);
5540 /* Get value for physical port */
5541 PhysPortIndex
= SK_PNMI_PORT_LOG2PHYS(
5545 CalculateLinkModeStatus(pAC
, IoC
, PhysPortIndex
);
5548 else { /* DualNetMode */
5550 *pBufPtr
= CalculateLinkModeStatus(pAC
, IoC
, NetIndex
);
5552 Offset
+= sizeof(char);
5555 case OID_SKGE_LINK_STATUS
:
5556 if (!pAC
->Pnmi
.DualNetActiveFlag
) { /* SingleNetMode */
5557 if (LogPortIndex
== 0) {
5558 /* Get value for virtual port */
5559 VirtualConf(pAC
, IoC
, Id
, pBufPtr
);
5562 /* Get value for physical ports */
5563 PhysPortIndex
= SK_PNMI_PORT_LOG2PHYS(
5566 *pBufPtr
= CalculateLinkStatus(pAC
, IoC
, PhysPortIndex
);
5569 else { /* DualNetMode */
5571 *pBufPtr
= CalculateLinkStatus(pAC
, IoC
, NetIndex
);
5573 Offset
+= sizeof(char);
5576 case OID_SKGE_FLOWCTRL_CAP
:
5577 if (!pAC
->Pnmi
.DualNetActiveFlag
) { /* SingleNetMode */
5578 if (LogPortIndex
== 0) {
5579 /* Get value for virtual port */
5580 VirtualConf(pAC
, IoC
, Id
, pBufPtr
);
5583 /* Get value for physical ports */
5584 PhysPortIndex
= SK_PNMI_PORT_LOG2PHYS(
5587 *pBufPtr
= pAC
->GIni
.GP
[PhysPortIndex
].PFlowCtrlCap
;
5590 else { /* DualNetMode */
5592 *pBufPtr
= pAC
->GIni
.GP
[NetIndex
].PFlowCtrlCap
;
5594 Offset
+= sizeof(char);
5597 case OID_SKGE_FLOWCTRL_MODE
:
5598 if (!pAC
->Pnmi
.DualNetActiveFlag
) { /* SingleNetMode */
5599 if (LogPortIndex
== 0) {
5600 /* Get value for virtual port */
5601 VirtualConf(pAC
, IoC
, Id
, pBufPtr
);
5604 /* Get value for physical port */
5605 PhysPortIndex
= SK_PNMI_PORT_LOG2PHYS(
5608 *pBufPtr
= pAC
->GIni
.GP
[PhysPortIndex
].PFlowCtrlMode
;
5611 else { /* DualNetMode */
5613 *pBufPtr
= pAC
->GIni
.GP
[NetIndex
].PFlowCtrlMode
;
5615 Offset
+= sizeof(char);
5618 case OID_SKGE_FLOWCTRL_STATUS
:
5619 if (!pAC
->Pnmi
.DualNetActiveFlag
) { /* SingleNetMode */
5620 if (LogPortIndex
== 0) {
5621 /* Get value for virtual port */
5622 VirtualConf(pAC
, IoC
, Id
, pBufPtr
);
5625 /* Get value for physical port */
5626 PhysPortIndex
= SK_PNMI_PORT_LOG2PHYS(
5629 *pBufPtr
= pAC
->GIni
.GP
[PhysPortIndex
].PFlowCtrlStatus
;
5632 else { /* DualNetMode */
5634 *pBufPtr
= pAC
->GIni
.GP
[NetIndex
].PFlowCtrlStatus
;
5636 Offset
+= sizeof(char);
5639 case OID_SKGE_PHY_OPERATION_CAP
:
5640 if (!pAC
->Pnmi
.DualNetActiveFlag
) { /* SingleNetMode */
5641 if (LogPortIndex
== 0) {
5642 /* Get value for virtual port */
5643 VirtualConf(pAC
, IoC
, Id
, pBufPtr
);
5646 /* Get value for physical ports */
5647 PhysPortIndex
= SK_PNMI_PORT_LOG2PHYS(
5650 *pBufPtr
= pAC
->GIni
.GP
[PhysPortIndex
].PMSCap
;
5653 else { /* DualNetMode */
5655 *pBufPtr
= pAC
->GIni
.GP
[NetIndex
].PMSCap
;
5657 Offset
+= sizeof(char);
5660 case OID_SKGE_PHY_OPERATION_MODE
:
5661 if (!pAC
->Pnmi
.DualNetActiveFlag
) { /* SingleNetMode */
5662 if (LogPortIndex
== 0) {
5663 /* Get value for virtual port */
5664 VirtualConf(pAC
, IoC
, Id
, pBufPtr
);
5667 /* Get value for physical port */
5668 PhysPortIndex
= SK_PNMI_PORT_LOG2PHYS(
5671 *pBufPtr
= pAC
->GIni
.GP
[PhysPortIndex
].PMSMode
;
5674 else { /* DualNetMode */
5676 *pBufPtr
= pAC
->GIni
.GP
[NetIndex
].PMSMode
;
5678 Offset
+= sizeof(char);
5681 case OID_SKGE_PHY_OPERATION_STATUS
:
5682 if (!pAC
->Pnmi
.DualNetActiveFlag
) { /* SingleNetMode */
5683 if (LogPortIndex
== 0) {
5684 /* Get value for virtual port */
5685 VirtualConf(pAC
, IoC
, Id
, pBufPtr
);
5688 /* Get value for physical port */
5689 PhysPortIndex
= SK_PNMI_PORT_LOG2PHYS(
5692 *pBufPtr
= pAC
->GIni
.GP
[PhysPortIndex
].PMSStatus
;
5697 *pBufPtr
= pAC
->GIni
.GP
[NetIndex
].PMSStatus
;
5699 Offset
+= sizeof(char);
5702 case OID_SKGE_SPEED_CAP
:
5703 if (!pAC
->Pnmi
.DualNetActiveFlag
) { /* SingleNetMode */
5704 if (LogPortIndex
== 0) {
5705 /* Get value for virtual port */
5706 VirtualConf(pAC
, IoC
, Id
, pBufPtr
);
5709 /* Get value for physical ports */
5710 PhysPortIndex
= SK_PNMI_PORT_LOG2PHYS(
5713 *pBufPtr
= pAC
->GIni
.GP
[PhysPortIndex
].PLinkSpeedCap
;
5716 else { /* DualNetMode */
5718 *pBufPtr
= pAC
->GIni
.GP
[NetIndex
].PLinkSpeedCap
;
5720 Offset
+= sizeof(char);
5723 case OID_SKGE_SPEED_MODE
:
5724 if (!pAC
->Pnmi
.DualNetActiveFlag
) { /* SingleNetMode */
5725 if (LogPortIndex
== 0) {
5726 /* Get value for virtual port */
5727 VirtualConf(pAC
, IoC
, Id
, pBufPtr
);
5730 /* Get value for physical port */
5731 PhysPortIndex
= SK_PNMI_PORT_LOG2PHYS(
5734 *pBufPtr
= pAC
->GIni
.GP
[PhysPortIndex
].PLinkSpeed
;
5737 else { /* DualNetMode */
5739 *pBufPtr
= pAC
->GIni
.GP
[NetIndex
].PLinkSpeed
;
5741 Offset
+= sizeof(char);
5744 case OID_SKGE_SPEED_STATUS
:
5745 if (!pAC
->Pnmi
.DualNetActiveFlag
) { /* SingleNetMode */
5746 if (LogPortIndex
== 0) {
5747 /* Get value for virtual port */
5748 VirtualConf(pAC
, IoC
, Id
, pBufPtr
);
5751 /* Get value for physical port */
5752 PhysPortIndex
= SK_PNMI_PORT_LOG2PHYS(
5755 *pBufPtr
= pAC
->GIni
.GP
[PhysPortIndex
].PLinkSpeedUsed
;
5758 else { /* DualNetMode */
5760 *pBufPtr
= pAC
->GIni
.GP
[NetIndex
].PLinkSpeedUsed
;
5762 Offset
+= sizeof(char);
5766 Val32
= SK_DRIVER_GET_MTU(pAC
, IoC
, NetIndex
);
5767 SK_PNMI_STORE_U32(pBufPtr
, Val32
);
5768 Offset
+= sizeof(SK_U32
);
5772 SK_DBG_MSG(pAC
, SK_DBGMOD_PNMI
, SK_DBGCAT_ERR
,
5773 ("MacPrivateConf: Unknown OID should be handled before"));
5775 pAC
->Pnmi
.SirqUpdatedFlag
--;
5776 return (SK_PNMI_ERR_GENERAL
);
5780 pAC
->Pnmi
.SirqUpdatedFlag
--;
5782 return (SK_PNMI_ERR_OK
);
5786 * From here SET or PRESET action. Check if the passed
5787 * buffer length is plausible.
5791 case OID_SKGE_LINK_MODE
:
5792 case OID_SKGE_FLOWCTRL_MODE
:
5793 case OID_SKGE_PHY_OPERATION_MODE
:
5794 case OID_SKGE_SPEED_MODE
:
5795 if (*pLen
< Limit
- LogPortIndex
) {
5797 *pLen
= Limit
- LogPortIndex
;
5798 return (SK_PNMI_ERR_TOO_SHORT
);
5800 if (*pLen
!= Limit
- LogPortIndex
) {
5803 return (SK_PNMI_ERR_BAD_VALUE
);
5808 if (*pLen
< sizeof(SK_U32
)) {
5810 *pLen
= sizeof(SK_U32
);
5811 return (SK_PNMI_ERR_TOO_SHORT
);
5813 if (*pLen
!= sizeof(SK_U32
)) {
5816 return (SK_PNMI_ERR_BAD_VALUE
);
5822 return (SK_PNMI_ERR_READ_ONLY
);
5826 * Perform preset or set
5829 for (; LogPortIndex
< Limit
; LogPortIndex
++) {
5833 case OID_SKGE_LINK_MODE
:
5834 /* Check the value range */
5835 Val8
= *(pBuf
+ Offset
);
5838 Offset
+= sizeof(char);
5841 if (Val8
< SK_LMODE_HALF
||
5842 (LogPortIndex
!= 0 && Val8
> SK_LMODE_AUTOSENSE
) ||
5843 (LogPortIndex
== 0 && Val8
> SK_LMODE_INDETERMINATED
)) {
5846 return (SK_PNMI_ERR_BAD_VALUE
);
5849 /* The preset ends here */
5850 if (Action
== SK_PNMI_PRESET
) {
5852 return (SK_PNMI_ERR_OK
);
5855 if (LogPortIndex
== 0) {
5858 * The virtual port consists of all currently
5859 * active ports. Find them and send an event
5860 * with the new link mode to SIRQ.
5862 for (PhysPortIndex
= 0;
5863 PhysPortIndex
< PhysPortMax
;
5866 if (!pAC
->Pnmi
.Port
[PhysPortIndex
].
5872 EventParam
.Para32
[0] = PhysPortIndex
;
5873 EventParam
.Para32
[1] = (SK_U32
)Val8
;
5874 if (SkGeSirqEvent(pAC
, IoC
,
5878 SK_ERR_LOG(pAC
, SK_ERRCL_SW
,
5883 return (SK_PNMI_ERR_GENERAL
);
5889 * Send an event with the new link mode to
5892 EventParam
.Para32
[0] = SK_PNMI_PORT_LOG2PHYS(
5894 EventParam
.Para32
[1] = (SK_U32
)Val8
;
5895 if (SkGeSirqEvent(pAC
, IoC
, SK_HWEV_SET_LMODE
,
5898 SK_ERR_LOG(pAC
, SK_ERRCL_SW
,
5903 return (SK_PNMI_ERR_GENERAL
);
5906 Offset
+= sizeof(char);
5909 case OID_SKGE_FLOWCTRL_MODE
:
5910 /* Check the value range */
5911 Val8
= *(pBuf
+ Offset
);
5914 Offset
+= sizeof(char);
5917 if (Val8
< SK_FLOW_MODE_NONE
||
5918 (LogPortIndex
!= 0 && Val8
> SK_FLOW_MODE_SYM_OR_REM
) ||
5919 (LogPortIndex
== 0 && Val8
> SK_FLOW_MODE_INDETERMINATED
)) {
5922 return (SK_PNMI_ERR_BAD_VALUE
);
5925 /* The preset ends here */
5926 if (Action
== SK_PNMI_PRESET
) {
5928 return (SK_PNMI_ERR_OK
);
5931 if (LogPortIndex
== 0) {
5934 * The virtual port consists of all currently
5935 * active ports. Find them and send an event
5936 * with the new flow control mode to SIRQ.
5938 for (PhysPortIndex
= 0;
5939 PhysPortIndex
< PhysPortMax
;
5942 if (!pAC
->Pnmi
.Port
[PhysPortIndex
].
5948 EventParam
.Para32
[0] = PhysPortIndex
;
5949 EventParam
.Para32
[1] = (SK_U32
)Val8
;
5950 if (SkGeSirqEvent(pAC
, IoC
,
5951 SK_HWEV_SET_FLOWMODE
,
5954 SK_ERR_LOG(pAC
, SK_ERRCL_SW
,
5959 return (SK_PNMI_ERR_GENERAL
);
5965 * Send an event with the new flow control
5966 * mode to the SIRQ module.
5968 EventParam
.Para32
[0] = SK_PNMI_PORT_LOG2PHYS(
5970 EventParam
.Para32
[1] = (SK_U32
)Val8
;
5971 if (SkGeSirqEvent(pAC
, IoC
,
5972 SK_HWEV_SET_FLOWMODE
, EventParam
)
5975 SK_ERR_LOG(pAC
, SK_ERRCL_SW
,
5980 return (SK_PNMI_ERR_GENERAL
);
5983 Offset
+= sizeof(char);
5986 case OID_SKGE_PHY_OPERATION_MODE
:
5987 /* Check the value range */
5988 Val8
= *(pBuf
+ Offset
);
5990 /* mode of this port remains unchanged */
5991 Offset
+= sizeof(char);
5994 if (Val8
< SK_MS_MODE_AUTO
||
5995 (LogPortIndex
!= 0 && Val8
> SK_MS_MODE_SLAVE
) ||
5996 (LogPortIndex
== 0 && Val8
> SK_MS_MODE_INDETERMINATED
)) {
5999 return (SK_PNMI_ERR_BAD_VALUE
);
6002 /* The preset ends here */
6003 if (Action
== SK_PNMI_PRESET
) {
6005 return (SK_PNMI_ERR_OK
);
6008 if (LogPortIndex
== 0) {
6011 * The virtual port consists of all currently
6012 * active ports. Find them and send an event
6013 * with new master/slave (role) mode to SIRQ.
6015 for (PhysPortIndex
= 0;
6016 PhysPortIndex
< PhysPortMax
;
6019 if (!pAC
->Pnmi
.Port
[PhysPortIndex
].
6025 EventParam
.Para32
[0] = PhysPortIndex
;
6026 EventParam
.Para32
[1] = (SK_U32
)Val8
;
6027 if (SkGeSirqEvent(pAC
, IoC
,
6031 SK_ERR_LOG(pAC
, SK_ERRCL_SW
,
6036 return (SK_PNMI_ERR_GENERAL
);
6042 * Send an event with the new master/slave
6043 * (role) mode to the SIRQ module.
6045 EventParam
.Para32
[0] = SK_PNMI_PORT_LOG2PHYS(
6047 EventParam
.Para32
[1] = (SK_U32
)Val8
;
6048 if (SkGeSirqEvent(pAC
, IoC
,
6049 SK_HWEV_SET_ROLE
, EventParam
) > 0) {
6051 SK_ERR_LOG(pAC
, SK_ERRCL_SW
,
6056 return (SK_PNMI_ERR_GENERAL
);
6060 Offset
+= sizeof(char);
6063 case OID_SKGE_SPEED_MODE
:
6064 /* Check the value range */
6065 Val8
= *(pBuf
+ Offset
);
6068 Offset
+= sizeof(char);
6071 if (Val8
< (SK_LSPEED_AUTO
) ||
6072 (LogPortIndex
!= 0 && Val8
> (SK_LSPEED_1000MBPS
)) ||
6073 (LogPortIndex
== 0 && Val8
> (SK_LSPEED_INDETERMINATED
))) {
6076 return (SK_PNMI_ERR_BAD_VALUE
);
6079 /* The preset ends here */
6080 if (Action
== SK_PNMI_PRESET
) {
6082 return (SK_PNMI_ERR_OK
);
6085 if (LogPortIndex
== 0) {
6088 * The virtual port consists of all currently
6089 * active ports. Find them and send an event
6090 * with the new flow control mode to SIRQ.
6092 for (PhysPortIndex
= 0;
6093 PhysPortIndex
< PhysPortMax
;
6096 if (!pAC
->Pnmi
.Port
[PhysPortIndex
].ActiveFlag
) {
6101 EventParam
.Para32
[0] = PhysPortIndex
;
6102 EventParam
.Para32
[1] = (SK_U32
)Val8
;
6103 if (SkGeSirqEvent(pAC
, IoC
,
6107 SK_ERR_LOG(pAC
, SK_ERRCL_SW
,
6112 return (SK_PNMI_ERR_GENERAL
);
6118 * Send an event with the new flow control
6119 * mode to the SIRQ module.
6121 EventParam
.Para32
[0] = SK_PNMI_PORT_LOG2PHYS(
6123 EventParam
.Para32
[1] = (SK_U32
)Val8
;
6124 if (SkGeSirqEvent(pAC
, IoC
,
6128 SK_ERR_LOG(pAC
, SK_ERRCL_SW
,
6133 return (SK_PNMI_ERR_GENERAL
);
6136 Offset
+= sizeof(char);
6140 /* Check the value range */
6141 Val32
= *(SK_U32
*)(pBuf
+ Offset
);
6143 /* mtu of this port remains unchanged */
6144 Offset
+= sizeof(SK_U32
);
6147 if (SK_DRIVER_PRESET_MTU(pAC
, IoC
, NetIndex
, Val32
) != 0) {
6149 return (SK_PNMI_ERR_BAD_VALUE
);
6152 /* The preset ends here */
6153 if (Action
== SK_PNMI_PRESET
) {
6154 return (SK_PNMI_ERR_OK
);
6157 if (SK_DRIVER_SET_MTU(pAC
, IoC
, NetIndex
, Val32
) != 0) {
6158 return (SK_PNMI_ERR_GENERAL
);
6161 Offset
+= sizeof(SK_U32
);
6165 SK_DBG_MSG(pAC
, SK_DBGMOD_PNMI
, SK_DBGCAT_ERR
,
6166 ("MacPrivateConf: Unknown OID should be handled before set"));
6169 return (SK_PNMI_ERR_GENERAL
);
6173 return (SK_PNMI_ERR_OK
);
6176 /*****************************************************************************
6178 * Monitor - OID handler function for RLMT_MONITOR_XXX
6181 * Because RLMT currently does not support the monitoring of
6182 * remote adapter cards, we return always an empty table.
6185 * SK_PNMI_ERR_OK The request was successfully performed.
6186 * SK_PNMI_ERR_GENERAL A general severe internal error occured.
6187 * SK_PNMI_ERR_TOO_SHORT The passed buffer is too short to contain
6188 * the correct data (e.g. a 32bit value is
6189 * needed, but a 16 bit value was passed).
6190 * SK_PNMI_ERR_BAD_VALUE The passed value is not in the valid
6192 * SK_PNMI_ERR_READ_ONLY The OID is read-only and cannot be set.
6193 * SK_PNMI_ERR_UNKNOWN_INST The requested instance of the OID doesn't
6194 * exist (e.g. port instance 3 on a two port
6197 PNMI_STATIC
int Monitor(
6198 SK_AC
*pAC
, /* Pointer to adapter context */
6199 SK_IOC IoC
, /* IO context handle */
6200 int Action
, /* GET/PRESET/SET action */
6201 SK_U32 Id
, /* Object ID that is to be processed */
6202 char *pBuf
, /* Buffer used for the management data transfer */
6203 unsigned int *pLen
, /* On call: pBuf buffer length. On return: used buffer */
6204 SK_U32 Instance
, /* Instance (1..n) that is to be queried or -1 */
6205 unsigned int TableIndex
, /* Index to the Id table */
6206 SK_U32 NetIndex
) /* NetIndex (0..n), in single net mode always zero */
6210 unsigned int Offset
;
6211 unsigned int Entries
;
6215 * Calculate instance if wished.
6217 /* XXX Not yet implemented. Return always an empty table. */
6220 if ((Instance
!= (SK_U32
)(-1))) {
6222 if ((Instance
< 1) || (Instance
> Entries
)) {
6225 return (SK_PNMI_ERR_UNKNOWN_INST
);
6228 Index
= (unsigned int)Instance
- 1;
6229 Limit
= (unsigned int)Instance
;
6239 if (Action
== SK_PNMI_GET
) {
6241 for (Offset
=0; Index
< Limit
; Index
++) {
6245 case OID_SKGE_RLMT_MONITOR_INDEX
:
6246 case OID_SKGE_RLMT_MONITOR_ADDR
:
6247 case OID_SKGE_RLMT_MONITOR_ERRS
:
6248 case OID_SKGE_RLMT_MONITOR_TIMESTAMP
:
6249 case OID_SKGE_RLMT_MONITOR_ADMIN
:
6253 SK_ERR_LOG(pAC
, SK_ERRCL_SW
, SK_PNMI_ERR046
,
6257 return (SK_PNMI_ERR_GENERAL
);
6263 /* Only MONITOR_ADMIN can be set */
6264 if (Id
!= OID_SKGE_RLMT_MONITOR_ADMIN
) {
6267 return (SK_PNMI_ERR_READ_ONLY
);
6270 /* Check if the length is plausible */
6271 if (*pLen
< (Limit
- Index
)) {
6273 return (SK_PNMI_ERR_TOO_SHORT
);
6275 /* Okay, we have a wide value range */
6276 if (*pLen
!= (Limit
- Index
)) {
6279 return (SK_PNMI_ERR_BAD_VALUE
);
6282 for (Offset=0; Index < Limit; Index ++) {
6286 * XXX Not yet implemented. Return always BAD_VALUE, because the table
6290 return (SK_PNMI_ERR_BAD_VALUE
);
6293 return (SK_PNMI_ERR_OK
);
6296 /*****************************************************************************
6298 * VirtualConf - Calculates the values of configuration OIDs for virtual port
6301 * We handle here the get of the configuration group OIDs, which are
6302 * a little bit complicated. The virtual port consists of all currently
6303 * active physical ports. If multiple ports are active and configured
6304 * differently we get in some trouble to return a single value. So we
6305 * get the value of the first active port and compare it with that of
6306 * the other active ports. If they are not the same, we return a value
6307 * that indicates that the state is indeterminated.
6312 PNMI_STATIC
void VirtualConf(
6313 SK_AC
*pAC
, /* Pointer to adapter context */
6314 SK_IOC IoC
, /* IO context handle */
6315 SK_U32 Id
, /* Object ID that is to be processed */
6316 char *pBuf
) /* Buffer used for the management data transfer */
6318 unsigned int PhysPortMax
;
6319 unsigned int PhysPortIndex
;
6321 SK_BOOL PortActiveFlag
;
6325 PortActiveFlag
= SK_FALSE
;
6326 PhysPortMax
= pAC
->GIni
.GIMacsFound
;
6328 for (PhysPortIndex
= 0; PhysPortIndex
< PhysPortMax
;
6331 pPrt
= &pAC
->GIni
.GP
[PhysPortIndex
];
6333 /* Check if the physical port is active */
6334 if (!pAC
->Pnmi
.Port
[PhysPortIndex
].ActiveFlag
) {
6339 PortActiveFlag
= SK_TRUE
;
6343 case OID_SKGE_LINK_CAP
:
6346 * Different capabilities should not happen, but
6347 * in the case of the cases OR them all together.
6348 * From a curious point of view the virtual port
6349 * is capable of all found capabilities.
6351 *pBuf
|= pPrt
->PLinkCap
;
6354 case OID_SKGE_LINK_MODE
:
6355 /* Check if it is the first active port */
6358 *pBuf
= pPrt
->PLinkModeConf
;
6363 * If we find an active port with a different link
6364 * mode than the first one we return a value that
6365 * indicates that the link mode is indeterminated.
6367 if (*pBuf
!= pPrt
->PLinkModeConf
) {
6369 *pBuf
= SK_LMODE_INDETERMINATED
;
6373 case OID_SKGE_LINK_MODE_STATUS
:
6374 /* Get the link mode of the physical port */
6375 Val8
= CalculateLinkModeStatus(pAC
, IoC
, PhysPortIndex
);
6377 /* Check if it is the first active port */
6385 * If we find an active port with a different link
6386 * mode status than the first one we return a value
6387 * that indicates that the link mode status is
6390 if (*pBuf
!= Val8
) {
6392 *pBuf
= SK_LMODE_STAT_INDETERMINATED
;
6396 case OID_SKGE_LINK_STATUS
:
6397 /* Get the link status of the physical port */
6398 Val8
= CalculateLinkStatus(pAC
, IoC
, PhysPortIndex
);
6400 /* Check if it is the first active port */
6408 * If we find an active port with a different link
6409 * status than the first one, we return a value
6410 * that indicates that the link status is
6413 if (*pBuf
!= Val8
) {
6415 *pBuf
= SK_PNMI_RLMT_LSTAT_INDETERMINATED
;
6419 case OID_SKGE_FLOWCTRL_CAP
:
6420 /* Check if it is the first active port */
6423 *pBuf
= pPrt
->PFlowCtrlCap
;
6428 * From a curious point of view the virtual port
6429 * is capable of all found capabilities.
6431 *pBuf
|= pPrt
->PFlowCtrlCap
;
6434 case OID_SKGE_FLOWCTRL_MODE
:
6435 /* Check if it is the first active port */
6438 *pBuf
= pPrt
->PFlowCtrlMode
;
6443 * If we find an active port with a different flow
6444 * control mode than the first one, we return a value
6445 * that indicates that the mode is indeterminated.
6447 if (*pBuf
!= pPrt
->PFlowCtrlMode
) {
6449 *pBuf
= SK_FLOW_MODE_INDETERMINATED
;
6453 case OID_SKGE_FLOWCTRL_STATUS
:
6454 /* Check if it is the first active port */
6457 *pBuf
= pPrt
->PFlowCtrlStatus
;
6462 * If we find an active port with a different flow
6463 * control status than the first one, we return a
6464 * value that indicates that the status is
6467 if (*pBuf
!= pPrt
->PFlowCtrlStatus
) {
6469 *pBuf
= SK_FLOW_STAT_INDETERMINATED
;
6473 case OID_SKGE_PHY_OPERATION_CAP
:
6474 /* Check if it is the first active port */
6477 *pBuf
= pPrt
->PMSCap
;
6482 * From a curious point of view the virtual port
6483 * is capable of all found capabilities.
6485 *pBuf
|= pPrt
->PMSCap
;
6488 case OID_SKGE_PHY_OPERATION_MODE
:
6489 /* Check if it is the first active port */
6492 *pBuf
= pPrt
->PMSMode
;
6497 * If we find an active port with a different master/
6498 * slave mode than the first one, we return a value
6499 * that indicates that the mode is indeterminated.
6501 if (*pBuf
!= pPrt
->PMSMode
) {
6503 *pBuf
= SK_MS_MODE_INDETERMINATED
;
6507 case OID_SKGE_PHY_OPERATION_STATUS
:
6508 /* Check if it is the first active port */
6511 *pBuf
= pPrt
->PMSStatus
;
6516 * If we find an active port with a different master/
6517 * slave status than the first one, we return a
6518 * value that indicates that the status is
6521 if (*pBuf
!= pPrt
->PMSStatus
) {
6523 *pBuf
= SK_MS_STAT_INDETERMINATED
;
6527 case OID_SKGE_SPEED_MODE
:
6528 /* Check if it is the first active port */
6531 *pBuf
= pPrt
->PLinkSpeed
;
6536 * If we find an active port with a different flow
6537 * control mode than the first one, we return a value
6538 * that indicates that the mode is indeterminated.
6540 if (*pBuf
!= pPrt
->PLinkSpeed
) {
6542 *pBuf
= SK_LSPEED_INDETERMINATED
;
6546 case OID_SKGE_SPEED_STATUS
:
6547 /* Check if it is the first active port */
6550 *pBuf
= pPrt
->PLinkSpeedUsed
;
6555 * If we find an active port with a different flow
6556 * control status than the first one, we return a
6557 * value that indicates that the status is
6560 if (*pBuf
!= pPrt
->PLinkSpeedUsed
) {
6562 *pBuf
= SK_LSPEED_STAT_INDETERMINATED
;
6569 * If no port is active return an indeterminated answer
6571 if (!PortActiveFlag
) {
6575 case OID_SKGE_LINK_CAP
:
6576 *pBuf
= SK_LMODE_CAP_INDETERMINATED
;
6579 case OID_SKGE_LINK_MODE
:
6580 *pBuf
= SK_LMODE_INDETERMINATED
;
6583 case OID_SKGE_LINK_MODE_STATUS
:
6584 *pBuf
= SK_LMODE_STAT_INDETERMINATED
;
6587 case OID_SKGE_LINK_STATUS
:
6588 *pBuf
= SK_PNMI_RLMT_LSTAT_INDETERMINATED
;
6591 case OID_SKGE_FLOWCTRL_CAP
:
6592 case OID_SKGE_FLOWCTRL_MODE
:
6593 *pBuf
= SK_FLOW_MODE_INDETERMINATED
;
6596 case OID_SKGE_FLOWCTRL_STATUS
:
6597 *pBuf
= SK_FLOW_STAT_INDETERMINATED
;
6600 case OID_SKGE_PHY_OPERATION_CAP
:
6601 *pBuf
= SK_MS_CAP_INDETERMINATED
;
6604 case OID_SKGE_PHY_OPERATION_MODE
:
6605 *pBuf
= SK_MS_MODE_INDETERMINATED
;
6608 case OID_SKGE_PHY_OPERATION_STATUS
:
6609 *pBuf
= SK_MS_STAT_INDETERMINATED
;
6611 case OID_SKGE_SPEED_CAP
:
6612 *pBuf
= SK_LSPEED_CAP_INDETERMINATED
;
6615 case OID_SKGE_SPEED_MODE
:
6616 *pBuf
= SK_LSPEED_INDETERMINATED
;
6619 case OID_SKGE_SPEED_STATUS
:
6620 *pBuf
= SK_LSPEED_STAT_INDETERMINATED
;
6626 /*****************************************************************************
6628 * CalculateLinkStatus - Determins the link status of a physical port
6631 * Determins the link status the following way:
6632 * LSTAT_PHY_DOWN: Link is down
6633 * LSTAT_AUTONEG: Auto-negotiation failed
6634 * LSTAT_LOG_DOWN: Link is up but RLMT did not yet put the port
6636 * LSTAT_LOG_UP: RLMT marked the port as up
6639 * Link status of physical port
6641 PNMI_STATIC SK_U8
CalculateLinkStatus(
6642 SK_AC
*pAC
, /* Pointer to adapter context */
6643 SK_IOC IoC
, /* IO context handle */
6644 unsigned int PhysPortIndex
) /* Physical port index */
6648 if (!pAC
->GIni
.GP
[PhysPortIndex
].PHWLinkUp
) {
6650 Result
= SK_PNMI_RLMT_LSTAT_PHY_DOWN
;
6652 else if (pAC
->GIni
.GP
[PhysPortIndex
].PAutoNegFail
> 0) {
6654 Result
= SK_PNMI_RLMT_LSTAT_AUTONEG
;
6656 else if (!pAC
->Rlmt
.Port
[PhysPortIndex
].PortDown
) {
6658 Result
= SK_PNMI_RLMT_LSTAT_LOG_UP
;
6661 Result
= SK_PNMI_RLMT_LSTAT_LOG_DOWN
;
6667 /*****************************************************************************
6669 * CalculateLinkModeStatus - Determins the link mode status of a phys. port
6672 * The COMMON module only tells us if the mode is half or full duplex.
6673 * But in the decade of auto sensing it is usefull for the user to
6674 * know if the mode was negotiated or forced. Therefore we have a
6675 * look to the mode, which was last used by the negotiation process.
6678 * The link mode status
6680 PNMI_STATIC SK_U8
CalculateLinkModeStatus(
6681 SK_AC
*pAC
, /* Pointer to adapter context */
6682 SK_IOC IoC
, /* IO context handle */
6683 unsigned int PhysPortIndex
) /* Physical port index */
6687 /* Get the current mode, which can be full or half duplex */
6688 Result
= pAC
->GIni
.GP
[PhysPortIndex
].PLinkModeStatus
;
6690 /* Check if no valid mode could be found (link is down) */
6691 if (Result
< SK_LMODE_STAT_HALF
) {
6693 Result
= SK_LMODE_STAT_UNKNOWN
;
6695 else if (pAC
->GIni
.GP
[PhysPortIndex
].PLinkMode
>= SK_LMODE_AUTOHALF
) {
6698 * Auto-negotiation was used to bring up the link. Change
6699 * the already found duplex status that it indicates
6700 * auto-negotiation was involved.
6702 if (Result
== SK_LMODE_STAT_HALF
) {
6704 Result
= SK_LMODE_STAT_AUTOHALF
;
6706 else if (Result
== SK_LMODE_STAT_FULL
) {
6708 Result
= SK_LMODE_STAT_AUTOFULL
;
6715 /*****************************************************************************
6717 * GetVpdKeyArr - Obtain an array of VPD keys
6720 * Read the VPD keys and build an array of VPD keys, which are
6724 * SK_PNMI_ERR_OK Task successfully performed.
6725 * SK_PNMI_ERR_GENERAL Something went wrong.
6727 PNMI_STATIC
int GetVpdKeyArr(
6728 SK_AC
*pAC
, /* Pointer to adapter context */
6729 SK_IOC IoC
, /* IO context handle */
6730 char *pKeyArr
, /* Ptr KeyArray */
6731 unsigned int KeyArrLen
, /* Length of array in bytes */
6732 unsigned int *pKeyNo
) /* Number of keys */
6734 unsigned int BufKeysLen
= SK_PNMI_VPD_BUFSIZE
;
6735 char BufKeys
[SK_PNMI_VPD_BUFSIZE
];
6736 unsigned int StartOffset
;
6737 unsigned int Offset
;
6742 SK_MEMSET(pKeyArr
, 0, KeyArrLen
);
6747 Ret
= VpdKeys(pAC
, IoC
, (char *)&BufKeys
, (int *)&BufKeysLen
,
6751 SK_ERR_LOG(pAC
, SK_ERRCL_SW
, SK_PNMI_ERR014
,
6754 return (SK_PNMI_ERR_GENERAL
);
6756 /* If no keys are available return now */
6757 if (*pKeyNo
== 0 || BufKeysLen
== 0) {
6759 return (SK_PNMI_ERR_OK
);
6762 * If the key list is too long for us trunc it and give a
6763 * errorlog notification. This case should not happen because
6764 * the maximum number of keys is limited due to RAM limitations
6766 if (*pKeyNo
> SK_PNMI_VPD_ENTRIES
) {
6768 SK_ERR_LOG(pAC
, SK_ERRCL_SW
, SK_PNMI_ERR015
,
6771 *pKeyNo
= SK_PNMI_VPD_ENTRIES
;
6775 * Now build an array of fixed string length size and copy
6776 * the keys together.
6778 for (Index
= 0, StartOffset
= 0, Offset
= 0; Offset
< BufKeysLen
;
6781 if (BufKeys
[Offset
] != 0) {
6786 if (Offset
- StartOffset
> SK_PNMI_VPD_KEY_SIZE
) {
6788 SK_ERR_LOG(pAC
, SK_ERRCL_SW
, SK_PNMI_ERR016
,
6790 return (SK_PNMI_ERR_GENERAL
);
6793 SK_STRNCPY(pKeyArr
+ Index
* SK_PNMI_VPD_KEY_SIZE
,
6794 &BufKeys
[StartOffset
], SK_PNMI_VPD_KEY_SIZE
);
6797 StartOffset
= Offset
+ 1;
6800 /* Last key not zero terminated? Get it anyway */
6801 if (StartOffset
< Offset
) {
6803 SK_STRNCPY(pKeyArr
+ Index
* SK_PNMI_VPD_KEY_SIZE
,
6804 &BufKeys
[StartOffset
], SK_PNMI_VPD_KEY_SIZE
);
6807 return (SK_PNMI_ERR_OK
);
6810 /*****************************************************************************
6812 * SirqUpdate - Let the SIRQ update its internal values
6815 * Just to be sure that the SIRQ module holds its internal data
6816 * structures up to date, we send an update event before we make
6820 * SK_PNMI_ERR_OK Task successfully performed.
6821 * SK_PNMI_ERR_GENERAL Something went wrong.
6823 PNMI_STATIC
int SirqUpdate(
6824 SK_AC
*pAC
, /* Pointer to adapter context */
6825 SK_IOC IoC
) /* IO context handle */
6827 SK_EVPARA EventParam
;
6830 /* Was the module already updated during the current PNMI call? */
6831 if (pAC
->Pnmi
.SirqUpdatedFlag
> 0) {
6833 return (SK_PNMI_ERR_OK
);
6836 /* Send an synchronuous update event to the module */
6837 SK_MEMSET((char *)&EventParam
, 0, sizeof(EventParam
));
6838 if (SkGeSirqEvent(pAC
, IoC
, SK_HWEV_UPDATE_STAT
, EventParam
) > 0) {
6840 SK_ERR_LOG(pAC
, SK_ERRCL_SW
, SK_PNMI_ERR047
,
6843 return (SK_PNMI_ERR_GENERAL
);
6846 return (SK_PNMI_ERR_OK
);
6849 /*****************************************************************************
6851 * RlmtUpdate - Let the RLMT update its internal values
6854 * Just to be sure that the RLMT module holds its internal data
6855 * structures up to date, we send an update event before we make
6859 * SK_PNMI_ERR_OK Task successfully performed.
6860 * SK_PNMI_ERR_GENERAL Something went wrong.
6862 PNMI_STATIC
int RlmtUpdate(
6863 SK_AC
*pAC
, /* Pointer to adapter context */
6864 SK_IOC IoC
, /* IO context handle */
6865 SK_U32 NetIndex
) /* NetIndex (0..n), in single net mode allways zero */
6867 SK_EVPARA EventParam
;
6870 /* Was the module already updated during the current PNMI call? */
6871 if (pAC
->Pnmi
.RlmtUpdatedFlag
> 0) {
6873 return (SK_PNMI_ERR_OK
);
6876 /* Send an synchronuous update event to the module */
6877 SK_MEMSET((char *)&EventParam
, 0, sizeof(EventParam
));
6878 EventParam
.Para32
[0] = NetIndex
;
6879 EventParam
.Para32
[1] = (SK_U32
)-1;
6880 if (SkRlmtEvent(pAC
, IoC
, SK_RLMT_STATS_UPDATE
, EventParam
) > 0) {
6882 SK_ERR_LOG(pAC
, SK_ERRCL_SW
, SK_PNMI_ERR048
,
6885 return (SK_PNMI_ERR_GENERAL
);
6888 return (SK_PNMI_ERR_OK
);
6891 /*****************************************************************************
6893 * MacUpdate - Force the XMAC to output the current statistic
6896 * The XMAC holds its statistic internally. To obtain the current
6897 * values we must send a command so that the statistic data will
6898 * be written to a predefined memory area on the adapter.
6901 * SK_PNMI_ERR_OK Task successfully performed.
6902 * SK_PNMI_ERR_GENERAL Something went wrong.
6904 PNMI_STATIC
int MacUpdate(
6905 SK_AC
*pAC
, /* Pointer to adapter context */
6906 SK_IOC IoC
, /* IO context handle */
6907 unsigned int FirstMac
, /* Index of the first Mac to be updated */
6908 unsigned int LastMac
) /* Index of the last Mac to be updated */
6910 unsigned int MacIndex
;
6913 * Were the statistics already updated during the
6914 * current PNMI call?
6916 if (pAC
->Pnmi
.MacUpdatedFlag
> 0) {
6918 return (SK_PNMI_ERR_OK
);
6921 /* Send an update command to all MACs specified */
6922 for (MacIndex
= FirstMac
; MacIndex
<= LastMac
; MacIndex
++) {
6925 * 2002-09-13 pweber: Freeze the current SW counters.
6926 * (That should be done as close as
6927 * possible to the update of the
6930 if (pAC
->GIni
.GIMacType
== SK_MAC_XMAC
) {
6931 pAC
->Pnmi
.BufPort
[MacIndex
] = pAC
->Pnmi
.Port
[MacIndex
];
6934 /* 2002-09-13 pweber: Update the HW counter */
6935 if (pAC
->GIni
.GIFunc
.pFnMacUpdateStats(pAC
, IoC
, MacIndex
) != 0) {
6937 return (SK_PNMI_ERR_GENERAL
);
6941 return (SK_PNMI_ERR_OK
);
6944 /*****************************************************************************
6946 * GetStatVal - Retrieve an XMAC statistic counter
6949 * Retrieves the statistic counter of a virtual or physical port. The
6950 * virtual port is identified by the index 0. It consists of all
6951 * currently active ports. To obtain the counter value for this port
6952 * we must add the statistic counter of all active ports. To grant
6953 * continuous counter values for the virtual port even when port
6954 * switches occur we must additionally add a delta value, which was
6955 * calculated during a SK_PNMI_EVT_RLMT_ACTIVE_UP event.
6958 * Requested statistic value
6960 PNMI_STATIC SK_U64
GetStatVal(
6961 SK_AC
*pAC
, /* Pointer to adapter context */
6962 SK_IOC IoC
, /* IO context handle */
6963 unsigned int LogPortIndex
, /* Index of the logical Port to be processed */
6964 unsigned int StatIndex
, /* Index to statistic value */
6965 SK_U32 NetIndex
) /* NetIndex (0..n), in single net mode allways zero */
6967 unsigned int PhysPortIndex
;
6968 unsigned int PhysPortMax
;
6972 if (pAC
->Pnmi
.DualNetActiveFlag
== SK_TRUE
) { /* Dual net mode */
6974 PhysPortIndex
= NetIndex
;
6976 Val
= GetPhysStatVal(pAC
, IoC
, PhysPortIndex
, StatIndex
);
6978 else { /* Single Net mode */
6980 if (LogPortIndex
== 0) {
6982 PhysPortMax
= pAC
->GIni
.GIMacsFound
;
6984 /* Add counter of all active ports */
6985 for (PhysPortIndex
= 0; PhysPortIndex
< PhysPortMax
;
6988 if (pAC
->Pnmi
.Port
[PhysPortIndex
].ActiveFlag
) {
6990 Val
+= GetPhysStatVal(pAC
, IoC
, PhysPortIndex
, StatIndex
);
6994 /* Correct value because of port switches */
6995 Val
+= pAC
->Pnmi
.VirtualCounterOffset
[StatIndex
];
6998 /* Get counter value of physical port */
6999 PhysPortIndex
= SK_PNMI_PORT_LOG2PHYS(pAC
, LogPortIndex
);
7001 Val
= GetPhysStatVal(pAC
, IoC
, PhysPortIndex
, StatIndex
);
7007 /*****************************************************************************
7009 * GetPhysStatVal - Get counter value for physical port
7012 * Builds a 64bit counter value. Except for the octet counters
7013 * the lower 32bit are counted in hardware and the upper 32bit
7014 * in software by monitoring counter overflow interrupts in the
7015 * event handler. To grant continous counter values during XMAC
7016 * resets (caused by a workaround) we must add a delta value.
7017 * The delta was calculated in the event handler when a
7018 * SK_PNMI_EVT_XMAC_RESET was received.
7023 PNMI_STATIC SK_U64
GetPhysStatVal(
7024 SK_AC
*pAC
, /* Pointer to adapter context */
7025 SK_IOC IoC
, /* IO context handle */
7026 unsigned int PhysPortIndex
, /* Index of the logical Port to be processed */
7027 unsigned int StatIndex
) /* Index to statistic value */
7034 unsigned int HelpIndex
;
7037 SK_PNMI_PORT
*pPnmiPrt
;
7038 SK_GEMACFUNC
*pFnMac
;
7040 pPrt
= &pAC
->GIni
.GP
[PhysPortIndex
];
7042 MacType
= pAC
->GIni
.GIMacType
;
7044 /* 2002-09-17 pweber: For XMAC, use the frozen SW counters (BufPort) */
7045 if (MacType
== SK_MAC_XMAC
) {
7046 pPnmiPrt
= &pAC
->Pnmi
.BufPort
[PhysPortIndex
];
7049 pPnmiPrt
= &pAC
->Pnmi
.Port
[PhysPortIndex
];
7052 pFnMac
= &pAC
->GIni
.GIFunc
;
7054 switch (StatIndex
) {
7056 if (MacType
== SK_MAC_GMAC
) {
7057 (void)pFnMac
->pFnMacStatistic(pAC
, IoC
, PhysPortIndex
,
7058 StatAddr
[SK_PNMI_HTX_BROADCAST
][MacType
].Reg
,
7060 (void)pFnMac
->pFnMacStatistic(pAC
, IoC
, PhysPortIndex
,
7061 StatAddr
[SK_PNMI_HTX_MULTICAST
][MacType
].Reg
,
7064 (void)pFnMac
->pFnMacStatistic(pAC
, IoC
, PhysPortIndex
,
7065 StatAddr
[SK_PNMI_HTX_UNICAST
][MacType
].Reg
,
7070 (void)pFnMac
->pFnMacStatistic(pAC
, IoC
, PhysPortIndex
,
7071 StatAddr
[StatIndex
][MacType
].Reg
,
7074 HighVal
= pPnmiPrt
->CounterHigh
[StatIndex
];
7078 if (MacType
== SK_MAC_GMAC
) {
7079 (void)pFnMac
->pFnMacStatistic(pAC
, IoC
, PhysPortIndex
,
7080 StatAddr
[SK_PNMI_HRX_BROADCAST
][MacType
].Reg
,
7082 (void)pFnMac
->pFnMacStatistic(pAC
, IoC
, PhysPortIndex
,
7083 StatAddr
[SK_PNMI_HRX_MULTICAST
][MacType
].Reg
,
7086 (void)pFnMac
->pFnMacStatistic(pAC
, IoC
, PhysPortIndex
,
7087 StatAddr
[SK_PNMI_HRX_UNICAST
][MacType
].Reg
,
7092 (void)pFnMac
->pFnMacStatistic(pAC
, IoC
, PhysPortIndex
,
7093 StatAddr
[StatIndex
][MacType
].Reg
,
7096 HighVal
= pPnmiPrt
->CounterHigh
[StatIndex
];
7099 case SK_PNMI_HTX_OCTET
:
7100 case SK_PNMI_HRX_OCTET
:
7101 (void)pFnMac
->pFnMacStatistic(pAC
, IoC
, PhysPortIndex
,
7102 StatAddr
[StatIndex
][MacType
].Reg
,
7104 (void)pFnMac
->pFnMacStatistic(pAC
, IoC
, PhysPortIndex
,
7105 StatAddr
[StatIndex
+ 1][MacType
].Reg
,
7109 case SK_PNMI_HTX_BURST
:
7110 case SK_PNMI_HTX_EXCESS_DEF
:
7111 case SK_PNMI_HTX_CARRIER
:
7112 /* Not supported by GMAC */
7113 if (MacType
== SK_MAC_GMAC
) {
7117 (void)pFnMac
->pFnMacStatistic(pAC
, IoC
, PhysPortIndex
,
7118 StatAddr
[StatIndex
][MacType
].Reg
,
7120 HighVal
= pPnmiPrt
->CounterHigh
[StatIndex
];
7123 case SK_PNMI_HTX_MACC
:
7124 /* GMAC only supports PAUSE MAC control frames */
7125 if (MacType
== SK_MAC_GMAC
) {
7126 HelpIndex
= SK_PNMI_HTX_PMACC
;
7129 HelpIndex
= StatIndex
;
7132 (void)pFnMac
->pFnMacStatistic(pAC
, IoC
, PhysPortIndex
,
7133 StatAddr
[HelpIndex
][MacType
].Reg
,
7136 HighVal
= pPnmiPrt
->CounterHigh
[StatIndex
];
7139 case SK_PNMI_HTX_COL
:
7140 case SK_PNMI_HRX_UNDERSIZE
:
7141 /* Not supported by XMAC */
7142 if (MacType
== SK_MAC_XMAC
) {
7146 (void)pFnMac
->pFnMacStatistic(pAC
, IoC
, PhysPortIndex
,
7147 StatAddr
[StatIndex
][MacType
].Reg
,
7149 HighVal
= pPnmiPrt
->CounterHigh
[StatIndex
];
7152 case SK_PNMI_HTX_DEFFERAL
:
7153 /* Not supported by GMAC */
7154 if (MacType
== SK_MAC_GMAC
) {
7159 * XMAC counts frames with deferred transmission
7160 * even in full-duplex mode.
7162 * In full-duplex mode the counter remains constant!
7164 if ((pPrt
->PLinkModeStatus
== SK_LMODE_STAT_AUTOFULL
) ||
7165 (pPrt
->PLinkModeStatus
== SK_LMODE_STAT_FULL
)) {
7171 /* Otherwise get contents of hardware register */
7172 (void)pFnMac
->pFnMacStatistic(pAC
, IoC
, PhysPortIndex
,
7173 StatAddr
[StatIndex
][MacType
].Reg
,
7175 HighVal
= pPnmiPrt
->CounterHigh
[StatIndex
];
7179 case SK_PNMI_HRX_BADOCTET
:
7180 /* Not supported by XMAC */
7181 if (MacType
== SK_MAC_XMAC
) {
7185 (void)pFnMac
->pFnMacStatistic(pAC
, IoC
, PhysPortIndex
,
7186 StatAddr
[StatIndex
][MacType
].Reg
,
7188 (void)pFnMac
->pFnMacStatistic(pAC
, IoC
, PhysPortIndex
,
7189 StatAddr
[StatIndex
+ 1][MacType
].Reg
,
7193 case SK_PNMI_HTX_OCTETLOW
:
7194 case SK_PNMI_HRX_OCTETLOW
:
7195 case SK_PNMI_HRX_BADOCTETLOW
:
7198 case SK_PNMI_HRX_LONGFRAMES
:
7199 /* For XMAC the SW counter is managed by PNMI */
7200 if (MacType
== SK_MAC_XMAC
) {
7201 return (pPnmiPrt
->StatRxLongFrameCts
);
7204 (void)pFnMac
->pFnMacStatistic(pAC
, IoC
, PhysPortIndex
,
7205 StatAddr
[StatIndex
][MacType
].Reg
,
7207 HighVal
= pPnmiPrt
->CounterHigh
[StatIndex
];
7210 case SK_PNMI_HRX_TOO_LONG
:
7211 (void)pFnMac
->pFnMacStatistic(pAC
, IoC
, PhysPortIndex
,
7212 StatAddr
[StatIndex
][MacType
].Reg
,
7214 HighVal
= pPnmiPrt
->CounterHigh
[StatIndex
];
7216 Val
= (((SK_U64
)HighVal
<< 32) | (SK_U64
)LowVal
);
7218 if (MacType
== SK_MAC_GMAC
) {
7219 /* For GMAC the SW counter is additionally managed by PNMI */
7220 Val
+= pPnmiPrt
->StatRxFrameTooLongCts
;
7224 * Frames longer than IEEE 802.3 frame max size are counted
7225 * by XMAC in frame_too_long counter even reception of long
7226 * frames was enabled and the frame was correct.
7227 * So correct the value by subtracting RxLongFrame counter.
7229 Val
-= pPnmiPrt
->StatRxLongFrameCts
;
7232 LowVal
= (SK_U32
)Val
;
7233 HighVal
= (SK_U32
)(Val
>> 32);
7236 case SK_PNMI_HRX_SHORTS
:
7237 /* Not supported by GMAC */
7238 if (MacType
== SK_MAC_GMAC
) {
7244 * XMAC counts short frame errors even if link down (#10620)
7246 * If link-down the counter remains constant
7248 if (pPrt
->PLinkModeStatus
!= SK_LMODE_STAT_UNKNOWN
) {
7250 /* Otherwise get incremental difference */
7251 (void)pFnMac
->pFnMacStatistic(pAC
, IoC
, PhysPortIndex
,
7252 StatAddr
[StatIndex
][MacType
].Reg
,
7254 HighVal
= pPnmiPrt
->CounterHigh
[StatIndex
];
7256 Val
= (((SK_U64
)HighVal
<< 32) | (SK_U64
)LowVal
);
7257 Val
-= pPnmiPrt
->RxShortZeroMark
;
7259 LowVal
= (SK_U32
)Val
;
7260 HighVal
= (SK_U32
)(Val
>> 32);
7264 case SK_PNMI_HRX_MACC
:
7265 case SK_PNMI_HRX_MACC_UNKWN
:
7266 case SK_PNMI_HRX_BURST
:
7267 case SK_PNMI_HRX_MISSED
:
7268 case SK_PNMI_HRX_FRAMING
:
7269 case SK_PNMI_HRX_CARRIER
:
7270 case SK_PNMI_HRX_IRLENGTH
:
7271 case SK_PNMI_HRX_SYMBOL
:
7272 case SK_PNMI_HRX_CEXT
:
7273 /* Not supported by GMAC */
7274 if (MacType
== SK_MAC_GMAC
) {
7278 (void)pFnMac
->pFnMacStatistic(pAC
, IoC
, PhysPortIndex
,
7279 StatAddr
[StatIndex
][MacType
].Reg
,
7281 HighVal
= pPnmiPrt
->CounterHigh
[StatIndex
];
7284 case SK_PNMI_HRX_PMACC_ERR
:
7285 /* For GMAC the SW counter is managed by PNMI */
7286 if (MacType
== SK_MAC_GMAC
) {
7287 return (pPnmiPrt
->StatRxPMaccErr
);
7290 (void)pFnMac
->pFnMacStatistic(pAC
, IoC
, PhysPortIndex
,
7291 StatAddr
[StatIndex
][MacType
].Reg
,
7293 HighVal
= pPnmiPrt
->CounterHigh
[StatIndex
];
7296 /* SW counter managed by PNMI */
7297 case SK_PNMI_HTX_SYNC
:
7298 LowVal
= (SK_U32
)pPnmiPrt
->StatSyncCts
;
7299 HighVal
= (SK_U32
)(pPnmiPrt
->StatSyncCts
>> 32);
7302 /* SW counter managed by PNMI */
7303 case SK_PNMI_HTX_SYNC_OCTET
:
7304 LowVal
= (SK_U32
)pPnmiPrt
->StatSyncOctetsCts
;
7305 HighVal
= (SK_U32
)(pPnmiPrt
->StatSyncOctetsCts
>> 32);
7308 case SK_PNMI_HRX_FCS
:
7310 * Broadcom filters FCS errors and counts it in
7311 * Receive Error Counter register
7313 if (pPrt
->PhyType
== SK_PHY_BCOM
) {
7314 /* do not read while not initialized (PHY_READ hangs!)*/
7315 if (pPrt
->PState
!= SK_PRT_RESET
) {
7316 SkXmPhyRead(pAC
, IoC
, PhysPortIndex
, PHY_BCOM_RE_CTR
, &Word
);
7320 HighVal
= pPnmiPrt
->CounterHigh
[StatIndex
];
7323 (void)pFnMac
->pFnMacStatistic(pAC
, IoC
, PhysPortIndex
,
7324 StatAddr
[StatIndex
][MacType
].Reg
,
7326 HighVal
= pPnmiPrt
->CounterHigh
[StatIndex
];
7331 (void)pFnMac
->pFnMacStatistic(pAC
, IoC
, PhysPortIndex
,
7332 StatAddr
[StatIndex
][MacType
].Reg
,
7334 HighVal
= pPnmiPrt
->CounterHigh
[StatIndex
];
7338 Val
= (((SK_U64
)HighVal
<< 32) | (SK_U64
)LowVal
);
7340 /* Correct value because of possible XMAC reset. XMAC Errata #2 */
7341 Val
+= pPnmiPrt
->CounterOffset
[StatIndex
];
7346 /*****************************************************************************
7348 * ResetCounter - Set all counters and timestamps to zero
7351 * Notifies other common modules which store statistic data to
7352 * reset their counters and finally reset our own counters.
7357 PNMI_STATIC
void ResetCounter(
7358 SK_AC
*pAC
, /* Pointer to adapter context */
7359 SK_IOC IoC
, /* IO context handle */
7362 unsigned int PhysPortIndex
;
7363 SK_EVPARA EventParam
;
7366 SK_MEMSET((char *)&EventParam
, 0, sizeof(EventParam
));
7368 /* Notify sensor module */
7369 SkEventQueue(pAC
, SKGE_I2C
, SK_I2CEV_CLEAR
, EventParam
);
7371 /* Notify RLMT module */
7372 EventParam
.Para32
[0] = NetIndex
;
7373 EventParam
.Para32
[1] = (SK_U32
)-1;
7374 SkEventQueue(pAC
, SKGE_RLMT
, SK_RLMT_STATS_CLEAR
, EventParam
);
7375 EventParam
.Para32
[1] = 0;
7377 /* Notify SIRQ module */
7378 SkEventQueue(pAC
, SKGE_HWAC
, SK_HWEV_CLEAR_STAT
, EventParam
);
7380 /* Notify CSUM module */
7382 EventParam
.Para32
[0] = NetIndex
;
7383 EventParam
.Para32
[1] = (SK_U32
)-1;
7384 SkEventQueue(pAC
, SKGE_CSUM
, SK_CSUM_EVENT_CLEAR_PROTO_STATS
,
7386 #endif /* SK_USE_CSUM */
7388 /* Clear XMAC statistic */
7389 for (PhysPortIndex
= 0; PhysPortIndex
<
7390 (unsigned int)pAC
->GIni
.GIMacsFound
; PhysPortIndex
++) {
7392 (void)pAC
->GIni
.GIFunc
.pFnMacResetCounter(pAC
, IoC
, PhysPortIndex
);
7394 SK_MEMSET((char *)&pAC
->Pnmi
.Port
[PhysPortIndex
].CounterHigh
,
7395 0, sizeof(pAC
->Pnmi
.Port
[PhysPortIndex
].CounterHigh
));
7396 SK_MEMSET((char *)&pAC
->Pnmi
.Port
[PhysPortIndex
].
7397 CounterOffset
, 0, sizeof(pAC
->Pnmi
.Port
[
7398 PhysPortIndex
].CounterOffset
));
7399 SK_MEMSET((char *)&pAC
->Pnmi
.Port
[PhysPortIndex
].StatSyncCts
,
7400 0, sizeof(pAC
->Pnmi
.Port
[PhysPortIndex
].StatSyncCts
));
7401 SK_MEMSET((char *)&pAC
->Pnmi
.Port
[PhysPortIndex
].
7402 StatSyncOctetsCts
, 0, sizeof(pAC
->Pnmi
.Port
[
7403 PhysPortIndex
].StatSyncOctetsCts
));
7404 SK_MEMSET((char *)&pAC
->Pnmi
.Port
[PhysPortIndex
].
7405 StatRxLongFrameCts
, 0, sizeof(pAC
->Pnmi
.Port
[
7406 PhysPortIndex
].StatRxLongFrameCts
));
7407 SK_MEMSET((char *)&pAC
->Pnmi
.Port
[PhysPortIndex
].
7408 StatRxFrameTooLongCts
, 0, sizeof(pAC
->Pnmi
.Port
[
7409 PhysPortIndex
].StatRxFrameTooLongCts
));
7410 SK_MEMSET((char *)&pAC
->Pnmi
.Port
[PhysPortIndex
].
7411 StatRxPMaccErr
, 0, sizeof(pAC
->Pnmi
.Port
[
7412 PhysPortIndex
].StatRxPMaccErr
));
7416 * Clear local statistics
7418 SK_MEMSET((char *)&pAC
->Pnmi
.VirtualCounterOffset
, 0,
7419 sizeof(pAC
->Pnmi
.VirtualCounterOffset
));
7420 pAC
->Pnmi
.RlmtChangeCts
= 0;
7421 pAC
->Pnmi
.RlmtChangeTime
= 0;
7422 SK_MEMSET((char *)&pAC
->Pnmi
.RlmtChangeEstimate
.EstValue
[0], 0,
7423 sizeof(pAC
->Pnmi
.RlmtChangeEstimate
.EstValue
));
7424 pAC
->Pnmi
.RlmtChangeEstimate
.EstValueIndex
= 0;
7425 pAC
->Pnmi
.RlmtChangeEstimate
.Estimate
= 0;
7426 pAC
->Pnmi
.Port
[NetIndex
].TxSwQueueMax
= 0;
7427 pAC
->Pnmi
.Port
[NetIndex
].TxRetryCts
= 0;
7428 pAC
->Pnmi
.Port
[NetIndex
].RxIntrCts
= 0;
7429 pAC
->Pnmi
.Port
[NetIndex
].TxIntrCts
= 0;
7430 pAC
->Pnmi
.Port
[NetIndex
].RxNoBufCts
= 0;
7431 pAC
->Pnmi
.Port
[NetIndex
].TxNoBufCts
= 0;
7432 pAC
->Pnmi
.Port
[NetIndex
].TxUsedDescrNo
= 0;
7433 pAC
->Pnmi
.Port
[NetIndex
].RxDeliveredCts
= 0;
7434 pAC
->Pnmi
.Port
[NetIndex
].RxOctetsDeliveredCts
= 0;
7435 pAC
->Pnmi
.Port
[NetIndex
].ErrRecoveryCts
= 0;
7438 /*****************************************************************************
7440 * GetTrapEntry - Get an entry in the trap buffer
7443 * The trap buffer stores various events. A user application somehow
7444 * gets notified that an event occured and retrieves the trap buffer
7445 * contens (or simply polls the buffer). The buffer is organized as
7446 * a ring which stores the newest traps at the beginning. The oldest
7447 * traps are overwritten by the newest ones. Each trap entry has a
7448 * unique number, so that applications may detect new trap entries.
7451 * A pointer to the trap entry
7453 PNMI_STATIC
char* GetTrapEntry(
7454 SK_AC
*pAC
, /* Pointer to adapter context */
7455 SK_U32 TrapId
, /* SNMP ID of the trap */
7456 unsigned int Size
) /* Space needed for trap entry */
7458 unsigned int BufPad
= pAC
->Pnmi
.TrapBufPad
;
7459 unsigned int BufFree
= pAC
->Pnmi
.TrapBufFree
;
7460 unsigned int Beg
= pAC
->Pnmi
.TrapQueueBeg
;
7461 unsigned int End
= pAC
->Pnmi
.TrapQueueEnd
;
7462 char *pBuf
= &pAC
->Pnmi
.TrapBuf
[0];
7464 unsigned int NeededSpace
;
7465 unsigned int EntrySize
;
7470 /* Last byte of entry will get a copy of the entry length */
7474 * Calculate needed buffer space */
7481 NeededSpace
= Beg
+ Size
;
7486 * Check if enough buffer space is provided. Otherwise
7487 * free some entries. Leave one byte space between begin
7488 * and end of buffer to make it possible to detect whether
7489 * the buffer is full or empty
7491 while (BufFree
< NeededSpace
+ 1) {
7495 End
= SK_PNMI_TRAP_QUEUE_LEN
;
7498 EntrySize
= (unsigned int)*((unsigned char *)pBuf
+ End
- 1);
7499 BufFree
+= EntrySize
;
7502 SK_MEMSET(pBuf
+ End
, (char)(-1), EntrySize
);
7504 if (End
== BufPad
) {
7506 SK_MEMSET(pBuf
, (char)(-1), End
);
7515 * Insert new entry as first entry. Newest entries are
7516 * stored at the beginning of the queue.
7521 Beg
= SK_PNMI_TRAP_QUEUE_LEN
- Size
;
7526 BufFree
-= NeededSpace
;
7528 /* Save the current offsets */
7529 pAC
->Pnmi
.TrapQueueBeg
= Beg
;
7530 pAC
->Pnmi
.TrapQueueEnd
= End
;
7531 pAC
->Pnmi
.TrapBufPad
= BufPad
;
7532 pAC
->Pnmi
.TrapBufFree
= BufFree
;
7534 /* Initialize the trap entry */
7535 *(pBuf
+ Beg
+ Size
- 1) = (char)Size
;
7536 *(pBuf
+ Beg
) = (char)Size
;
7537 Val32
= (pAC
->Pnmi
.TrapUnique
) ++;
7538 SK_PNMI_STORE_U32(pBuf
+ Beg
+ 1, Val32
);
7539 SK_PNMI_STORE_U32(pBuf
+ Beg
+ 1 + sizeof(SK_U32
), TrapId
);
7540 Val64
= SK_PNMI_HUNDREDS_SEC(SkOsGetTime(pAC
));
7541 SK_PNMI_STORE_U64(pBuf
+ Beg
+ 1 + 2 * sizeof(SK_U32
), Val64
);
7543 return (pBuf
+ Beg
);
7546 /*****************************************************************************
7548 * CopyTrapQueue - Copies the trap buffer for the TRAP OID
7551 * On a query of the TRAP OID the trap buffer contents will be
7552 * copied continuously to the request buffer, which must be large
7553 * enough. No length check is performed.
7558 PNMI_STATIC
void CopyTrapQueue(
7559 SK_AC
*pAC
, /* Pointer to adapter context */
7560 char *pDstBuf
) /* Buffer to which the queued traps will be copied */
7562 unsigned int BufPad
= pAC
->Pnmi
.TrapBufPad
;
7563 unsigned int Trap
= pAC
->Pnmi
.TrapQueueBeg
;
7564 unsigned int End
= pAC
->Pnmi
.TrapQueueEnd
;
7565 char *pBuf
= &pAC
->Pnmi
.TrapBuf
[0];
7567 unsigned int DstOff
= 0;
7570 while (Trap
!= End
) {
7572 Len
= (unsigned int)*(pBuf
+ Trap
);
7575 * Last byte containing a copy of the length will
7578 *(pDstBuf
+ DstOff
) = (char)(Len
- 1);
7579 SK_MEMCPY(pDstBuf
+ DstOff
+ 1, pBuf
+ Trap
+ 1, Len
- 2);
7583 if (Trap
== SK_PNMI_TRAP_QUEUE_LEN
) {
7590 /*****************************************************************************
7592 * GetTrapQueueLen - Get the length of the trap buffer
7595 * Evaluates the number of currently stored traps and the needed
7596 * buffer size to retrieve them.
7601 PNMI_STATIC
void GetTrapQueueLen(
7602 SK_AC
*pAC
, /* Pointer to adapter context */
7603 unsigned int *pLen
, /* Length in Bytes of all queued traps */
7604 unsigned int *pEntries
) /* Returns number of trapes stored in queue */
7606 unsigned int BufPad
= pAC
->Pnmi
.TrapBufPad
;
7607 unsigned int Trap
= pAC
->Pnmi
.TrapQueueBeg
;
7608 unsigned int End
= pAC
->Pnmi
.TrapQueueEnd
;
7609 char *pBuf
= &pAC
->Pnmi
.TrapBuf
[0];
7611 unsigned int Entries
= 0;
7612 unsigned int TotalLen
= 0;
7615 while (Trap
!= End
) {
7617 Len
= (unsigned int)*(pBuf
+ Trap
);
7618 TotalLen
+= Len
- 1;
7622 if (Trap
== SK_PNMI_TRAP_QUEUE_LEN
) {
7628 *pEntries
= Entries
;
7632 /*****************************************************************************
7634 * QueueSimpleTrap - Store a simple trap to the trap buffer
7637 * A simple trap is a trap with now additional data. It consists
7638 * simply of a trap code.
7643 PNMI_STATIC
void QueueSimpleTrap(
7644 SK_AC
*pAC
, /* Pointer to adapter context */
7645 SK_U32 TrapId
) /* Type of sensor trap */
7647 GetTrapEntry(pAC
, TrapId
, SK_PNMI_TRAP_SIMPLE_LEN
);
7650 /*****************************************************************************
7652 * QueueSensorTrap - Stores a sensor trap in the trap buffer
7655 * Gets an entry in the trap buffer and fills it with sensor related
7661 PNMI_STATIC
void QueueSensorTrap(
7662 SK_AC
*pAC
, /* Pointer to adapter context */
7663 SK_U32 TrapId
, /* Type of sensor trap */
7664 unsigned int SensorIndex
) /* Index of sensor which caused the trap */
7667 unsigned int Offset
;
7668 unsigned int DescrLen
;
7672 /* Get trap buffer entry */
7673 DescrLen
= SK_STRLEN(pAC
->I2c
.SenTable
[SensorIndex
].SenDesc
);
7674 pBuf
= GetTrapEntry(pAC
, TrapId
,
7675 SK_PNMI_TRAP_SENSOR_LEN_BASE
+ DescrLen
);
7676 Offset
= SK_PNMI_TRAP_SIMPLE_LEN
;
7678 /* Store additionally sensor trap related data */
7679 Val32
= OID_SKGE_SENSOR_INDEX
;
7680 SK_PNMI_STORE_U32(pBuf
+ Offset
, Val32
);
7681 *(pBuf
+ Offset
+ 4) = 4;
7682 Val32
= (SK_U32
)SensorIndex
;
7683 SK_PNMI_STORE_U32(pBuf
+ Offset
+ 5, Val32
);
7686 Val32
= (SK_U32
)OID_SKGE_SENSOR_DESCR
;
7687 SK_PNMI_STORE_U32(pBuf
+ Offset
, Val32
);
7688 *(pBuf
+ Offset
+ 4) = (char)DescrLen
;
7689 SK_MEMCPY(pBuf
+ Offset
+ 5, pAC
->I2c
.SenTable
[SensorIndex
].SenDesc
,
7691 Offset
+= DescrLen
+ 5;
7693 Val32
= OID_SKGE_SENSOR_TYPE
;
7694 SK_PNMI_STORE_U32(pBuf
+ Offset
, Val32
);
7695 *(pBuf
+ Offset
+ 4) = 1;
7696 *(pBuf
+ Offset
+ 5) = (char)pAC
->I2c
.SenTable
[SensorIndex
].SenType
;
7699 Val32
= OID_SKGE_SENSOR_VALUE
;
7700 SK_PNMI_STORE_U32(pBuf
+ Offset
, Val32
);
7701 *(pBuf
+ Offset
+ 4) = 4;
7702 Val32
= (SK_U32
)pAC
->I2c
.SenTable
[SensorIndex
].SenValue
;
7703 SK_PNMI_STORE_U32(pBuf
+ Offset
+ 5, Val32
);
7706 /*****************************************************************************
7708 * QueueRlmtNewMacTrap - Store a port switch trap in the trap buffer
7711 * Nothing further to explain.
7716 PNMI_STATIC
void QueueRlmtNewMacTrap(
7717 SK_AC
*pAC
, /* Pointer to adapter context */
7718 unsigned int ActiveMac
) /* Index (0..n) of the currently active port */
7724 pBuf
= GetTrapEntry(pAC
, OID_SKGE_TRAP_RLMT_CHANGE_PORT
,
7725 SK_PNMI_TRAP_RLMT_CHANGE_LEN
);
7727 Val32
= OID_SKGE_RLMT_PORT_ACTIVE
;
7728 SK_PNMI_STORE_U32(pBuf
+ SK_PNMI_TRAP_SIMPLE_LEN
, Val32
);
7729 *(pBuf
+ SK_PNMI_TRAP_SIMPLE_LEN
+ 4) = 1;
7730 *(pBuf
+ SK_PNMI_TRAP_SIMPLE_LEN
+ 5) = (char)ActiveMac
;
7733 /*****************************************************************************
7735 * QueueRlmtPortTrap - Store port related RLMT trap to trap buffer
7738 * Nothing further to explain.
7743 PNMI_STATIC
void QueueRlmtPortTrap(
7744 SK_AC
*pAC
, /* Pointer to adapter context */
7745 SK_U32 TrapId
, /* Type of RLMT port trap */
7746 unsigned int PortIndex
) /* Index of the port, which changed its state */
7752 pBuf
= GetTrapEntry(pAC
, TrapId
, SK_PNMI_TRAP_RLMT_PORT_LEN
);
7754 Val32
= OID_SKGE_RLMT_PORT_INDEX
;
7755 SK_PNMI_STORE_U32(pBuf
+ SK_PNMI_TRAP_SIMPLE_LEN
, Val32
);
7756 *(pBuf
+ SK_PNMI_TRAP_SIMPLE_LEN
+ 4) = 1;
7757 *(pBuf
+ SK_PNMI_TRAP_SIMPLE_LEN
+ 5) = (char)PortIndex
;
7760 /*****************************************************************************
7762 * CopyMac - Copies a MAC address
7765 * Nothing further to explain.
7770 PNMI_STATIC
void CopyMac(
7771 char *pDst
, /* Pointer to destination buffer */
7772 SK_MAC_ADDR
*pMac
) /* Pointer of Source */
7777 for (i
= 0; i
< sizeof(SK_MAC_ADDR
); i
++) {
7779 *(pDst
+ i
) = pMac
->a
[i
];
7783 #ifdef SK_POWER_MGMT
7784 /*****************************************************************************
7786 * PowerManagement - OID handler function of PowerManagement OIDs
7789 * The code is simple. No description necessary.
7792 * SK_PNMI_ERR_OK The request was successfully performed.
7793 * SK_PNMI_ERR_GENERAL A general severe internal error occured.
7794 * SK_PNMI_ERR_TOO_SHORT The passed buffer is too short to contain
7795 * the correct data (e.g. a 32bit value is
7796 * needed, but a 16 bit value was passed).
7797 * SK_PNMI_ERR_UNKNOWN_INST The requested instance of the OID doesn't
7798 * exist (e.g. port instance 3 on a two port
7802 PNMI_STATIC
int PowerManagement(
7803 SK_AC
*pAC
, /* Pointer to adapter context */
7804 SK_IOC IoC
, /* IO context handle */
7805 int Action
, /* Get/PreSet/Set action */
7806 SK_U32 Id
, /* Object ID that is to be processed */
7807 char *pBuf
, /* Buffer to which to mgmt data will be retrieved */
7808 unsigned int *pLen
, /* On call: buffer length. On return: used buffer */
7809 SK_U32 Instance
, /* Instance (1..n) that is to be queried or -1 */
7810 unsigned int TableIndex
, /* Index to the Id table */
7811 SK_U32 NetIndex
) /* NetIndex (0..n), in single net mode allways zero */
7814 SK_U32 RetCode
= SK_PNMI_ERR_GENERAL
;
7817 * Check instance. We only handle single instance variables
7819 if (Instance
!= (SK_U32
)(-1) && Instance
!= 1) {
7822 return (SK_PNMI_ERR_UNKNOWN_INST
);
7829 case OID_PNP_CAPABILITIES
:
7830 if (*pLen
< sizeof(SK_PNP_CAPABILITIES
)) {
7832 *pLen
= sizeof(SK_PNP_CAPABILITIES
);
7833 return (SK_PNMI_ERR_TOO_SHORT
);
7837 case OID_PNP_SET_POWER
:
7838 case OID_PNP_QUERY_POWER
:
7839 if (*pLen
< sizeof(SK_DEVICE_POWER_STATE
))
7841 *pLen
= sizeof(SK_DEVICE_POWER_STATE
);
7842 return (SK_PNMI_ERR_TOO_SHORT
);
7846 case OID_PNP_ADD_WAKE_UP_PATTERN
:
7847 case OID_PNP_REMOVE_WAKE_UP_PATTERN
:
7848 if (*pLen
< sizeof(SK_PM_PACKET_PATTERN
)) {
7850 *pLen
= sizeof(SK_PM_PACKET_PATTERN
);
7851 return (SK_PNMI_ERR_TOO_SHORT
);
7855 case OID_PNP_ENABLE_WAKE_UP
:
7856 if (*pLen
< sizeof(SK_U32
)) {
7858 *pLen
= sizeof(SK_U32
);
7859 return (SK_PNMI_ERR_TOO_SHORT
);
7867 if (Action
== SK_PNMI_GET
) {
7874 case OID_PNP_CAPABILITIES
:
7875 RetCode
= SkPowerQueryPnPCapabilities(pAC
, IoC
, pBuf
, pLen
);
7878 case OID_PNP_QUERY_POWER
:
7879 /* The Windows DDK describes: An OID_PNP_QUERY_POWER requests
7880 the miniport to indicate whether it can transition its NIC
7881 to the low-power state.
7882 A miniport driver must always return NDIS_STATUS_SUCCESS
7883 to a query of OID_PNP_QUERY_POWER. */
7884 *pLen
= sizeof(SK_DEVICE_POWER_STATE
);;
7885 RetCode
= SK_PNMI_ERR_OK
;
7888 /* NDIS handles these OIDs as write-only.
7889 * So in case of get action the buffer with written length = 0
7892 case OID_PNP_SET_POWER
:
7893 case OID_PNP_ADD_WAKE_UP_PATTERN
:
7894 case OID_PNP_REMOVE_WAKE_UP_PATTERN
:
7896 RetCode
= SK_PNMI_ERR_NOT_SUPPORTED
;
7899 case OID_PNP_ENABLE_WAKE_UP
:
7900 RetCode
= SkPowerGetEnableWakeUp(pAC
, IoC
, pBuf
, pLen
);
7904 RetCode
= SK_PNMI_ERR_GENERAL
;
7913 * Perform preset or set
7916 /* POWER module does not support PRESET action */
7917 if (Action
== SK_PNMI_PRESET
) {
7918 return (SK_PNMI_ERR_OK
);
7922 case OID_PNP_SET_POWER
:
7923 RetCode
= SkPowerSetPower(pAC
, IoC
, pBuf
, pLen
);
7926 case OID_PNP_ADD_WAKE_UP_PATTERN
:
7927 RetCode
= SkPowerAddWakeUpPattern(pAC
, IoC
, pBuf
, pLen
);
7930 case OID_PNP_REMOVE_WAKE_UP_PATTERN
:
7931 RetCode
= SkPowerRemoveWakeUpPattern(pAC
, IoC
, pBuf
, pLen
);
7934 case OID_PNP_ENABLE_WAKE_UP
:
7935 RetCode
= SkPowerSetEnableWakeUp(pAC
, IoC
, pBuf
, pLen
);
7939 RetCode
= SK_PNMI_ERR_READ_ONLY
;
7944 #endif /* SK_POWER_MGMT */
7946 #ifdef SK_DIAG_SUPPORT
7947 /*****************************************************************************
7949 * DiagActions - OID handler function of Diagnostic driver
7952 * The code is simple. No description necessary.
7955 * SK_PNMI_ERR_OK The request was successfully performed.
7956 * SK_PNMI_ERR_GENERAL A general severe internal error occured.
7957 * SK_PNMI_ERR_TOO_SHORT The passed buffer is too short to contain
7958 * the correct data (e.g. a 32bit value is
7959 * needed, but a 16 bit value was passed).
7960 * SK_PNMI_ERR_UNKNOWN_INST The requested instance of the OID doesn't
7961 * exist (e.g. port instance 3 on a two port
7965 PNMI_STATIC
int DiagActions(
7966 SK_AC
*pAC
, /* Pointer to adapter context */
7967 SK_IOC IoC
, /* IO context handle */
7968 int Action
, /* GET/PRESET/SET action */
7969 SK_U32 Id
, /* Object ID that is to be processed */
7970 char *pBuf
, /* Buffer used for the management data transfer */
7971 unsigned int *pLen
, /* On call: pBuf buffer length. On return: used buffer */
7972 SK_U32 Instance
, /* Instance (1..n) that is to be queried or -1 */
7973 unsigned int TableIndex
, /* Index to the Id table */
7974 SK_U32 NetIndex
) /* NetIndex (0..n), in single net mode always zero */
7977 SK_U32 RetCode
= SK_PNMI_ERR_GENERAL
;
7980 * Check instance. We only handle single instance variables.
7982 if (Instance
!= (SK_U32
)(-1) && Instance
!= 1) {
7985 return (SK_PNMI_ERR_UNKNOWN_INST
);
7993 case OID_SKGE_DIAG_MODE
:
7994 if (*pLen
< sizeof(SK_U32
)) {
7996 *pLen
= sizeof(SK_U32
);
7997 return (SK_PNMI_ERR_TOO_SHORT
);
8002 SK_ERR_LOG(pAC
, SK_ERRCL_SW
, SK_PNMI_ERR040
, SK_PNMI_ERR040MSG
);
8004 return (SK_PNMI_ERR_GENERAL
);
8007 /* Perform action. */
8010 if (Action
== SK_PNMI_GET
) {
8014 case OID_SKGE_DIAG_MODE
:
8015 SK_PNMI_STORE_U32(pBuf
, pAC
->DiagModeActive
);
8016 *pLen
= sizeof(SK_U32
);
8017 RetCode
= SK_PNMI_ERR_OK
;
8022 RetCode
= SK_PNMI_ERR_GENERAL
;
8029 /* From here SET or PRESET value. */
8031 /* PRESET value is not supported. */
8032 if (Action
== SK_PNMI_PRESET
) {
8033 return (SK_PNMI_ERR_OK
);
8038 case OID_SKGE_DIAG_MODE
:
8040 /* Handle the SET. */
8043 /* Enter the DIAG mode in the driver. */
8045 /* If DiagMode is not active, we can enter it. */
8046 if (!pAC
->DiagModeActive
) {
8048 RetCode
= SkDrvEnterDiagMode(pAC
);
8052 RetCode
= SK_PNMI_ERR_GENERAL
;
8056 /* Leave the DIAG mode in the driver. */
8058 RetCode
= SkDrvLeaveDiagMode(pAC
);
8062 RetCode
= SK_PNMI_ERR_BAD_VALUE
;
8068 RetCode
= SK_PNMI_ERR_GENERAL
;
8071 if (RetCode
== SK_PNMI_ERR_OK
) {
8072 *pLen
= sizeof(SK_U32
);
8080 #endif /* SK_DIAG_SUPPORT */
8082 /*****************************************************************************
8084 * Vct - OID handler function of OIDs
8087 * The code is simple. No description necessary.
8090 * SK_PNMI_ERR_OK The request was performed successfully.
8091 * SK_PNMI_ERR_GENERAL A general severe internal error occured.
8092 * SK_PNMI_ERR_TOO_SHORT The passed buffer is too short to contain
8093 * the correct data (e.g. a 32bit value is
8094 * needed, but a 16 bit value was passed).
8095 * SK_PNMI_ERR_UNKNOWN_INST The requested instance of the OID doesn't
8096 * exist (e.g. port instance 3 on a two port
8098 * SK_PNMI_ERR_READ_ONLY Only the Get action is allowed.
8102 PNMI_STATIC
int Vct(
8103 SK_AC
*pAC
, /* Pointer to adapter context */
8104 SK_IOC IoC
, /* IO context handle */
8105 int Action
, /* GET/PRESET/SET action */
8106 SK_U32 Id
, /* Object ID that is to be processed */
8107 char *pBuf
, /* Buffer used for the management data transfer */
8108 unsigned int *pLen
, /* On call: pBuf buffer length. On return: used buffer */
8109 SK_U32 Instance
, /* Instance (-1,2..n) that is to be queried */
8110 unsigned int TableIndex
, /* Index to the Id table */
8111 SK_U32 NetIndex
) /* NetIndex (0..n), in single net mode always zero */
8114 SK_PNMI_VCT
*pVctBackupData
;
8117 SK_U32 PhysPortIndex
;
8121 SK_U32 RetCode
= SK_PNMI_ERR_GENERAL
;
8127 * Calculate the port indexes from the instance.
8129 PhysPortMax
= pAC
->GIni
.GIMacsFound
;
8130 LogPortMax
= SK_PNMI_PORT_PHYS2LOG(PhysPortMax
);
8132 /* Dual net mode? */
8133 if (pAC
->Pnmi
.DualNetActiveFlag
== SK_TRUE
) {
8137 if ((Instance
!= (SK_U32
) (-1))) {
8138 /* Check instance range. */
8139 if ((Instance
< 2) || (Instance
> LogPortMax
)) {
8141 return (SK_PNMI_ERR_UNKNOWN_INST
);
8144 if (pAC
->Pnmi
.DualNetActiveFlag
== SK_TRUE
) {
8145 PhysPortIndex
= NetIndex
;
8148 PhysPortIndex
= Instance
- 2;
8150 Limit
= PhysPortIndex
+ 1;
8154 * Instance == (SK_U32) (-1), get all Instances of that OID.
8156 * Not implemented yet. May be used in future releases.
8159 Limit
= PhysPortMax
;
8162 pPrt
= &pAC
->GIni
.GP
[PhysPortIndex
];
8163 if (pPrt
->PHWLinkUp
) {
8170 /* Check MAC type */
8171 if (pPrt
->PhyType
!= SK_PHY_MARV_COPPER
) {
8173 return (SK_PNMI_ERR_GENERAL
);
8176 /* Initialize backup data pointer. */
8177 pVctBackupData
= &pAC
->Pnmi
.VctBackup
[PhysPortIndex
];
8179 /* Check action type */
8180 if (Action
== SK_PNMI_GET
) {
8184 case OID_SKGE_VCT_GET
:
8185 if (*pLen
< (Limit
- PhysPortIndex
) * sizeof(SK_PNMI_VCT
)) {
8186 *pLen
= (Limit
- PhysPortIndex
) * sizeof(SK_PNMI_VCT
);
8187 return (SK_PNMI_ERR_TOO_SHORT
);
8191 case OID_SKGE_VCT_STATUS
:
8192 if (*pLen
< (Limit
- PhysPortIndex
) * sizeof(SK_U8
)) {
8193 *pLen
= (Limit
- PhysPortIndex
) * sizeof(SK_U8
);
8194 return (SK_PNMI_ERR_TOO_SHORT
);
8200 return (SK_PNMI_ERR_GENERAL
);
8205 for (; PhysPortIndex
< Limit
; PhysPortIndex
++) {
8208 case OID_SKGE_VCT_GET
:
8209 if ((Link
== SK_FALSE
) &&
8210 (pAC
->Pnmi
.VctStatus
[PhysPortIndex
] & SK_PNMI_VCT_PENDING
)) {
8211 RetCode
= SkGmCableDiagStatus(pAC
, IoC
, PhysPortIndex
, SK_FALSE
);
8213 pAC
->Pnmi
.VctStatus
[PhysPortIndex
] &= ~SK_PNMI_VCT_PENDING
;
8214 pAC
->Pnmi
.VctStatus
[PhysPortIndex
] |=
8215 (SK_PNMI_VCT_NEW_VCT_DATA
| SK_PNMI_VCT_TEST_DONE
);
8217 /* Copy results for later use to PNMI struct. */
8218 for (i
= 0; i
< 4; i
++) {
8219 if (pPrt
->PMdiPairSts
[i
] == SK_PNMI_VCT_NORMAL_CABLE
) {
8220 if ((pPrt
->PMdiPairLen
[i
] > 35) && (pPrt
->PMdiPairLen
[i
] < 0xff)) {
8221 pPrt
->PMdiPairSts
[i
] = SK_PNMI_VCT_IMPEDANCE_MISMATCH
;
8224 if ((pPrt
->PMdiPairLen
[i
] > 35) && (pPrt
->PMdiPairLen
[i
] != 0xff)) {
8225 CableLength
= 1000 * (((175 * pPrt
->PMdiPairLen
[i
]) / 210) - 28);
8230 pVctBackupData
->PMdiPairLen
[i
] = CableLength
;
8231 pVctBackupData
->PMdiPairSts
[i
] = pPrt
->PMdiPairSts
[i
];
8234 Para
.Para32
[0] = PhysPortIndex
;
8235 Para
.Para32
[1] = -1;
8236 SkEventQueue(pAC
, SKGE_DRV
, SK_DRV_PORT_RESET
, Para
);
8237 SkEventDispatcher(pAC
, IoC
);
8240 ; /* VCT test is running. */
8244 /* Get all results. */
8245 CheckVctStatus(pAC
, IoC
, pBuf
, Offset
, PhysPortIndex
);
8246 Offset
+= sizeof(SK_U8
);
8247 *(pBuf
+ Offset
) = pPrt
->PCableLen
;
8248 Offset
+= sizeof(SK_U8
);
8249 for (i
= 0; i
< 4; i
++) {
8250 SK_PNMI_STORE_U32((pBuf
+ Offset
), pVctBackupData
->PMdiPairLen
[i
]);
8251 Offset
+= sizeof(SK_U32
);
8253 for (i
= 0; i
< 4; i
++) {
8254 *(pBuf
+ Offset
) = pVctBackupData
->PMdiPairSts
[i
];
8255 Offset
+= sizeof(SK_U8
);
8258 RetCode
= SK_PNMI_ERR_OK
;
8261 case OID_SKGE_VCT_STATUS
:
8262 CheckVctStatus(pAC
, IoC
, pBuf
, Offset
, PhysPortIndex
);
8263 Offset
+= sizeof(SK_U8
);
8264 RetCode
= SK_PNMI_ERR_OK
;
8269 return (SK_PNMI_ERR_GENERAL
);
8275 } /* if SK_PNMI_GET */
8278 * From here SET or PRESET action. Check if the passed
8279 * buffer length is plausible.
8284 case OID_SKGE_VCT_SET
:
8285 if (*pLen
< (Limit
- PhysPortIndex
) * sizeof(SK_U32
)) {
8286 *pLen
= (Limit
- PhysPortIndex
) * sizeof(SK_U32
);
8287 return (SK_PNMI_ERR_TOO_SHORT
);
8293 return (SK_PNMI_ERR_GENERAL
);
8297 * Perform preset or set.
8300 /* VCT does not support PRESET action. */
8301 if (Action
== SK_PNMI_PRESET
) {
8302 return (SK_PNMI_ERR_OK
);
8306 for (; PhysPortIndex
< Limit
; PhysPortIndex
++) {
8308 case OID_SKGE_VCT_SET
: /* Start VCT test. */
8309 if (Link
== SK_FALSE
) {
8310 SkGeStopPort(pAC
, IoC
, PhysPortIndex
, SK_STOP_ALL
, SK_SOFT_RST
);
8312 RetCode
= SkGmCableDiagStatus(pAC
, IoC
, PhysPortIndex
, SK_TRUE
);
8313 if (RetCode
== 0) { /* RetCode: 0 => Start! */
8314 pAC
->Pnmi
.VctStatus
[PhysPortIndex
] |= SK_PNMI_VCT_PENDING
;
8315 pAC
->Pnmi
.VctStatus
[PhysPortIndex
] &= ~SK_PNMI_VCT_NEW_VCT_DATA
;
8316 pAC
->Pnmi
.VctStatus
[PhysPortIndex
] &= ~SK_PNMI_VCT_LINK
;
8319 * Start VCT timer counter.
8321 SK_MEMSET((char *) &Para
, 0, sizeof(Para
));
8322 Para
.Para32
[0] = PhysPortIndex
;
8323 Para
.Para32
[1] = -1;
8324 SkTimerStart(pAC
, IoC
, &pAC
->Pnmi
.VctTimeout
[PhysPortIndex
].VctTimer
,
8325 4000000, SKGE_PNMI
, SK_PNMI_EVT_VCT_RESET
, Para
);
8326 SK_PNMI_STORE_U32((pBuf
+ Offset
), RetCode
);
8327 RetCode
= SK_PNMI_ERR_OK
;
8329 else { /* RetCode: 2 => Running! */
8330 SK_PNMI_STORE_U32((pBuf
+ Offset
), RetCode
);
8331 RetCode
= SK_PNMI_ERR_OK
;
8334 else { /* RetCode: 4 => Link! */
8336 SK_PNMI_STORE_U32((pBuf
+ Offset
), RetCode
);
8337 RetCode
= SK_PNMI_ERR_OK
;
8339 Offset
+= sizeof(SK_U32
);
8344 return (SK_PNMI_ERR_GENERAL
);
8353 PNMI_STATIC
void CheckVctStatus(
8358 SK_U32 PhysPortIndex
)
8361 SK_PNMI_VCT
*pVctData
;
8364 pPrt
= &pAC
->GIni
.GP
[PhysPortIndex
];
8366 pVctData
= (SK_PNMI_VCT
*) (pBuf
+ Offset
);
8367 pVctData
->VctStatus
= SK_PNMI_VCT_NONE
;
8369 if (!pPrt
->PHWLinkUp
) {
8371 /* Was a VCT test ever made before? */
8372 if (pAC
->Pnmi
.VctStatus
[PhysPortIndex
] & SK_PNMI_VCT_TEST_DONE
) {
8373 if ((pAC
->Pnmi
.VctStatus
[PhysPortIndex
] & SK_PNMI_VCT_LINK
)) {
8374 pVctData
->VctStatus
|= SK_PNMI_VCT_OLD_VCT_DATA
;
8377 pVctData
->VctStatus
|= SK_PNMI_VCT_NEW_VCT_DATA
;
8381 /* Check VCT test status. */
8382 RetCode
= SkGmCableDiagStatus(pAC
,IoC
, PhysPortIndex
, SK_FALSE
);
8383 if (RetCode
== 2) { /* VCT test is running. */
8384 pVctData
->VctStatus
|= SK_PNMI_VCT_RUNNING
;
8386 else { /* VCT data was copied to pAC here. Check PENDING state. */
8387 if (pAC
->Pnmi
.VctStatus
[PhysPortIndex
] & SK_PNMI_VCT_PENDING
) {
8388 pVctData
->VctStatus
|= SK_PNMI_VCT_NEW_VCT_DATA
;
8392 if (pPrt
->PCableLen
!= 0xff) { /* Old DSP value. */
8393 pVctData
->VctStatus
|= SK_PNMI_VCT_OLD_DSP_DATA
;
8398 /* Was a VCT test ever made before? */
8399 if (pAC
->Pnmi
.VctStatus
[PhysPortIndex
] & SK_PNMI_VCT_TEST_DONE
) {
8400 pVctData
->VctStatus
&= ~SK_PNMI_VCT_NEW_VCT_DATA
;
8401 pVctData
->VctStatus
|= SK_PNMI_VCT_OLD_VCT_DATA
;
8404 /* DSP only valid in 100/1000 modes. */
8405 if (pAC
->GIni
.GP
[PhysPortIndex
].PLinkSpeedUsed
!=
8406 SK_LSPEED_STAT_10MBPS
) {
8407 pVctData
->VctStatus
|= SK_PNMI_VCT_NEW_DSP_DATA
;
8410 } /* CheckVctStatus */
8413 /*****************************************************************************
8415 * SkPnmiGenIoctl - Handles new generic PNMI IOCTL, calls the needed
8416 * PNMI function depending on the subcommand and
8417 * returns all data belonging to the complete database
8421 * Looks up the requested subcommand, calls the corresponding handler
8422 * function and passes all required parameters to it.
8423 * The function is called by the driver. It is needed to handle the new
8424 * generic PNMI IOCTL. This IOCTL is given to the driver and contains both
8425 * the OID and a subcommand to decide what kind of request has to be done.
8428 * SK_PNMI_ERR_OK The request was successfully performed
8429 * SK_PNMI_ERR_GENERAL A general severe internal error occured
8430 * SK_PNMI_ERR_TOO_SHORT The passed buffer is too short to take
8432 * SK_PNMI_ERR_UNKNOWN_OID The requested OID is unknown
8433 * SK_PNMI_ERR_UNKNOWN_INST The requested instance of the OID doesn't
8434 * exist (e.g. port instance 3 on a two port
8438 SK_AC
*pAC
, /* Pointer to adapter context struct */
8439 SK_IOC IoC
, /* I/O context */
8440 void *pBuf
, /* Buffer used for the management data transfer */
8441 unsigned int *pLen
, /* Length of buffer */
8442 SK_U32 NetIndex
) /* NetIndex (0..n), in single net mode always zero */
8444 SK_I32 Mode
; /* Store value of subcommand. */
8445 SK_U32 Oid
; /* Store value of OID. */
8446 int ReturnCode
; /* Store return value to show status of PNMI action. */
8447 int HeaderLength
; /* Length of desired action plus OID. */
8449 ReturnCode
= SK_PNMI_ERR_GENERAL
;
8451 SK_MEMCPY(&Mode
, pBuf
, sizeof(SK_I32
));
8452 SK_MEMCPY(&Oid
, (char *) pBuf
+ sizeof(SK_I32
), sizeof(SK_U32
));
8453 HeaderLength
= sizeof(SK_I32
) + sizeof(SK_U32
);
8454 *pLen
= *pLen
- HeaderLength
;
8455 SK_MEMCPY((char *) pBuf
+ sizeof(SK_I32
), (char *) pBuf
+ HeaderLength
, *pLen
);
8458 case SK_GET_SINGLE_VAR
:
8459 ReturnCode
= SkPnmiGetVar(pAC
, IoC
, Oid
,
8460 (char *) pBuf
+ sizeof(SK_I32
), pLen
,
8461 ((SK_U32
) (-1)), NetIndex
);
8462 SK_PNMI_STORE_U32(pBuf
, ReturnCode
);
8463 *pLen
= *pLen
+ sizeof(SK_I32
);
8465 case SK_PRESET_SINGLE_VAR
:
8466 ReturnCode
= SkPnmiPreSetVar(pAC
, IoC
, Oid
,
8467 (char *) pBuf
+ sizeof(SK_I32
), pLen
,
8468 ((SK_U32
) (-1)), NetIndex
);
8469 SK_PNMI_STORE_U32(pBuf
, ReturnCode
);
8470 *pLen
= *pLen
+ sizeof(SK_I32
);
8472 case SK_SET_SINGLE_VAR
:
8473 ReturnCode
= SkPnmiSetVar(pAC
, IoC
, Oid
,
8474 (char *) pBuf
+ sizeof(SK_I32
), pLen
,
8475 ((SK_U32
) (-1)), NetIndex
);
8476 SK_PNMI_STORE_U32(pBuf
, ReturnCode
);
8477 *pLen
= *pLen
+ sizeof(SK_I32
);
8479 case SK_GET_FULL_MIB
:
8480 ReturnCode
= SkPnmiGetStruct(pAC
, IoC
, pBuf
, pLen
, NetIndex
);
8482 case SK_PRESET_FULL_MIB
:
8483 ReturnCode
= SkPnmiPreSetStruct(pAC
, IoC
, pBuf
, pLen
, NetIndex
);
8485 case SK_SET_FULL_MIB
:
8486 ReturnCode
= SkPnmiSetStruct(pAC
, IoC
, pBuf
, pLen
, NetIndex
);
8492 return (ReturnCode
);