⭐ 欢迎来到虫虫下载站! | 📦 资源下载 📁 资源专辑 ℹ️ 关于我们
⭐ 虫虫下载站

📄 card.c

📁 Realtek8139小端口网卡驱动程序源代码
💻 C
📖 第 1 页 / 共 5 页
字号:
            NdisRawWritePortUchar(
                Adapter->IoAddr + NIC_RMT_ADDR_LSB,
                LSB(PtrToUlong(XmitBufAddress - 1))
            );

            NdisRawWritePortUchar(Adapter->IoAddr + NIC_RMT_ADDR_MSB,
                                  MSB((PtrToUlong(XmitBufAddress) - 1))
                                 );

// RTL8139 PCMCIA CHANGE START

            //
            //  RTL8139 PCMCIA CHANGE!!!
            //
            //NdisRawWritePortUchar(Adapter->IoAddr + NIC_RMT_COUNT_LSB, 0x1 );
            //NdisRawWritePortUchar(Adapter->IoAddr + NIC_RMT_COUNT_MSB, 0x0 );
            NdisRawWritePortUchar(Adapter->IoAddr + NIC_RMT_COUNT_LSB, 0x2 );
            NdisRawWritePortUchar(Adapter->IoAddr + NIC_RMT_COUNT_MSB, 0x0 );

            //
            // Set direction (Read)
            //

            NdisRawWritePortUchar( Adapter->IoAddr + NIC_COMMAND,
                           CR_START | CR_PAGE0 | CR_DMA_READ );

            //
            //  RTL8139 PCMCIA CHANGE!!!
            //
            //NdisRawReadPortUchar( Adapter->IoAddr + NIC_RACK_NIC, &Tmp1 );
            NdisRawReadPortUshort( Adapter->IoAddr + NIC_RACK_NIC, &TmpShort );
            Tmp1 = LSB(TmpShort);

// RTL8139 PCMCIA CHANGE END

            //
            // Do Write errata as described on pages 1-143 and
            // 1-144 of the 1992 LAN databook
            //

            //
            // Set Count and destination address
            //
            ReadBuffer = XmitBufAddress + ((ULONG_PTR)XmitBufAddress & 1);

            OldAddr = NewAddr = (USHORT)(ReadBuffer);

//          NdisRawWritePortUchar(Adapter->IoAddr + NIC_COMMAND,   // robin
//                                CR_PAGE0                          // robin
//                                );                                // robin
            NdisRawWritePortUchar(Adapter->IoAddr + NIC_RMT_ADDR_LSB,
                                  LSB(PtrToUlong(ReadBuffer))
                                 );
            NdisRawWritePortUchar(Adapter->IoAddr + NIC_RMT_ADDR_MSB,
                                  MSB(PtrToUlong(ReadBuffer))
                                 );
            NdisRawWritePortUchar(Adapter->IoAddr + NIC_RMT_COUNT_LSB, 0x2 );
            NdisRawWritePortUchar(Adapter->IoAddr + NIC_RMT_COUNT_MSB, 0x0 );

            //
            // Set direction (Read)
            //
            NdisRawWritePortUchar(
                           Adapter->IoAddr + NIC_COMMAND,
                           CR_START | CR_PAGE0 | CR_DMA_READ
                           );

            //
            // Read from port
            //
            NdisRawReadPortUshort( Adapter->IoAddr + NIC_RACK_NIC, &TmpShort );

            //
            // Wait for addr to change
            //
            TmpShort = 0xFFFF;

            while (TmpShort != 0) {

                NdisRawReadPortUchar( Adapter->IoAddr + NIC_CRDA_LSB, &Tmp );
                NewAddr = Tmp;
                NdisRawReadPortUchar( Adapter->IoAddr + NIC_CRDA_MSB, &Tmp );
                NewAddr |= (Tmp << 8);

                if (NewAddr != OldAddr) {

                    break;

                }

                NdisStallExecution(1);

                TmpShort--;
            }

            if (NewAddr == OldAddr) {

                NdisWriteErrorLogEntry(
                    Adapter->MiniportAdapterHandle,
                    NDIS_ERROR_CODE_HARDWARE_FAILURE,
                    2,
                    cardCopyDownPacket,
                    (ULONG_PTR)XmitBufAddress
                    );

                return(FALSE);

            }

            //
            // Set Count and destination address
            //
            NdisRawWritePortUchar( Adapter->IoAddr + NIC_RMT_ADDR_LSB,
                               LSB(PtrToUlong(XmitBufAddress - 1)) );

            NdisRawWritePortUchar( Adapter->IoAddr + NIC_RMT_ADDR_MSB,
                               MSB(PtrToUlong(XmitBufAddress - 1)) );

            NdisRawWritePortUchar( Adapter->IoAddr + NIC_RMT_COUNT_LSB, 0x2 );

            NdisRawWritePortUchar( Adapter->IoAddr + NIC_RMT_COUNT_MSB, 0x0 );

            //
            // Set direction (Write)
            //
            NdisRawWritePortUchar( Adapter->IoAddr + NIC_COMMAND,
                           CR_START | CR_PAGE0 | CR_DMA_WRITE );

            //
            // It seems that the card stores words in LOW:HIGH order
            //
            NdisRawWritePortUshort( Adapter->IoAddr + NIC_RACK_NIC,
                           (USHORT)(Tmp1 | ((*CurBufAddress) << 8)) );

            //
            // Wait for DMA to complete
            //
            Count = 0xFFFF;

            while (Count) {

                NdisRawReadPortUchar( Adapter->IoAddr + NIC_INTR_STATUS, &Tmp1 );

                if (Tmp1 & ISR_DMA_DONE) {

                    break;

                } else {

                    Count--;
                    NdisStallExecution(4);

                }

            }

            CurBufAddress++;
            XmitBufAddress++;
            PacketLength--;
            CurBufLen--;

        }

        //
        // Do Write errata as described on pages 1-143 and 1-144 of
        // the 1992 LAN databook
        //

        //
        // Set Count and destination address
        //
        ReadBuffer = XmitBufAddress + ((ULONG_PTR)XmitBufAddress & 1);

        OldAddr = NewAddr = (USHORT)(ReadBuffer);

