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

📄 card.c

📁 使用网络驱动器接口标准开发的ne2000网卡的NT驱动.
💻 C
📖 第 1 页 / 共 5 页
字号:
        // byte and then merge it with our first byte.
        //

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

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

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

        //
        // Set direction (Read)
        //

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

// NE2000 PCMCIA CHANGE!!!  start
        //NdisRawReadPortUchar(Adapter->IoPAddr + NIC_RACK_NIC, &TmpSave);
        NdisRawReadPortUshort(Adapter->IoPAddr + NIC_RACK_NIC, &TmpShort);
        TmpSave = LSB(TmpShort);
// NE2000 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->IoPAddr + NIC_COMMAND, CR_PAGE0); // robin

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

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

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

        //
        // Set direction (Read)
        //

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

        //
        // Read from port
        //

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

        //
        // Wait for addr to change
        //

        TmpShort = 0xFFFF;

        while (TmpShort != 0) {

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

            NewAddr = Tmp;

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

            NewAddr |= (Tmp << 8);

            if (NewAddr != OldAddr) {

                break;
            }

            NdisStallExecution(1);

            TmpShort--;

        }

        if (NewAddr == OldAddr) {

            return(FALSE);

        }

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

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

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

        //
        // Set direction (Write)
        //

        NdisRawWritePortUchar(
            Adapter->IoPAddr + NIC_COMMAND,
            CR_START | CR_PAGE0 | CR_DMA_WRITE
        );

        //
        // It seems that the card stores words in LOW:HIGH order
        //

        NdisRawWritePortUshort(
                       Adapter->IoPAddr + NIC_RACK_NIC,
                       (USHORT)(TmpSave | ((*SourceBuffer) << 8))
                       );

        //
        // Wait for DMA to complete
        //

        Count = 0xFFFF;

        while (Count) {

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

            if (Tmp & ISR_DMA_DONE) {

                break;

            } else {

                Count--;

                NdisStallExecution(4);

            }

        }

        SourceBuffer++;
        TargetBuffer++;
        Length--;

    }

    //
    // 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(                              // robin
//                     Adapter->IoPAddr + NIC_COMMAND,  // robin
//                     CR_PAGE0                         // robin
//                    );                                // robin

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

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

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

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

    //
    // Set direction (Read)
    //

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

    if (Adapter->EightBitSlot) {

        //
        // Read from port
        //

        NdisRawReadPortUchar(
                       Adapter->IoPAddr + NIC_RACK_NIC,
                       &Tmp
                      );


        NdisRawReadPortUchar(
                       Adapter->IoPAddr + NIC_RACK_NIC,
                       &Tmp
                      );

    } else {

        //
        // Read from port
        //

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

    }

    //
    // Wait for addr to change
    //

    TmpShort = 0xFFFF;

    while (TmpShort != 0) {

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

        NewAddr = Tmp;

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

        NewAddr |= (Tmp << 8);

        if (NewAddr != OldAddr) {

            break;
        }

        NdisStallExecution(1);

        TmpShort--;

    }

    if (NewAddr == OldAddr) {

        return(FALSE);

    }

    //
    // Set Count and destination address
    //

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

    NdisRawWritePortUchar(
                       Adapter->IoPAddr + NIC_RMT_ADDR_LSB,
                       LSB(PtrToUlong(TargetBuffer))
                      );

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

    NdisRawWritePortUchar(
                       Adapter->IoPAddr + NIC_RMT_COUNT_LSB,
                       LSB(Length)
                      );

    NdisRawWritePortUchar(
                       Adapter->IoPAddr + NIC_RMT_COUNT_MSB,
                       MSB(Length)
                      );

    //
    // Set direction (Write)
    //

    NdisRawWritePortUchar(
                   Adapter->IoPAddr + NIC_COMMAND,
                   CR_START | CR_PAGE0 | CR_DMA_WRITE
                  );

    if (Adapter->EightBitSlot) {

        //
        // Repeatedly write to out port
        //

        NdisRawWritePortBufferUchar(
                       Adapter->IoPAddr + NIC_RACK_NIC,
                       SourceBuffer,
                       Length);

    } else {

        //
        // Write words to out ports
        //

        NdisRawWritePortBufferUshort(
                       Adapter->IoPAddr + NIC_RACK_NIC,
                       (PUSHORT)SourceBuffer,
                       (Length >> 1));

        //
        // Write trailing byte (if necessary)
        //
        if (Length & 0x1)
        {
            SourceBuffer += (Length - 1);

// NE2000 PCMCIA CHANGE!!!  start

            //NdisRawWritePortUchar(
            //    Adapter->IoPAddr + NIC_RACK_NIC,
            //    *SourceBuffer
            //);

            TmpShort = (USHORT)(*SourceBuffer);
            NdisRawWritePortUshort(
                Adapter->IoPAddr + NIC_RACK_NIC,
                TmpShort
            );
// NE2000 PCMCIA CHANGE!!!  end


        }

    }

    //
    // Wait for DMA to complete
    //

    Count = 0xFFFF;

    while (Count) {

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

        if (Tmp & ISR_DMA_DONE) {

            break;

        } else {

            Count--;

            NdisStallExecution(4);

        }

#if DBG
        if (!(Tmp & ISR_DMA_DONE)) {

            DbgPrint("CopyDownDMA didn't finish!");

        }
#endif // DBG

    }

    IF_LOG(Ne2000Log('>');)

    return TRUE;
}


