public VT6102(PCIDevice device) { if (device == null) { throw new ArgumentException("PCI Device is null. Unable to get VIA Rhine-II card"); } pciCard = device; // We are handling this device pciCard.Claimed = true; // Setup interrupt handling //Interrupts.IRQ10 += HandleNetworkInterrupt; //Interrupts.AddIRQHandler(device.InterruptLine, HandleNetworkInterrupt); // Get IO Address from PCI Bus io = pciCard.GetAddressSpace(0) as Kernel.IOAddressSpace; // Enable the card pciCard.EnableDevice(); // Get the EEPROM MAC Address and set it as the devices MAC byte[] eeprom_mac = new byte[6]; UInt32 result = io.Read32(0x00); eeprom_mac[0] = BinaryHelper.GetByteFrom32bit(result, 0); eeprom_mac[1] = BinaryHelper.GetByteFrom32bit(result, 8); eeprom_mac[2] = BinaryHelper.GetByteFrom32bit(result, 16); eeprom_mac[3] = BinaryHelper.GetByteFrom32bit(result, 24); result = io.Read32(0x04); eeprom_mac[4] = BinaryHelper.GetByteFrom32bit(result, 0); eeprom_mac[5] = BinaryHelper.GetByteFrom32bit(result, 8); mac = new MACAddress(eeprom_mac); // Software Reset device SoftwareReset(); // Configure Receive Config ReceiveConfigRegister = 0x1C; // Configure Transmit Config TransmitConfigRegister = 0x04; // Setup RX Descriptors mRxDescriptors = new ManagedMemorySpace(256, 16); // Setup TX Descriptors mTxDescriptors = new ManagedMemorySpace(256, 16); /* Initialize the RX and TX buffers, and set up the RX descriptors to point to the buffers. Also, mark the RX descriptors as being owned by the card so data can be received in them */ mRxBuffers = new List<ManagedMemorySpace>(); for (uint rxd = 0; rxd < 16; rxd++) { uint xOffset = rxd * 16; ManagedMemorySpace buffer = new ManagedMemorySpace(2048); mRxDescriptors.Write32(xOffset + 12, mRxDescriptors.Offset + xOffset + 16); mRxDescriptors.Write32(xOffset + 8, buffer.Offset); mRxDescriptors.Write32(xOffset + 4, buffer.Size); mRxDescriptors.Write32(xOffset, 0x80000000); mRxBuffers.Add(buffer); } mRxDescriptors.Write32(252, mRxDescriptors.Offset); for (uint txd = 0; txd < 16; txd++) { uint xOffset = txd * 16; mTxDescriptors.Write32(xOffset + 12, mTxDescriptors.Offset + xOffset + 16); mTxDescriptors.Write32(xOffset + 8, 0); mTxDescriptors.Write32(xOffset + 4, 0); mTxDescriptors.Write32(xOffset, 0); } mTxDescriptors.Write32(252, mTxDescriptors.Offset); mNextTXDesc = 0; RxDescAddressRegister = mRxDescriptors.Offset; TxDescAddressRegister = mTxDescriptors.Offset; // Setup and clear interrupts IntMaskRegister = 0xFFFF; IntStatusRegister = 0xFFFF; // Setup our Receive and Transmit Queues mTransmitBuffer = new Queue<byte[]>(); mRecvBuffer = new Queue<byte[]>(); }
// Initialize a new instance of the AMD PCNet device driver public AMDPCNet(PCIDevice device) { if (device == null) { throw new ArgumentException("PCI Device is null. Unable to get AMD PCNet card"); } pciCard = device; // We are handling this device pciCard.Claimed = true; // Setup interrupt handling //Interrupts.IRQ09 += HandleNetworkInterrupt; //Interrupts.AddIRQHandler(device.InterruptLine, HandleNetworkInterrupt); // Get IO Address from PCI Bus io = (Kernel.IOAddressSpace)pciCard.GetAddressSpace(0); // Enable the card pciCard.EnableDevice(); // Set the device into 32-bit mode io.Write32(0x10, 0); // Get the EEPROM MAC Address and set it as the devices MAC byte[] eeprom_mac = new byte[6]; UInt32 result = io.Read32(0x00); eeprom_mac[0] = BinaryHelper.GetByteFrom32bit(result, 0); eeprom_mac[1] = BinaryHelper.GetByteFrom32bit(result, 8); eeprom_mac[2] = BinaryHelper.GetByteFrom32bit(result, 16); eeprom_mac[3] = BinaryHelper.GetByteFrom32bit(result, 24); result = io.Read32(0x04); eeprom_mac[4] = BinaryHelper.GetByteFrom32bit(result, 0); eeprom_mac[5] = BinaryHelper.GetByteFrom32bit(result, 8); mac = new MACAddress(eeprom_mac); // Allocate 32 bytes for the 28 byte Initialization block that has to be aligned to a 4 byte boundary //UInt32 address = Heap.MemAlloc(0x20); //mInitBlock = new ManagedUInt32Array(7); // 7 UInt32's, aligned on a 4byte boundary mInitBlock = new ManagedMemorySpace(28, 4); /*Console.Write("Allocated 32 bytes for initialization block @ 0x" + address.ToHex(8)); Console.WriteLine("(Aligned to 0x" + aligned_address.ToHex(8) + ")");*/ // Allocate 80 uints for the 16 RX and TX Descriptor rings. These addresses have to be aligned on a 16-byte boundary mTxDescriptor = new ManagedMemorySpace(256, 16); mRxDescriptor = new ManagedMemorySpace(256, 16); /*Console.Write("Allocated 320 bytes for RX ring descriptors @ 0x" + rd_address.ToHex(8)); Console.WriteLine("(Aligned to 0x" + mRxDescriptorAddress.ToHex(8) + ")"); Console.Write("Allocated 320 bytes for TX ring descriptors @ 0x" + tx_address.ToHex(8)); Console.WriteLine("(Aligned to 0x" + mTxDescriptorAddress.ToHex(8) + ")");*/ // Fill in the Initialization block mInitBlock.Write32(0x00, (0x4 << 28) | (0x4 << 20)); mInitBlock.Write32(0x04, (uint)(eeprom_mac[0] | (eeprom_mac[1] << 8) | (eeprom_mac[2] << 16) | (eeprom_mac[3] << 24))); mInitBlock.Write32(0x08, (uint)(eeprom_mac[4] | (eeprom_mac[5] << 8))); mInitBlock.Write32(0x0C, 0x0); mInitBlock.Write32(0x10, 0x0); mInitBlock.Write32(0x14, mRxDescriptor.Offset); mInitBlock.Write32(0x18, mTxDescriptor.Offset); // Write the Initialization blocks address to the registers on the card InitializationBlockAddress = mInitBlock.Offset; // Set the device to PCNet-PCI II Controller mode (full 32-bit mode) SoftwareStyleRegister = 0x03; /* Initialize the RX and TX buffers, and set up the RX and TX descriptors to point to the buffers. Also, mark the RX descriptors as being owned by the card so data can be received in them */ mRxBuffers = new List<ManagedMemorySpace>(); mTxBuffers = new List<ManagedMemorySpace>(); for (uint rxd = 0; rxd < 16; rxd++) { uint xOffset = rxd * 16; ManagedMemorySpace buffer = new ManagedMemorySpace(2048); mRxDescriptor.Write32(xOffset + 8, buffer.Offset); UInt16 buffer_len = (UInt16)(~buffer.Size); buffer_len++; UInt32 flags = (UInt32)(buffer_len & 0x0FFF) | 0xF000 | 0x80000000; mRxDescriptor.Write32(xOffset + 4, flags); mRxBuffers.Add(buffer); } for (uint txd = 0; txd < 16; txd++) { uint xOffset = txd * 16; ManagedMemorySpace buffer = new ManagedMemorySpace(2048); mTxDescriptor.Write32(xOffset + 8, buffer.Offset); mTxBuffers.Add(buffer); } // Set TX Descriptor 0 as the first one to use... Increment this when we use one to use them in a circular fashion mNextTXDesc = 0; // Setup our Receive and Transmit Queues mTransmitBuffer = new Queue<byte[]>(); mRecvBuffer = new Queue<byte[]>(); }