//      NdisRawWritePortUchar(Adapter->IoAddr + NIC_COMMAND,   // robin
//                            CR_PAGE0                          // robin
//                           );                                 // robin
        NdisRawWritePortUchar(Adapter->IoAddr + NIC_RMT_ADDR_LSB,
                              LSB(PtrToUlong(ReadBuffer))
                             );

        NdisRawWritePortUchar(Adapter->IoAddr + NIC_RMT_ADDR_MSB,
                              MSB(PtrToUlong(ReadBuffer))
                             );
        NdisRawWritePortUchar(Adapter->IoAddr + NIC_RMT_COUNT_LSB,
                              0x2
                             );
        NdisRawWritePortUchar(Adapter->IoAddr + NIC_RMT_COUNT_MSB,
                              0x0
                             );

        //
        // Set direction (Read)
        //
        NdisRawWritePortUchar(
                       Adapter->IoAddr + NIC_COMMAND,
                       CR_START | CR_PAGE0 | CR_DMA_READ
                       );

        if (Adapter->EightBitSlot) {

            //
            // Read from port
            //
            NdisRawReadPortUchar( Adapter->IoAddr + NIC_RACK_NIC, &Tmp );
            NdisRawReadPortUchar( Adapter->IoAddr + NIC_RACK_NIC, &Tmp );

        } else {

            //
            // Read from port
            //
            NdisRawReadPortUshort( Adapter->IoAddr + NIC_RACK_NIC, &TmpShort );

        }

        //
        // Wait for addr to change
        //
        TmpShort = 0xFFFF;

        while (TmpShort != 0) {

            NdisRawReadPortUchar( Adapter->IoAddr + NIC_CRDA_LSB, &Tmp );
            NewAddr = Tmp;
            NdisRawReadPortUchar( Adapter->IoAddr + NIC_CRDA_MSB, &Tmp );
            NewAddr |= (Tmp << 8);

            if (NewAddr != OldAddr) {

                break;

            }

            NdisStallExecution(1);

            TmpShort--;
        }

        if (NewAddr == OldAddr) {

            NdisWriteErrorLogEntry(
                Adapter->MiniportAdapterHandle,
                NDIS_ERROR_CODE_HARDWARE_FAILURE,
                2,
                cardCopyDownPacket,
                (ULONG_PTR)XmitBufAddress
                );

            return(FALSE);

        }

        //
        // Set Count and destination address
        //