BOOLEAN
CardCopyUp(
    IN PNE2000_ADAPTER Adapter,
    IN PUCHAR TargetBuffer,
    IN PUCHAR SourceBuffer,
    IN UINT BufferLength
    )

/*++

Routine Description:

    Copies data from the card to memory.

Arguments:

    Adapter - pointer to the adapter block

    Target - the target address

    Source - the source address (on the card)

    BufferLength - the number of bytes to copy

Return Value:

    TRUE if the transfer completed with no problems.

--*/

{

    //
    // Used to check when the dma is done
    //
    UCHAR IsrValue;

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

    //
    // Place holder for port values
    //
    UCHAR Temp;

    if (BufferLength == 0) {

        return TRUE;

    }

    //
    // Read the Command Register, to make sure it is ready for a write
    //
    NdisRawReadPortUchar(Adapter->IoPAddr+NIC_COMMAND, &Temp);

    if (Adapter->EightBitSlot) {

        //
        // If byte mode
        //

        //
        // Set Count and destination address
        //

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

        NdisRawWritePortUchar(
                           Adapter->IoPAddr + NIC_RMT_ADDR_LSB,
                           LSB(PtrToUlong(SourceBuffer))
                          );

        NdisRawWritePortUchar(
                           Adapter->IoPAddr + NIC_RMT_ADDR_MSB,
                           MSB(PtrToUlong(SourceBuffer))
                          );

        NdisRawWritePortUchar(
                           Adapter->IoPAddr + NIC_RMT_COUNT_LSB,
                           LSB(BufferLength)
                          );

        NdisRawWritePortUchar(
                           Adapter->IoPAddr + NIC_RMT_COUNT_MSB,
                           MSB(BufferLength)
                          );

        //
        // Set direction (Read)
        //

        NdisRawWritePortUchar(
                       Adapter->IoPAddr + NIC_COMMAND,
                       CR_START | CR_PAGE0 | CR_DMA_READ
                      );
        //
        // Repeatedly read from port
        //

        NdisRawReadPortBufferUchar(
                       Adapter->IoPAddr + NIC_RACK_NIC,
                       TargetBuffer,
                       BufferLength
                      );

    } else {

        //
        // Else word mode
        //

        USHORT Tmp;

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

        //
        // Avoid transfers to odd addresses
        //

        if ((ULONG_PTR)SourceBuffer & 0x1) {

            //
            // For odd addresses we need to read previous word and store the
            // second byte
            //

            //
            // Set Count and Source address
            //

            NdisRawWritePortUchar(
                               Adapter->IoPAddr + NIC_RMT_ADDR_LSB,
                               LSB(PtrToUlong(SourceBuffer - 1))
                              );

            NdisRawWritePortUchar(
                               Adapter->IoPAddr + NIC_RMT_ADDR_MSB,
                               MSB(PtrToUlong(SourceBuffer - 1))
                              );

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

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

⌨️ 快捷键说明

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