Example #1
0
        public IxgbeDevice(string pciAddr, int rxQueues, int txQueues)
            : base(pciAddr, rxQueues, txQueues)
        {
            if (txQueues < 0 || txQueues > MaxQueues)
            {
                throw new ArgumentException(String.Format("Cannot configure {0} tx queues - limit is {1}",
                                                          txQueues, MaxQueues));
            }
            if (rxQueues < 0 || rxQueues > MaxQueues)
            {
                throw new ArgumentException(String.Format("Cannot configure {0} rx queues - limit is {1}",
                                                          rxQueues, MaxQueues));
            }

            DriverName = "ixy-ixgbe";

            RxQueues = new IxgbeRxQueue[rxQueues];
            TxQueues = new IxgbeTxQueue[txQueues];

            PciController.RemoveDriver(pciAddr);
            PciController.EnableDma(pciAddr);
            try
            {
                //View accessor for mmapped file is automatically created
                PciMemMap = PciController.MapResource(pciAddr);
            }
            catch (Exception e)
            {
                Log.Error("FATAL: Could not map memory for device {0} - {1}", pciAddr, e.Message);
                Environment.Exit(1);
            }

            ResetAndInit();
        }
Example #2
0
        private void InitRx()
        {
            //Disable RX while re-configuring
            ClearFlags(IxgbeDefs.RXCTRL, IxgbeDefs.RXCTRL_RXEN);

            //No DCB or VT, just a single 128kb packet buffer
            SetReg(IxgbeDefs.RXPBSIZE(0), IxgbeDefs.RXPBSIZE_128KB);
            for (uint i = 1; i < 8; i++)
            {
                SetReg(IxgbeDefs.RXPBSIZE(i), 0);
            }

            //Always enable CRC offloading
            SetFlags(IxgbeDefs.HLREG0, IxgbeDefs.HLREG0_RXCRCSTRP);
            SetFlags(IxgbeDefs.RDRXCTL, IxgbeDefs.RDRXCTL_CRCSTRIP);

            //Accept broadcast packets
            SetFlags(IxgbeDefs.FCTRL, IxgbeDefs.FCTRL_BAM);

            //Per queue config
            for (uint i = 0; i < RxQueues.Length; i++)
            {
                Log.Notice("Initializing rx queue {0}", i);
                //Enable advanced rx descriptors
                SetReg(IxgbeDefs.SRRCTL(i), (GetReg(IxgbeDefs.SRRCTL(i)) & ~IxgbeDefs.SRRCTL_DESCTYPE_MASK)
                       | IxgbeDefs.SRRCTL_DESCTYPE_ADV_ONEBUF);
                //DROP_EN causes the NIC to drop packets if no descriptors are available instead of buffering them
                //A single overflowing queue can fill up the whole buffer and impact operations if not setting this
                SetFlags(IxgbeDefs.SRRCTL(i), IxgbeDefs.SRRCTL_DROP_EN);

                //Sec 7.1.9 - Set up descriptor ring
                int ringSizeBytes = NumRxQueueEntries * RxDescriptorSize;
                var dmaMem        = MemoryHelper.AllocateDmaC((uint)ringSizeBytes, true);
                //TODO : The C version sets the allocated memory to -1 here

                SetReg(IxgbeDefs.RDBAL(i), (uint)(dmaMem.PhysicalAddress & 0xFFFFFFFFL));
                SetReg(IxgbeDefs.RDBAH(i), (uint)(dmaMem.PhysicalAddress >> 32));
                SetReg(IxgbeDefs.RDLEN(i), (uint)ringSizeBytes);
                Log.Notice("RX ring {0} physical address: {1}", i, dmaMem.PhysicalAddress);
                Log.Notice("RX ring {0} virtual address: {1}", i, dmaMem.VirtualAddress);

                //Set ring to empty
                SetReg(IxgbeDefs.RDH(i), 0);
                SetReg(IxgbeDefs.RDT(i), 0);

                var queue = new IxgbeRxQueue(NumRxQueueEntries);
                queue.Index           = 0;
                queue.DescriptorsAddr = dmaMem.VirtualAddress;
                RxQueues[i]           = queue;
            }
            //Section 4.6.7 - set some magic bits
            SetFlags(IxgbeDefs.CTRL_EXT, IxgbeDefs.CTRL_EXT_NS_DIS);
            //This flag probably refers to a broken feature: It's reserved and initialized as '1' but it must be '0'
            for (uint i = 0; i < RxQueues.Length; i++)
            {
                ClearFlags(IxgbeDefs.DCA_RXCTRL(i), 1 << 12);
            }

            //Start RX
            SetFlags(IxgbeDefs.RXCTRL, IxgbeDefs.RXCTRL_RXEN);
        }