//      NdisRawWritePortUchar( Adapter->IoAddr + NIC_COMMAND, CR_PAGE0 ); // robin

        NdisRawWritePortUchar( Adapter->IoAddr + NIC_RMT_ADDR_LSB,
                           LSB(PtrToUlong(XmitBufAddress)) );

        NdisRawWritePortUchar( Adapter->IoAddr + NIC_RMT_ADDR_MSB,
                           MSB(PtrToUlong(XmitBufAddress)) );

        NdisRawWritePortUchar( Adapter->IoAddr + NIC_RMT_COUNT_LSB,
                           LSB(PacketLength) );

        NdisRawWritePortUchar( Adapter->IoAddr + NIC_RMT_COUNT_MSB,
                           MSB(PacketLength) );
        //
        // Set direction (Write)
        //
        NdisRawWritePortUchar( Adapter->IoAddr + NIC_COMMAND,
                       CR_START | CR_PAGE0 | CR_DMA_WRITE );

    } // setup

    //
    // Copy the data now
    //

    do {

        UINT Count;
        UCHAR Tmp;

        //
        // Write the previous byte with this one
        //
        if (OddBufLen) {

            //
            // It seems that the card stores words in LOW:HIGH order
            //
            NdisRawWritePortUshort( Adapter->IoAddr + NIC_RACK_NIC,
                       (USHORT)(*OddBufAddress | ((*CurBufAddress) << 8)) );

            OddBufLen = FALSE;
            CurBufAddress++;
            CurBufLen--;

        }

        if (Adapter->EightBitSlot) { // byte mode

            NdisRawWritePortBufferUchar(
                Adapter->IoAddr + NIC_RACK_NIC,
                CurBufAddress,
                CurBufLen
                );

        } else { // word mode

            NdisRawWritePortBufferUshort(
                Adapter->IoAddr + NIC_RACK_NIC,
                (PUSHORT)CurBufAddress,
                (CurBufLen >> 1));

            //
            // Save trailing byte (if an odd lengthed transfer)
            //
            if (CurBufLen & 0x1) {
                OddBufAddress = CurBufAddress + (CurBufLen - 1);
                OddBufLen = TRUE;
            }

        }

        //
        // Wait for DMA to complete
        //
        Count = 0xFFFF;
        while (Count) {

            NdisRawReadPortUchar(
                Adapter->IoAddr + NIC_INTR_STATUS,
                &Tmp );

            if (Tmp & ISR_DMA_DONE) {

                break;

            } else {

                Count--;
                NdisStallExecution(4);

            }

        }

        //
        // Move to the next buffer
        //
        NdisGetNextBuffer(CurBuffer, &CurBuffer);

        if (CurBuffer){
            NdisQueryBuffer(CurBuffer, (PVOID *)&CurBufAddress, &CurBufLen);
        }

        //
        // Get address and length of the next buffer
        //
        while (CurBuffer && (CurBufLen == 0)) {

            NdisGetNextBuffer(CurBuffer, &CurBuffer);

            if (CurBuffer){
                NdisQueryBuffer(CurBuffer, (PVOID *)&CurBufAddress, &CurBufLen);
            }

        }

    } while (CurBuffer);

    //
    // Write trailing byte (if necessary)
    //
    if (OddBufLen)
    {
      UINT    Count;
      UCHAR   Tmp;
      USHORT  TmpShort;

     

 
          NdisRawWritePortUchar(Adapter->IoAddr + NIC_RACK_NIC, *OddBufAddress);
   
      //
      // Wait for DMA to complete                      robin-2
      //
      Count = 0xFFFF;
      while (Count) {

          NdisRawReadPortUchar(
              Adapter->IoAddr + NIC_INTR_STATUS,
              &Tmp );

          if (Tmp & ISR_DMA_DONE) {
              break;
          } else {
              Count--;
              NdisStallExecution(4);
          }
      }
    }

    //
    // Return length written
    //
    *Length = PacketLength;

    return TRUE;
}

BOOLEAN
CardCopyDown(
    IN PRTL8139_ADAPTER Adapter,
    IN PUCHAR TargetBuffer,
    IN PUCHAR SourceBuffer,
    IN UINT Length
    )

/*++

Routine Description:

    Copies Length bytes from the SourceBuffer to the card buffer space
    at card address TargetBuffer.

Arguments:

    Adapter - pointer to the adapter block

    SourceBuffer - Buffer in virtual address space

    TargetBuffer - Buffer in card address space

    Length - number of bytes to transfer to card

Return Value:

    TRUE if the transfer completed with no problems.

--*/

