From 5ad887fa8e875231d72a27c474b10241a5818bf1 Mon Sep 17 00:00:00 2001 From: Stephen Hemminger Date: Sat, 15 Sep 2007 19:35:14 -0400 Subject: sk98lin: resurrect driver This reverts commit e1abecc48938fbe1966ea6e78267fc673fa59295. The driver works on some hardware that skge doesn't handle yet. Signed-off-by: Stephen Hemminger Signed-off-by: Jeff Garzik --- drivers/net/sk98lin/skdim.c | 742 ++++++++++++++++++++++++++++++++++++++++++++ 1 file changed, 742 insertions(+) create mode 100644 drivers/net/sk98lin/skdim.c (limited to 'drivers/net/sk98lin/skdim.c') diff --git a/drivers/net/sk98lin/skdim.c b/drivers/net/sk98lin/skdim.c new file mode 100644 index 00000000000..37ce03fb8de --- /dev/null +++ b/drivers/net/sk98lin/skdim.c @@ -0,0 +1,742 @@ +/****************************************************************************** + * + * Name: skdim.c + * Project: GEnesis, PCI Gigabit Ethernet Adapter + * Version: $Revision: 1.5 $ + * Date: $Date: 2003/11/28 12:55:40 $ + * Purpose: All functions to maintain interrupt moderation + * + ******************************************************************************/ + +/****************************************************************************** + * + * (C)Copyright 1998-2002 SysKonnect GmbH. + * (C)Copyright 2002-2003 Marvell. + * + * This program is free software; you can redistribute it and/or modify + * it under the terms of the GNU General Public License as published by + * the Free Software Foundation; either version 2 of the License, or + * (at your option) any later version. + * + * The information in this file is provided "AS IS" without warranty. + * + ******************************************************************************/ + +/****************************************************************************** + * + * Description: + * + * This module is intended to manage the dynamic interrupt moderation on both + * GEnesis and Yukon adapters. + * + * Include File Hierarchy: + * + * "skdrv1st.h" + * "skdrv2nd.h" + * + ******************************************************************************/ + +#ifndef lint +static const char SysKonnectFileId[] = + "@(#) $Id: skdim.c,v 1.5 2003/11/28 12:55:40 rroesler Exp $ (C) SysKonnect."; +#endif + +#define __SKADDR_C + +#ifdef __cplusplus +#error C++ is not yet supported. +extern "C" { +#endif + +/******************************************************************************* +** +** Includes +** +*******************************************************************************/ + +#ifndef __INC_SKDRV1ST_H +#include "h/skdrv1st.h" +#endif + +#ifndef __INC_SKDRV2ND_H +#include "h/skdrv2nd.h" +#endif + +#include + +/******************************************************************************* +** +** Defines +** +*******************************************************************************/ + +/******************************************************************************* +** +** Typedefs +** +*******************************************************************************/ + +/******************************************************************************* +** +** Local function prototypes +** +*******************************************************************************/ + +static unsigned int GetCurrentSystemLoad(SK_AC *pAC); +static SK_U64 GetIsrCalls(SK_AC *pAC); +static SK_BOOL IsIntModEnabled(SK_AC *pAC); +static void SetCurrIntCtr(SK_AC *pAC); +static void EnableIntMod(SK_AC *pAC); +static void DisableIntMod(SK_AC *pAC); +static void ResizeDimTimerDuration(SK_AC *pAC); +static void DisplaySelectedModerationType(SK_AC *pAC); +static void DisplaySelectedModerationMask(SK_AC *pAC); +static void DisplayDescrRatio(SK_AC *pAC); + +/******************************************************************************* +** +** Global variables +** +*******************************************************************************/ + +/******************************************************************************* +** +** Local variables +** +*******************************************************************************/ + +/******************************************************************************* +** +** Global functions +** +*******************************************************************************/ + +/******************************************************************************* +** Function : SkDimModerate +** Description : Called in every ISR to check if moderation is to be applied +** or not for the current number of interrupts +** Programmer : Ralph Roesler +** Last Modified: 22-mar-03 +** Returns : void (!) +** Notes : - +*******************************************************************************/ + +void +SkDimModerate(SK_AC *pAC) { + unsigned int CurrSysLoad = 0; /* expressed in percent */ + unsigned int LoadIncrease = 0; /* expressed in percent */ + SK_U64 ThresholdInts = 0; + SK_U64 IsrCallsPerSec = 0; + +#define M_DIMINFO pAC->DynIrqModInfo + + if (!IsIntModEnabled(pAC)) { + if (M_DIMINFO.IntModTypeSelect == C_INT_MOD_DYNAMIC) { + CurrSysLoad = GetCurrentSystemLoad(pAC); + if (CurrSysLoad > 75) { + /* + ** More than 75% total system load! Enable the moderation + ** to shield the system against too many interrupts. + */ + EnableIntMod(pAC); + } else if (CurrSysLoad > M_DIMINFO.PrevSysLoad) { + LoadIncrease = (CurrSysLoad - M_DIMINFO.PrevSysLoad); + if (LoadIncrease > ((M_DIMINFO.PrevSysLoad * + C_INT_MOD_ENABLE_PERCENTAGE) / 100)) { + if (CurrSysLoad > 10) { + /* + ** More than 50% increase with respect to the + ** previous load of the system. Most likely this + ** is due to our ISR-proc... + */ + EnableIntMod(pAC); + } + } + } else { + /* + ** Neither too much system load at all nor too much increase + ** with respect to the previous system load. Hence, we can leave + ** the ISR-handling like it is without enabling moderation. + */ + } + M_DIMINFO.PrevSysLoad = CurrSysLoad; + } + } else { + if (M_DIMINFO.IntModTypeSelect == C_INT_MOD_DYNAMIC) { + ThresholdInts = ((M_DIMINFO.MaxModIntsPerSec * + C_INT_MOD_DISABLE_PERCENTAGE) / 100); + IsrCallsPerSec = GetIsrCalls(pAC); + if (IsrCallsPerSec <= ThresholdInts) { + /* + ** The number of interrupts within the last second is + ** lower than the disable_percentage of the desried + ** maxrate. Therefore we can disable the moderation. + */ + DisableIntMod(pAC); + M_DIMINFO.MaxModIntsPerSec = + (M_DIMINFO.MaxModIntsPerSecUpperLimit + + M_DIMINFO.MaxModIntsPerSecLowerLimit) / 2; + } else { + /* + ** The number of interrupts per sec is the same as expected. + ** Evalulate the descriptor-ratio. If it has changed, a resize + ** in the moderation timer might be useful + */ + if (M_DIMINFO.AutoSizing) { + ResizeDimTimerDuration(pAC); + } + } + } + } + + /* + ** Some information to the log... + */ + if (M_DIMINFO.DisplayStats) { + DisplaySelectedModerationType(pAC); + DisplaySelectedModerationMask(pAC); + DisplayDescrRatio(pAC); + } + + M_DIMINFO.NbrProcessedDescr = 0; + SetCurrIntCtr(pAC); +} + +/******************************************************************************* +** Function : SkDimStartModerationTimer +** Description : Starts the audit-timer for the dynamic interrupt moderation +** Programmer : Ralph Roesler +** Last Modified: 22-mar-03 +** Returns : void (!) +** Notes : - +*******************************************************************************/ + +void +SkDimStartModerationTimer(SK_AC *pAC) { + SK_EVPARA EventParam; /* Event struct for timer event */ + + SK_MEMSET((char *) &EventParam, 0, sizeof(EventParam)); + EventParam.Para32[0] = SK_DRV_MODERATION_TIMER; + SkTimerStart(pAC, pAC->IoBase, &pAC->DynIrqModInfo.ModTimer, + SK_DRV_MODERATION_TIMER_LENGTH, + SKGE_DRV, SK_DRV_TIMER, EventParam); +} + +/******************************************************************************* +** Function : SkDimEnableModerationIfNeeded +** Description : Either enables or disables moderation +** Programmer : Ralph Roesler +** Last Modified: 22-mar-03 +** Returns : void (!) +** Notes : This function is called when a particular adapter is opened +** There is no Disable function, because when all interrupts +** might be disable, the moderation timer has no meaning at all +******************************************************************************/ + +void +SkDimEnableModerationIfNeeded(SK_AC *pAC) { + + if (M_DIMINFO.IntModTypeSelect == C_INT_MOD_STATIC) { + EnableIntMod(pAC); /* notification print in this function */ + } else if (M_DIMINFO.IntModTypeSelect == C_INT_MOD_DYNAMIC) { + SkDimStartModerationTimer(pAC); + if (M_DIMINFO.DisplayStats) { + printk("Dynamic moderation has been enabled\n"); + } + } else { + if (M_DIMINFO.DisplayStats) { + printk("No moderation has been enabled\n"); + } + } +} + +/******************************************************************************* +** Function : SkDimDisplayModerationSettings +** Description : Displays the current settings regarding interrupt moderation +** Programmer : Ralph Roesler +** Last Modified: 22-mar-03 +** Returns : void (!) +** Notes : - +*******************************************************************************/ + +void +SkDimDisplayModerationSettings(SK_AC *pAC) { + DisplaySelectedModerationType(pAC); + DisplaySelectedModerationMask(pAC); +} + +/******************************************************************************* +** +** Local functions +** +*******************************************************************************/ + +/******************************************************************************* +** Function : GetCurrentSystemLoad +** Description : Retrieves the current system load of the system. This load +** is evaluated for all processors within the system. +** Programmer : Ralph Roesler +** Last Modified: 22-mar-03 +** Returns : unsigned int: load expressed in percentage +** Notes : The possible range being returned is from 0 up to 100. +** Whereas 0 means 'no load at all' and 100 'system fully loaded' +** It is impossible to determine what actually causes the system +** to be in 100%, but maybe that is due to too much interrupts. +*******************************************************************************/ + +static unsigned int +GetCurrentSystemLoad(SK_AC *pAC) { + unsigned long jif = jiffies; + unsigned int UserTime = 0; + unsigned int SystemTime = 0; + unsigned int NiceTime = 0; + unsigned int IdleTime = 0; + unsigned int TotalTime = 0; + unsigned int UsedTime = 0; + unsigned int SystemLoad = 0; + + /* unsigned int NbrCpu = 0; */ + + /* + ** The following lines have been commented out, because + ** from kernel 2.5.44 onwards, the kernel-owned structure + ** + ** struct kernel_stat kstat + ** + ** is not marked as an exported symbol in the file + ** + ** kernel/ksyms.c + ** + ** As a consequence, using this driver as KLM is not possible + ** and any access of the structure kernel_stat via the + ** dedicated macros kstat_cpu(i).cpustat.xxx is to be avoided. + ** + ** The kstat-information might be added again in future + ** versions of the 2.5.xx kernel, but for the time being, + ** number of interrupts will serve as indication how much + ** load we currently have... + ** + ** for (NbrCpu = 0; NbrCpu < num_online_cpus(); NbrCpu++) { + ** UserTime = UserTime + kstat_cpu(NbrCpu).cpustat.user; + ** NiceTime = NiceTime + kstat_cpu(NbrCpu).cpustat.nice; + ** SystemTime = SystemTime + kstat_cpu(NbrCpu).cpustat.system; + ** } + */ + SK_U64 ThresholdInts = 0; + SK_U64 IsrCallsPerSec = 0; + + ThresholdInts = ((M_DIMINFO.MaxModIntsPerSec * + C_INT_MOD_ENABLE_PERCENTAGE) + 100); + IsrCallsPerSec = GetIsrCalls(pAC); + if (IsrCallsPerSec >= ThresholdInts) { + /* + ** We do not know how much the real CPU-load is! + ** Return 80% as a default in order to activate DIM + */ + SystemLoad = 80; + return (SystemLoad); + } + + UsedTime = UserTime + NiceTime + SystemTime; + + IdleTime = jif * num_online_cpus() - UsedTime; + TotalTime = UsedTime + IdleTime; + + SystemLoad = ( 100 * (UsedTime - M_DIMINFO.PrevUsedTime) ) / + (TotalTime - M_DIMINFO.PrevTotalTime); + + if (M_DIMINFO.DisplayStats) { + printk("Current system load is: %u\n", SystemLoad); + } + + M_DIMINFO.PrevTotalTime = TotalTime; + M_DIMINFO.PrevUsedTime = UsedTime; + + return (SystemLoad); +} + +/******************************************************************************* +** Function : GetIsrCalls +** Description : Depending on the selected moderation mask, this function will +** return the number of interrupts handled in the previous time- +** frame. This evaluated number is based on the current number +** of interrupts stored in PNMI-context and the previous stored +** interrupts. +** Programmer : Ralph Roesler +** Last Modified: 23-mar-03 +** Returns : int: the number of interrupts being executed in the last +** timeframe +** Notes : It makes only sense to call this function, when dynamic +** interrupt moderation is applied +*******************************************************************************/ + +static SK_U64 +GetIsrCalls(SK_AC *pAC) { + SK_U64 RxPort0IntDiff = 0; + SK_U64 RxPort1IntDiff = 0; + SK_U64 TxPort0IntDiff = 0; + SK_U64 TxPort1IntDiff = 0; + + if (pAC->DynIrqModInfo.MaskIrqModeration == IRQ_MASK_TX_ONLY) { + if (pAC->GIni.GIMacsFound == 2) { + TxPort1IntDiff = pAC->Pnmi.Port[1].TxIntrCts - + pAC->DynIrqModInfo.PrevPort1TxIntrCts; + } + TxPort0IntDiff = pAC->Pnmi.Port[0].TxIntrCts - + pAC->DynIrqModInfo.PrevPort0TxIntrCts; + } else if (pAC->DynIrqModInfo.MaskIrqModeration == IRQ_MASK_RX_ONLY) { + if (pAC->GIni.GIMacsFound == 2) { + RxPort1IntDiff = pAC->Pnmi.Port[1].RxIntrCts - + pAC->DynIrqModInfo.PrevPort1RxIntrCts; + } + RxPort0IntDiff = pAC->Pnmi.Port[0].RxIntrCts - + pAC->DynIrqModInfo.PrevPort0RxIntrCts; + } else { + if (pAC->GIni.GIMacsFound == 2) { + RxPort1IntDiff = pAC->Pnmi.Port[1].RxIntrCts - + pAC->DynIrqModInfo.PrevPort1RxIntrCts; + TxPort1IntDiff = pAC->Pnmi.Port[1].TxIntrCts - + pAC->DynIrqModInfo.PrevPort1TxIntrCts; + } + RxPort0IntDiff = pAC->Pnmi.Port[0].RxIntrCts - + pAC->DynIrqModInfo.PrevPort0RxIntrCts; + TxPort0IntDiff = pAC->Pnmi.Port[0].TxIntrCts - + pAC->DynIrqModInfo.PrevPort0TxIntrCts; + } + + return (RxPort0IntDiff + RxPort1IntDiff + TxPort0IntDiff + TxPort1IntDiff); +} + +/******************************************************************************* +** Function : GetRxCalls +** Description : This function will return the number of times a receive inter- +** rupt was processed. This is needed to evaluate any resizing +** factor. +** Programmer : Ralph Roesler +** Last Modified: 23-mar-03 +** Returns : SK_U64: the number of RX-ints being processed +** Notes : It makes only sense to call this function, when dynamic +** interrupt moderation is applied +*******************************************************************************/ + +static SK_U64 +GetRxCalls(SK_AC *pAC) { + SK_U64 RxPort0IntDiff = 0; + SK_U64 RxPort1IntDiff = 0; + + if (pAC->GIni.GIMacsFound == 2) { + RxPort1IntDiff = pAC->Pnmi.Port[1].RxIntrCts - + pAC->DynIrqModInfo.PrevPort1RxIntrCts; + } + RxPort0IntDiff = pAC->Pnmi.Port[0].RxIntrCts - + pAC->DynIrqModInfo.PrevPort0RxIntrCts; + + return (RxPort0IntDiff + RxPort1IntDiff); +} + +/******************************************************************************* +** Function : SetCurrIntCtr +** Description : Will store the current number orf occured interrupts in the +** adapter context. This is needed to evaluated the number of +** interrupts within a current timeframe. +** Programmer : Ralph Roesler +** Last Modified: 23-mar-03 +** Returns : void (!) +** Notes : - +*******************************************************************************/ + +static void +SetCurrIntCtr(SK_AC *pAC) { + if (pAC->GIni.GIMacsFound == 2) { + pAC->DynIrqModInfo.PrevPort1RxIntrCts = pAC->Pnmi.Port[1].RxIntrCts; + pAC->DynIrqModInfo.PrevPort1TxIntrCts = pAC->Pnmi.Port[1].TxIntrCts; + } + pAC->DynIrqModInfo.PrevPort0RxIntrCts = pAC->Pnmi.Port[0].RxIntrCts; + pAC->DynIrqModInfo.PrevPort0TxIntrCts = pAC->Pnmi.Port[0].TxIntrCts; +} + +/******************************************************************************* +** Function : IsIntModEnabled() +** Description : Retrieves the current value of the interrupts moderation +** command register. Its content determines whether any +** moderation is running or not. +** Programmer : Ralph Roesler +** Last Modified: 23-mar-03 +** Returns : SK_TRUE : if mod timer running +** SK_FALSE : if no moderation is being performed +** Notes : - +*******************************************************************************/ + +static SK_BOOL +IsIntModEnabled(SK_AC *pAC) { + unsigned long CtrCmd; + + SK_IN32(pAC->IoBase, B2_IRQM_CTRL, &CtrCmd); + if ((CtrCmd & TIM_START) == TIM_START) { + return SK_TRUE; + } else { + return SK_FALSE; + } +} + +/******************************************************************************* +** Function : EnableIntMod() +** Description : Enables the interrupt moderation using the values stored in +** in the pAC->DynIntMod data structure +** Programmer : Ralph Roesler +** Last Modified: 22-mar-03 +** Returns : - +** Notes : - +*******************************************************************************/ + +static void +EnableIntMod(SK_AC *pAC) { + unsigned long ModBase; + + if (pAC->GIni.GIChipId == CHIP_ID_GENESIS) { + ModBase = C_CLK_FREQ_GENESIS / pAC->DynIrqModInfo.MaxModIntsPerSec; + } else { + ModBase = C_CLK_FREQ_YUKON / pAC->DynIrqModInfo.MaxModIntsPerSec; + } + + SK_OUT32(pAC->IoBase, B2_IRQM_INI, ModBase); + SK_OUT32(pAC->IoBase, B2_IRQM_MSK, pAC->DynIrqModInfo.MaskIrqModeration); + SK_OUT32(pAC->IoBase, B2_IRQM_CTRL, TIM_START); + if (M_DIMINFO.DisplayStats) { + printk("Enabled interrupt moderation (%i ints/sec)\n", + M_DIMINFO.MaxModIntsPerSec); + } +} + +/******************************************************************************* +** Function : DisableIntMod() +** Description : Disables the interrupt moderation independent of what inter- +** rupts are running or not +** Programmer : Ralph Roesler +** Last Modified: 23-mar-03 +** Returns : - +** Notes : - +*******************************************************************************/ + +static void +DisableIntMod(SK_AC *pAC) { + + SK_OUT32(pAC->IoBase, B2_IRQM_CTRL, TIM_STOP); + if (M_DIMINFO.DisplayStats) { + printk("Disabled interrupt moderation\n"); + } +} + +/******************************************************************************* +** Function : ResizeDimTimerDuration(); +** Description : Checks the current used descriptor ratio and resizes the +** duration timer (longer/smaller) if possible. +** Programmer : Ralph Roesler +** Last Modified: 23-mar-03 +** Returns : - +** Notes : There are both maximum and minimum timer duration value. +** This function assumes that interrupt moderation is already +** enabled! +*******************************************************************************/ + +static void +ResizeDimTimerDuration(SK_AC *pAC) { + SK_BOOL IncreaseTimerDuration; + int TotalMaxNbrDescr; + int UsedDescrRatio; + int RatioDiffAbs; + int RatioDiffRel; + int NewMaxModIntsPerSec; + int ModAdjValue; + long ModBase; + + /* + ** Check first if we are allowed to perform any modification + */ + if (IsIntModEnabled(pAC)) { + if (M_DIMINFO.IntModTypeSelect != C_INT_MOD_DYNAMIC) { + return; + } else { + if (M_DIMINFO.ModJustEnabled) { + M_DIMINFO.ModJustEnabled = SK_FALSE; + return; + } + } + } + + /* + ** If we got until here, we have to evaluate the amount of the + ** descriptor ratio change... + */ + TotalMaxNbrDescr = pAC->RxDescrPerRing * GetRxCalls(pAC); + UsedDescrRatio = (M_DIMINFO.NbrProcessedDescr * 100) / TotalMaxNbrDescr; + + if (UsedDescrRatio > M_DIMINFO.PrevUsedDescrRatio) { + RatioDiffAbs = (UsedDescrRatio - M_DIMINFO.PrevUsedDescrRatio); + RatioDiffRel = (RatioDiffAbs * 100) / UsedDescrRatio; + M_DIMINFO.PrevUsedDescrRatio = UsedDescrRatio; + IncreaseTimerDuration = SK_FALSE; /* in other words: DECREASE */ + } else if (UsedDescrRatio < M_DIMINFO.PrevUsedDescrRatio) { + RatioDiffAbs = (M_DIMINFO.PrevUsedDescrRatio - UsedDescrRatio); + RatioDiffRel = (RatioDiffAbs * 100) / M_DIMINFO.PrevUsedDescrRatio; + M_DIMINFO.PrevUsedDescrRatio = UsedDescrRatio; + IncreaseTimerDuration = SK_TRUE; /* in other words: INCREASE */ + } else { + RatioDiffAbs = (M_DIMINFO.PrevUsedDescrRatio - UsedDescrRatio); + RatioDiffRel = (RatioDiffAbs * 100) / M_DIMINFO.PrevUsedDescrRatio; + M_DIMINFO.PrevUsedDescrRatio = UsedDescrRatio; + IncreaseTimerDuration = SK_TRUE; /* in other words: INCREASE */ + } + + /* + ** Now we can determine the change in percent + */ + if ((RatioDiffRel >= 0) && (RatioDiffRel <= 5) ) { + ModAdjValue = 1; /* 1% change - maybe some other value in future */ + } else if ((RatioDiffRel > 5) && (RatioDiffRel <= 10) ) { + ModAdjValue = 1; /* 1% change - maybe some other value in future */ + } else if ((RatioDiffRel > 10) && (RatioDiffRel <= 15) ) { + ModAdjValue = 1; /* 1% change - maybe some other value in future */ + } else { + ModAdjValue = 1; /* 1% change - maybe some other value in future */ + } + + if (IncreaseTimerDuration) { + NewMaxModIntsPerSec = M_DIMINFO.MaxModIntsPerSec + + (M_DIMINFO.MaxModIntsPerSec * ModAdjValue) / 100; + } else { + NewMaxModIntsPerSec = M_DIMINFO.MaxModIntsPerSec - + (M_DIMINFO.MaxModIntsPerSec * ModAdjValue) / 100; + } + + /* + ** Check if we exceed boundaries... + */ + if ( (NewMaxModIntsPerSec > M_DIMINFO.MaxModIntsPerSecUpperLimit) || + (NewMaxModIntsPerSec < M_DIMINFO.MaxModIntsPerSecLowerLimit)) { + if (M_DIMINFO.DisplayStats) { + printk("Cannot change ModTim from %i to %i ints/sec\n", + M_DIMINFO.MaxModIntsPerSec, NewMaxModIntsPerSec); + } + return; + } else { + if (M_DIMINFO.DisplayStats) { + printk("Resized ModTim from %i to %i ints/sec\n", + M_DIMINFO.MaxModIntsPerSec, NewMaxModIntsPerSec); + } + } + + M_DIMINFO.MaxModIntsPerSec = NewMaxModIntsPerSec; + + if (pAC->GIni.GIChipId == CHIP_ID_GENESIS) { + ModBase = C_CLK_FREQ_GENESIS / pAC->DynIrqModInfo.MaxModIntsPerSec; + } else { + ModBase = C_CLK_FREQ_YUKON / pAC->DynIrqModInfo.MaxModIntsPerSec; + } + + /* + ** We do not need to touch any other registers + */ + SK_OUT32(pAC->IoBase, B2_IRQM_INI, ModBase); +} + +/******************************************************************************* +** Function : DisplaySelectedModerationType() +** Description : Displays what type of moderation we have +** Programmer : Ralph Roesler +** Last Modified: 23-mar-03 +** Returns : void! +** Notes : - +*******************************************************************************/ + +static void +DisplaySelectedModerationType(SK_AC *pAC) { + + if (pAC->DynIrqModInfo.DisplayStats) { + if (pAC->DynIrqModInfo.IntModTypeSelect == C_INT_MOD_STATIC) { + printk("Static int moderation runs with %i INTS/sec\n", + pAC->DynIrqModInfo.MaxModIntsPerSec); + } else if (pAC->DynIrqModInfo.IntModTypeSelect == C_INT_MOD_DYNAMIC) { + if (IsIntModEnabled(pAC)) { + printk("Dynamic int moderation runs with %i INTS/sec\n", + pAC->DynIrqModInfo.MaxModIntsPerSec); + } else { + printk("Dynamic int moderation currently not applied\n"); + } + } else { + printk("No interrupt moderation selected!\n"); + } + } +} + +/******************************************************************************* +** Function : DisplaySelectedModerationMask() +** Description : Displays what interrupts are moderated +** Programmer : Ralph Roesler +** Last Modified: 23-mar-03 +** Returns : void! +** Notes : - +*******************************************************************************/ + +static void +DisplaySelectedModerationMask(SK_AC *pAC) { + + if (pAC->DynIrqModInfo.DisplayStats) { + if (pAC->DynIrqModInfo.IntModTypeSelect != C_INT_MOD_NONE) { + switch (pAC->DynIrqModInfo.MaskIrqModeration) { + case IRQ_MASK_TX_ONLY: + printk("Only Tx-interrupts are moderated\n"); + break; + case IRQ_MASK_RX_ONLY: + printk("Only Rx-interrupts are moderated\n"); + break; + case IRQ_MASK_SP_ONLY: + printk("Only special-interrupts are moderated\n"); + break; + case IRQ_MASK_TX_RX: + printk("Tx- and Rx-interrupts are moderated\n"); + break; + case IRQ_MASK_SP_RX: + printk("Special- and Rx-interrupts are moderated\n"); + break; + case IRQ_MASK_SP_TX: + printk("Special- and Tx-interrupts are moderated\n"); + break; + case IRQ_MASK_RX_TX_SP: + printk("All Rx-, Tx and special-interrupts are moderated\n"); + break; + default: + printk("Don't know what is moderated\n"); + break; + } + } else { + printk("No specific interrupts masked for moderation\n"); + } + } +} + +/******************************************************************************* +** Function : DisplayDescrRatio +** Description : Like the name states... +** Programmer : Ralph Roesler +** Last Modified: 23-mar-03 +** Returns : void! +** Notes : - +*******************************************************************************/ + +static void +DisplayDescrRatio(SK_AC *pAC) { + int TotalMaxNbrDescr = 0; + + if (pAC->DynIrqModInfo.DisplayStats) { + TotalMaxNbrDescr = pAC->RxDescrPerRing * GetRxCalls(pAC); + printk("Ratio descriptors: %i/%i\n", + M_DIMINFO.NbrProcessedDescr, TotalMaxNbrDescr); + } +} + +/******************************************************************************* +** +** End of file +** +*******************************************************************************/ -- cgit v1.2.3