📄 dm9isa.cpp
字号:
PU8 pcurr=(PU8)ptrBuffer;
for(;count--;pcurr++)
{
VALIDATE_ADDR_PORT(DM9_MWCMD);
NdisRawWritePortUchar(
m_szCurrentSettings[SID_PORT_BASE_ADDRESS]
+ DM9ISA_DATA_OFFSET, *pcurr);
}
}
break;
case WORD_MODE:
{
PU16 pcurr=(PU16)ptrBuffer;
for(;count--;pcurr++)
{
VALIDATE_ADDR_PORT(DM9_MWCMD);
NdisRawWritePortUshort(
m_szCurrentSettings[SID_PORT_BASE_ADDRESS]
+ DM9ISA_DATA_OFFSET, *pcurr);
}
}
break;
case DWORD_MODE:
{
PU32 pcurr=(PU32)ptrBuffer;
for(;count--;pcurr++)
{
VALIDATE_ADDR_PORT(DM9_MWCMD);
NdisRawWritePortUlong(
m_szCurrentSettings[SID_PORT_BASE_ADDRESS]
+ DM9ISA_DATA_OFFSET, *pcurr);
}
}
break;
default:
break;
} // of switch
#else // !PREEMPTIVE_TX_WRITE
// select port to be read from
VALIDATE_ADDR_PORT(DM9_MWCMD);
switch (m_nIoMode)
{
case BYTE_MODE:
NdisRawWritePortBufferUchar(
m_szCurrentSettings[SID_PORT_BASE_ADDRESS] + DM9ISA_DATA_OFFSET,
pbtBuffer,count);
break;
case WORD_MODE:
NdisRawWritePortBufferUshort(
m_szCurrentSettings[SID_PORT_BASE_ADDRESS] + DM9ISA_DATA_OFFSET,
(PWORD)pbtBuffer,count);
break;
case DWORD_MODE:
NdisRawWritePortBufferUlong(
m_szCurrentSettings[SID_PORT_BASE_ADDRESS] + DM9ISA_DATA_OFFSET,
(PDWORD)pbtBuffer,count);
break;
default:
break;
} // of switch
#endif
//JJ-DBG.CPP
nTxMemoryWrAddr= (((U16)DeviceReadPort(DM9_MDWAH) << 8 ) | (U16)DeviceReadPort(DM9_MDWAL));
if (nTxMemoryWrAddr != nToWrAddr)
//ERROR;
WPrintf(WSTR("[Err TxWrAddr]= ToWrAdr %d, ChipWrAdr %d"), nToWrAddr, nTxMemoryWrAddr); // "\r\n"
#if 0
else
WPrintf(WSTR("[TxWrAdr OK]= ToWrAdr %d, ChipWrAdr %d"), nToWrAddr, nTxMemoryWrAddr); // "\r\n"
#endif
LEAVE_CRITICAL_SECTION
return pbtBuffer;
}
/********************************************************************************
*
* Devcie control routines
*
********************************************************************************/
void DM9ISA::DeviceEnableInterrupt(void)
{
// Setting for DM9000 Series
// bits to turn on interrupt latch
// <7> buffer chain enable
// <3> rx overflow count overflow
// <2> rx overflow
// <1> tx completed indication
// <0> rx completed indication
DeviceWritePort(DM9_IMR,((1<<7)|(1<<3)|(1<<2)|(1<<1)|(1<<0)));
}
void DM9ISA::DeviceDisableInterrupt(void)
{
// <7> buffer chain enable
DeviceWritePort(DM9_IMR,(1<<7));
}
void DM9ISA::DeviceEnableReceive(void)
{
// RX enable RXCR<0>
if(m_szCurrentSettings[SID_OP_MODE] & MAKE_MASK(0)) return;
m_szCurrentSettings[SID_OP_MODE] |= MAKE_MASK(0);
_PSTR(_T("--------------------------------------\r\n"));
_PSTR(_T("Func=DM9ISA::DeviceEnableReceive(void)\r\n"));
_RPT_WREG(RN_RXCR, DM9_RXCR, m_szCurrentSettings[SID_OP_MODE]);
DeviceWritePort(DM9_RXCR, m_szCurrentSettings[SID_OP_MODE]);
_PSTR(_T("--------------------------------------\r\n"));
}
void DM9ISA::DeviceDisableReceive(void)
{
// RX enable RXCR<0>
if(!(m_szCurrentSettings[SID_OP_MODE] & MAKE_MASK(0))) return;
m_szCurrentSettings[SID_OP_MODE] &= ~MAKE_MASK(0);
_PSTR(_T("--------------------------------------\r\n"));
_PSTR(_T("Func=DM9ISA::DeviceDisableReceive(void)\r\n"));
_RPT_WREG(RN_RXCR, DM9_RXCR, m_szCurrentSettings[SID_OP_MODE]);
DeviceWritePort(DM9_RXCR, m_szCurrentSettings[SID_OP_MODE]);
_PSTR(_T("--------------------------------------\r\n"));
}
U32 DM9ISA::DeviceGetInterruptStatus(void)
{
U32 intstat;
// mask for bits
// <3> rx overflow count overflow
// <2> rx overflowf
// <1> tx completed indication
// <0> rx completed indication
#if 1
//if (!m_JJ_PrintMessage_control) // JJ(+)
// DEBUG_PRINTF(TEXT("[DM9ISA]DeviceGetInterruptStatus: - \r\n"));
#endif
intstat= DeviceReadPort(DM9_ISR);
DeviceWritePort(DM9_ISR, intstat);
return intstat; //return xxx & MAKE_MASK4(3,2,1,0);
}
U32 DM9ISA::DeviceSetInterruptStatus(
U32 uValue)
{
return DeviceWritePort(DM9_ISR,uValue);
}
U32 DM9ISA::DeviceGetReceiveStatus(void)
{
// DEBUG_PRINTF(TEXT("nTxPendings=%d, %d"),
// m_nTxPendings, m_pUpper->m_objTxQueue.Size());
//if (!m_JJ_PrintMessage_control)
// DEBUG_PRINTF(TEXT("[DM9ISA]DeviceGetReceiveStatus: TxPendings=%d, QueueSize=%d\r\n"), m_nTxPendings, m_pUpper->GetQueueSize());
U32 cr;
cr = DeviceReadPort(DM9_ROCR);
return ((cr>>7)&1)<<31 | (cr&0x7F);
}
//BOOL DM9ISA::DeviceCheckForHang(void)
//{
//}
void DM9ISA::DbgDump(DWORD dwPort)
{
U16 nDB;
nDB= (WORD) DeviceReadPort(dwPort);
DEBUG_PRINTF(_T(" ReadReg %02XH: BYTE: 0x%02X\r\n"), dwPort, nDB);
}
void DM9ISA::DbgDumpDBL(DWORD dwPortH, DWORD dwPortL)
{
DEBUG_PRINTF(_T("ReadReg %02XH,%02XH: "), dwPortH, dwPortL);
U16 nDB= (WORD) DeviceReadPort(dwPortH);
DEBUG_PRINTF(_T("0x%02X"), nDB);
nDB= (WORD) DeviceReadPort(dwPortL);
DEBUG_PRINTF(_T("%02X\r\n"), nDB);
}
void DM9ISA::DbgDumpChip(void)
{
U16 val= (WORD) DeviceReadPort(DM9_CHIPREV);
if (val <0x10) WPrintf(_T("DM9000E"));
else if (val <0x1A) WPrintf(_T("DM9000A"));
else WPrintf(_T("DM9000B"));
//_DEBUG_PRINTF(_T("\r\n"));
}
void DM9ISA::DbgDUMP_REGs(TCHAR *CFN)
{
DEBUG_PRINTF(_T(" =======================\r\n"));
//DEBUG_PRINTF(_T(" DbgDUMP_REGs: "));
//DEBUG_PRINTF(CFN);
//DEBUG_PRINTF(_T("\r\n"));
//DEBUG_PRINTF(_T(" ----------------------------------------------\r\n"));
//DEBUG_PRINTF(_T(" Vender ID: ")); DbgDumpDBL(DM9_VIDH, DM9_VIDL);
//DEBUG_PRINTF(_T(" Prduct ID: ")); DbgDumpDBL(DM9_PIDH, DM9_PIDL);
DEBUG_PRINTF(_T(" %s: "), CFN); DbgDumpChip(); WNextLine();
DEBUG_PRINTF(_T(" -----------------------\r\n"));
DbgDump(DM9_NCR); //0
DbgDump(DM9_NSR); //1
/*
DbgDump(_DM9_TXCR); //2
DbgDump(DM9_TXSR1); //3
DbgDump(DM9_TXSR2); //4
DbgDump(_DM9_RXCR); //5
DbgDump(DM9_RXSR); //6
DbgDump(0x40);
DbgDump(0x41);
DbgDump(DM9_ISR);
*/
DbgDump(DM9_IMR);
}
void DM9ISA::DeviceStart(void)
{
#ifdef IMPL_FLOW_CONTROL
U32 val;
U16 nDB;
// set PHY supports flow control
DeviceWritePhy(0, MIIADDR_ANAR, DeviceReadPhy(0,MIIADDR_ANAR)|bMII_ANAR_FCS); // 4, ANAR.10(=set)
// check full-duplex mode or not<3>
val = DeviceReadPort(DM9_NCR);
if( val & MAKE_MASK(3)) /* full duplex mode */
{
/* full duplex mode */
val = DeviceReadPort(DM9_PAUSETH);
DeviceWritePort(DM9_PAUSETH,(U8)val);
// enable flow control<0>
// enable pause packet<5>
DeviceWritePort(DM9_FCR,MAKE_MASK2(5,0)); // DeviceWritePort(DM9_FLOW,MAKE_MASK2(5,0)); // DM9000
// DM9013, rename DM9_FLOW to DM9_FCR
}
else /* non full duplex mode */
{
/* non full duplex mode */
val = DeviceReadPort(DM9_BACKTH);
DeviceWritePort(DM9_BACKTH,(U8)val);
// enable back pressure<half dumplex mode)<4,3>
DeviceWritePort(DM9_FCR,MAKE_MASK2(4,3)); // DeviceWritePort(DM9_FLOW,MAKE_MASK2(4,3)); // DM9000
// DM9013, rename DM9_FLOW to DM9_FCR
}
#endif
//
//(+)20080124 By Joseph
/*
DEBUG_PRINTF(_T("JJ_Reload EEPROM()\r\n"));
//nDB= (WORD) DeviceReadPort(DM9_EPCNTL);
//DeviceWritePort(DM9_EPCNTL,(U32)nDB|0x20);
DeviceWritePort(DM9_EPCNTL,(U32)0x20);
NdisStallExecution(2); // 2us
DeviceWritePort(DM9_EPCNTL,(U32)0x00);
//DeviceWritePort(DM9_EPCNTL,(U32)nDB&0xdf); //0xdf
NdisStallExecution(2); // 2us
*/
DEBUG_PRINTF(_T("----------------------------------------------\r\n"));
nDB= (WORD) DeviceReadPort(DM9_INT_PC);
DEBUG_PRINTF(_T("ReadReg %02XH: BYTE: 0x%02X\r\n"), DM9_INT_PC, nDB);
DEBUG_PRINTF(_T("==============================================\r\n"));
//(-)20080124 By Joseph
//
// enable interrupt
DeviceEnableInterrupt();
_PSTR(_T("--------------------------------------\r\n"));
_PSTR(_T("Func=DM9ISA::DeviceStart(void)\r\n"));
_RPT_WREG(RN_RXCR, DM9_RXCR, m_szCurrentSettings[SID_OP_MODE]);
DeviceWritePort(DM9_RXCR, m_szCurrentSettings[SID_OP_MODE]);
_PSTR(_T("--------------------------------------\r\n"));
//Ke.DeviceCheckLink();
}
void DM9ISA::DeviceReset(void)
{
// announce shutdown
m_fShutdown = TRUE;
// wait until all activities are fi.
m_mutexRxValidate.Lock();
m_mutexTxValidate.Lock();
CException *pexp;
TRY
{
InitialHardware(++m_nResetCounts);
_PSTR(_T("DeviceReset: DeviceOnSetupFilter(0) \r\n"));
DeviceOnSetupFilter(0);
FI;
}
CATCH(pexp){
// nothing to do
CLEAN(pexp);
} // of catch
// dequeue for all objects in waiting and standby queue
PCQUEUE_GEN_HEADER pcurr;
for(;(pcurr=m_TQWaiting.Dequeue());)
DeviceSendCompleted(pcurr);
for(;(pcurr=m_TQStandby.Dequeue());)
DeviceSendCompleted(pcurr);
m_mutexRxValidate.Release();
m_mutexTxValidate.Release();
m_fShutdown = FALSE;
}
void DM9ISA::InitialChip(void)
{
}
int DM9ISA::LnkStat_GetLinkStatus(void)
{
int linkStatus= NETLINKSTATUS_NONE;
#if 1
U32 ncr, nsr;
WORD wData;
ncr= DeviceReadPort(DM9_NCR); //NetReadReg(pNic, REGINDEX_NCR);
nsr= DeviceReadPort(DM9_NSR); //NetReadReg(pNic, REGINDEX_NSR);
wData= DeviceReadPhy(0, MIIADDR_SPSTAT); // 17,
linkStatus =DEV_LinkStatus(ncr, nsr);
_PSTR_RELX(_T("[9ISA: LinkAuto: NCNSPhy17:%02X,%02X,%04X]---------------------[%s]\r\n"),
ncr,
nsr,
wData,
SpeedNameTbl[linkStatus]);
#endif
return(linkStatus);
}
void DM9ISA::InitialHardware(int nResetCounts)
//------------------------------------------------
// Reset activities
// 1. Abort all current tx and rx.
// 2. Cleanup waiting and standby queues.
// 3. Re-init tx and rx descriptors.
// 4. Softreset MAC, PHY and set registers angain.
//------------------------------------------------
{
U32 val;
SETFNAME("DM9ISA::InitialHardware()");
FUNCTION_ENTER_MSG();
WNextLine();
m_uLastAddressPort = (U32)-1; // reset member varialbes
//[0. Initial Chip for each driver]
NdisMSleep(mSec5); // 5 ms [;must > 3 ms, refer to data sheet, 10.3.3 T4(Min.)= 3 ms ]
//[0. Initial Chip Misc.]
InitialChip();
//[0. activate internal phy, set GPIO 0 to be output]
DeviceWritePort(DM9_GPCR, (1<<0)); //_RPT_WREG(RN_GPCR, DM9_GPCR, (1<<0));
NdisStallExecution(1); // 1 us
#if 1
//[1. Power on the Internal PHY] (before PHY Reset)
//[MAC REG. _0x1F <- 0x01 ;PHY-OFF and delay 0.5 msec]
//[MAC REG. _0x1F <- 0x00 ;PHY-ON and delay 2 msec]
DeviceWritePort(0x1f, 0x01); //DM9_GPR
NdisStallExecution(1); // 1 us
DeviceWritePort(0x1f, 0x00); //DM9_GPR
NdisStallExecution(20); // 20 us
#endif
//LinkState_Get_BMSR(1);
//LinkState_Get_DSCSR(_T("Chk-Default-DBG-PHYReg17"), 17);
//LinkState_Get_SCFG(_T("Chk-Default-DBG-PHYReg20"), 20);
//[2-1. software reset the device-PHY ;and delay 6 msec]
DeviceWritePhy(0, 0, 0x8000);
NdisMSleep(mSec6); // 6 ms
//LinkState_Get_BMSR(1);
//LinkState_Get_DSCSR(_T("Chk-Rst-DBG-PHYReg17"), 17);
//LinkState_Get_SCFG(_T("Chk-Rst-DBG-PHYReg20"), 20);
//[2-2. Software Reset]
//[software reset the device-MAC ;and delay 20 usec] (Twice)
DeviceWritePort(DM9_NCR, 0x03); NdisMSleep(20); // 20 us
DeviceWritePort(DM9_NCR, 0x00);
DeviceWritePort(DM9_NCR, 0x03); NdisMSleep(20); // 20 us
DeviceWritePort(DM9_NCR, 0x00);
// v3.2.x
// [read the H/W IO Mode]
// ISR<7:6> == x1, dword ; 32-bit
// ISR<7:6> == 0x, word ; 16-bit
// ISR<7:6> == 10, byte mode ; 8-bit
val = DeviceReadPort(DM9_ISR); //_RPT_RREG(RN_ISR, DM9_ISR, val); // ref: DbgDump();
if(val & MAKE_MASK(6)){
m_nIoMode = DWORD_MODE;
m_nIoMaxPad = 3;
WPrintf(_T(" IOMODE: 32-bit mode \r\n"));
}
else if(!(val & MAKE_MASK(7))){
m_nIoMode = WORD_MODE; // 16-bit mode
m_nIoMaxPad = 1;
WPrintf(_T(" IOMODE: 16-bit mode \r\n"));
}
else{
m_nIoMode = BYTE_MODE; // 8-bit mode
m_nIoMaxPad = 0;
WPrintf(_T(" IOMODE: 8-bit mode \r\n"));
}
// v3.2.9
val= DeviceReadPort(DM9_CHIPREV);
m_nMaxTxPending= (val>= 0x10)?2:1; // if DM9000E, RESULT is 1
m_nTxPendings = 0;
if (m_nIoMode == DWORD_MODE){
WPrintf(_T(" IOMODE: 32-bit mode (MaxTx %d):REG2C=%02XH\r\n"), m_nMaxTxPending, val);
}
if (m_nIoMode == WORD_MODE){
WPrintf(_T(" IOMODE: 16-bit mode (MaxTx %d):REG2C=%02XH\r\n"), m_nMaxTxPending, val);
}
if (m_nIoMode == BYTE_MODE){
WPrintf(_T(" IOMODE: 8-bit mode (MaxTx %d):REG2C=%02XH\r\n"), m_nMaxTxPending, val);
}
//[3.]
//[clear MAC register status bits ;WAKEST/TX2END/TX1END (each Clear by read or write 1)]
DeviceWritePort(DM9_NSR, 0x2C); //_RPT_WREG(RN_NSR, DM9_NSR, 0x2C);
//[4. Enable pointer auto-return for Tx & Rx FIFO]
//[Enable memory chain]
DeviceWritePort(DM9_IMR, (1<<7)); //_RPT_WREG(RN_IMR, DM9_IMR, (1<<7));
//[5.]
//[Clear MAC register status bits]
DeviceWritePort(DM9_ISR, 0x3f); //_RPT_WREG(RN_ISR, DM9_ISR, 0x3f);
//[6.]
//[activate internal phy, set GPIO 0 to be output]
DeviceWritePort(DM9_GPCR, (1<<0)); //_RPT_WREG(RN_GPCR, DM9_GPCR, (1<<0));
DEBUG_PRINTF(TEXT("RPT_InitHW: CNT: %d (;Cold Start= 0) \r\n"), nResetCounts);
if(nResetCounts) return;
//
// PHY-Down-On Before A.N. as check-4-hang does!
//
DeviceWritePort(0x1f, 0x01); //DM9_GPR
NdisMSleep(mSec5); // 5 ms
DeviceWritePort(0x1f, 0x00); //DM9_GPR
NdisMSleep(mSec10); // 10 ms
WNextLine();
m_CHIPMsgCtrl= FALSE; // TO BE FALSE
WPrintf(_T("[#]\r\n"));
WPrintf(_T("[#]\r\n"));
WPrintf(_T("[#]\r\n"));
WPrintf(_T("[#]\r\n"));
WPrintf(_T("[#]\r\n"));
WNextLine();
#ifdef IMPL_TST_FORCE_100H
DeviceWritePhy(0, 0, PARAM_100H/*PARAM_10H*/);
//...,m ,. m,. sdvm, wv..
#else
DeviceWritePhy(0, 0, DEV_LSMode(LINKSPEED_AUTO)); // -OP_SetLinkMode [To be explicity!]
//0x3300,0x1200
#endif
NdisMSleep(mSec5); // 5 ms
#if 1
// REG MIIADDR_SCFG.4= 20.4
m_auto_mdix_flgb= !(DeviceReadPhy(0, MIIADDR_SCFG)&MAKE_MASK1(4)); // MAKE_MASK1(4)==0x0010
//if (m_nMaxTxPending==1) m_auto_mdix_flgb= FALSE; //DM9000E
/* MYLinkProcess= */
ISA_LinkUp();
#if 1
m_n4HangCounts= 3; // Trick! Especial for DM9003 that not succeed here, but 4Hang DIRECT succesed!
#else
/* MYLinkProcess= */
if (MYLinkProcess) // Trick!
m_n4HangCounts= 1; // to show -> OP_ShowLinkMode() in check 4 hang!
#endif
#else
//[#ifdef IMPL_FIBER_MODE] - Test Fiber Mode (Work on 2008.03.07)
/* Fiber mode or Control DM8606*/
/* Control DM8606 -{100M Full,Scrambler and descrambler func. bypassed}*/
_T(" [Force 100M Full-Scram/Descram ByPass-] \r\n"
.._DeviceWritePhy(0, 0, 0x2100);
.._LnkStat_WaitLinkUp(_T("Wait_LinkUp"), ..
..DeviceWritePhy(0, MIIADDR_DSCR, MAKE_MASK1(14)); //16.14: DSCR.14, set= Scrambler and descrambler function bypassed.
.._LnkStat_WaitLinkUp(_T("Wait_LinkUp"), ..
..
⌨️ 快捷键说明
复制代码
Ctrl + C
搜索代码
Ctrl + F
全屏模式
F11
切换主题
Ctrl + Shift + D
显示快捷键
?
增大字号
Ctrl + =
减小字号
Ctrl + -