{
    //
    // Temporary place holders for odd alignment transfers
    //
    UCHAR Tmp, TmpSave;
    USHORT TmpShort;

    //
    // Values for waiting for noticing when a DMA completes.
    //
    USHORT OldAddr, NewAddr;

    //
    // Count of transfers to do
    //
    USHORT Count;

    //
    // Address the copy if coming from
    //
    PUCHAR ReadBuffer;


    //
    // Skip 0 length copies
    //

    if (Length == 0) {

        return(TRUE);

    }


    if (!Adapter->EightBitSlot && ((ULONG_PTR)TargetBuffer & 0x1)) {

        //
        // For odd addresses we need to read first to get the previous
        // byte and then merge it with our first byte.
        //

        //
        // Set Count and Source address
        //
        NdisRawWritePortUchar(
            Adapter->IoAddr + NIC_RMT_ADDR_LSB,
            LSB(PtrToUlong(TargetBuffer - 1))
        );

        NdisRawWritePortUchar(
            Adapter->IoAddr + NIC_RMT_ADDR_MSB,
            MSB(PtrToUlong(TargetBuffer - 1))
        );

// RTL8139 PCMCIA CHANGE!!!  start
        //NdisRawWritePortUchar(Adapter->IoAddr + NIC_RMT_COUNT_LSB, 0x1);
        NdisRawWritePortUchar(Adapter->IoAddr + NIC_RMT_COUNT_LSB, 0x2);
        NdisRawWritePortUchar(Adapter->IoAddr + NIC_RMT_COUNT_MSB, 0x0);
// RTL8139 PCMCIA CHANGE!!!  end

        //
        // Set direction (Read)
        //

        NdisRawWritePortUchar(
            Adapter->IoAddr + NIC_COMMAND,
            CR_START | CR_PAGE0 | CR_DMA_READ
        );

// RTL8139 PCMCIA CHANGE!!!  start
        //NdisRawReadPortUchar(Adapter->IoAddr + NIC_RACK_NIC, &TmpSave);
        NdisRawReadPortUshort(Adapter->IoAddr + NIC_RACK_NIC, &TmpShort);
        TmpSave = LSB(TmpShort);
// RTL8139 PCMCIA CHANGE!!!  end

        //
        // Do Write errata as described on pages 1-143 and 1-144 of the 1992
        // LAN databook
        //

        //
        // Set Count and destination address
        //

        ReadBuffer = TargetBuffer + ((ULONG_PTR)TargetBuffer & 1);

        OldAddr = NewAddr = (USHORT)(ReadBuffer);

//      NdisRawWritePortUchar(Adapter->IoAddr + NIC_COMMAND, CR_PAGE0); // robin

        NdisRawWritePortUchar(
            Adapter->IoAddr + NIC_RMT_ADDR_LSB,
            LSB(PtrToUlong(ReadBuffer))
        );

        NdisRawWritePortUchar(
            Adapter->IoAddr + NIC_RMT_ADDR_MSB,
            MSB(PtrToUlong(ReadBuffer))
        );

        NdisRawWritePortUchar(Adapter->IoAddr + NIC_RMT_COUNT_LSB, 0x2);
        NdisRawWritePortUchar(Adapter->IoAddr + NIC_RMT_COUNT_MSB, 0x0);

        //
        // Set direction (Read)
        //

        NdisRawWritePortUchar(
            Adapter->IoAddr + NIC_COMMAND,
            CR_START | CR_PAGE0 | CR_DMA_READ
        );

        //
        // Read from port
        //

        NdisRawReadPortUshort(Adapter->IoAddr + NIC_RACK_NIC, &TmpShort);

        //
        // Wait for addr to change
        //

        TmpShort = 0xFFFF;

        while (TmpShort != 0) {

            NdisRawReadPortUchar(
                          Adapter->IoAddr + NIC_CRDA_LSB,
                          &Tmp
                         );

            NewAddr = Tmp;

            NdisRawReadPortUchar(
                          Adapter->IoAddr + NIC_CRDA_MSB,
                          &Tmp
                         );

            NewAddr |= (Tmp << 8);

            if (NewAddr != OldAddr) {

⌨️ 快捷键说明

复制代码 Ctrl + C
搜索代码 Ctrl + F
全屏模式 F11
切换主题 Ctrl + Shift + D
显示快捷键 ?
增大字号 Ctrl + =
减小字号 Ctrl + -