46 #include "config/the_isa.hh"
47 #include "debug/EthernetAll.hh"
51 #include "params/NSGigE.hh"
56 using std::make_shared;
93 using namespace TheISA;
101 txFifo(p->tx_fifo_size), rxFifo(p->rx_fifo_size),
102 txPacket(0), rxPacket(0), txPacketBufPtr(NULL), rxPacketBufPtr(NULL),
103 txXferLen(0), rxXferLen(0), rxDmaFree(false), txDmaFree(false),
104 txState(txIdle), txEnable(false), CTDD(false), txHalt(false),
105 txFragPtr(0), txDescCnt(0), txDmaState(dmaIdle), rxState(rxIdle),
106 rxEnable(false), CRDD(false), rxPktBytes(0), rxHalt(false),
107 rxFragPtr(0), rxDescCnt(0), rxDmaState(dmaIdle), extstsEnable(false),
108 eepromState(eepromStart), eepromClk(false), eepromBitsToRx(0),
109 eepromOpcode(0), eepromAddress(0), eepromData(0),
110 dmaReadDelay(p->dma_read_delay), dmaWriteDelay(p->dma_write_delay),
111 dmaReadFactor(p->dma_read_factor), dmaWriteFactor(p->dma_write_factor),
112 rxDmaData(NULL), rxDmaAddr(0), rxDmaLen(0),
113 txDmaData(NULL), txDmaAddr(0), txDmaLen(0),
114 rxDmaReadEvent(this), rxDmaWriteEvent(this),
115 txDmaReadEvent(this), txDmaWriteEvent(this),
116 dmaDescFree(p->dma_desc_free), dmaDataFree(p->dma_data_free),
117 txDelay(p->tx_delay), rxDelay(p->rx_delay),
118 rxKickTick(0), rxKickEvent(this), txKickTick(0), txKickEvent(this),
119 txEvent(this), rxFilterEnable(p->rx_filter),
120 acceptBroadcast(false), acceptMulticast(false), acceptUnicast(false),
121 acceptPerfect(false), acceptArp(false), multicastHashEnable(false),
122 intrDelay(p->intr_delay), intrTick(0), cpuPendingIntr(false),
123 intrEvent(0), interface(0)
127 interface = new NSGigEInt(name() + ".int0", this);
153 panic(
"Device specific PCI config space not implemented!\n");
173 if (if_name ==
"interface") {
175 panic(
"interface already connected to\n");
192 DPRINTF(EthernetPIO,
"read da=%#x pa=%#x size=%d\n",
199 panic(
"Accessing reserved register");
200 }
else if (daddr >
RESERVED && daddr <= 0x3FC) {
206 pkt->
set<uint32_t>(0);
209 }
else if (daddr > 0x3FC)
210 panic(
"Something is messed up!\n");
212 assert(pkt->
getSize() ==
sizeof(uint32_t));
213 uint32_t &
reg = *pkt->
getPtr<uint32_t>();
325 panic(
"unaligned read from filter hash table!");
332 panic(
"reading RFDR for something other than pattern"
333 " matching or hashing! %#x\n", rfaddr);
397 panic(
"reading unimplemented register: addr=%#x", daddr);
400 DPRINTF(EthernetPIO,
"read from %#x: data=%d data=%#x\n",
413 DPRINTF(EthernetPIO,
"write da=%#x pa=%#x size=%d\n",
417 panic(
"Accessing reserved register");
418 }
else if (daddr >
RESERVED && daddr <= 0x3FC) {
420 }
else if (daddr > 0x3FC)
421 panic(
"Something is messed up!\n");
423 if (pkt->
getSize() ==
sizeof(uint32_t)) {
424 uint32_t
reg = pkt->
get<uint32_t>();
427 DPRINTF(EthernetPIO,
"write data=%d data=%#x\n", reg, reg);
434 }
else if (reg &
CR_TXE) {
444 }
else if (reg &
CR_RXE) {
521 panic(
"CFGR_AUTO_1000 not implemented!\n");
523 if (reg & CFGR_PCI64_DET)
524 panic(
"CFGR_PCI64_DET is read only register!\n");
575 panic(
"ISR is a read only register!\n");
655 if (reg & RX_CFG_RX_RD) ;
697 panic(
"RFCR_APAT not implemented!\n");
700 panic(
"Unicast hash filtering not used by drivers!\n");
703 panic(
"RFCR_ULM not implemented!\n");
729 panic(
"unaligned write to filter hash table!");
733 = (uint8_t)(reg >> 8);
736 panic(
"writing RFDR for something other than pattern matching "
737 "or hashing! %#x\n", rfaddr);
745 panic(
"the driver never uses BRDR, something is wrong!\n");
748 panic(
"SRR is read only register!\n");
751 panic(
"the driver never uses MIBC, something is wrong!\n");
762 panic(
"the driver never uses VDR, something is wrong!\n");
772 panic(
"TBICR_MR_LOOPBACK never used, something wrong!\n");
786 panic(
"TBISR is read only register!\n");
802 panic(
"this should only be written to by the fake phy!\n");
805 panic(
"TANER is read only register!\n");
812 panic(
"invalid register access daddr=%#x", daddr);
815 panic(
"Invalid Request Size");
825 panic(
"Cannot set a reserved interrupt");
828 warn(
"interrupt not implemented %#x\n", interrupts);
861 "interrupt written to ISR: intr=%#x isr=%#x imr=%#x\n",
882 panic(
"Cannot clear a reserved interrupt");
913 "interrupt cleared from ISR: intr=%x isr=%x imr=%x\n",
923 DPRINTF(EthernetIntr,
"interrupt mask changed: isr=%x imr=%x masked=%x\n",
947 DPRINTF(EthernetIntr,
"don't need to schedule event...intrTick=%d\n",
957 DPRINTF(EthernetIntr,
"going to schedule an interrupt for intrTick=%d\n",
979 "would send an interrupt now, but there's already pending\n");
984 DPRINTF(EthernetIntr,
"posting interrupt\n");
1004 DPRINTF(EthernetIntr,
"clearing interrupt\n");
1016 DPRINTF(Ethernet,
"transmit reset\n");
1030 DPRINTF(Ethernet,
"receive reset\n");
1085 DPRINTF(EthernetDMA,
"rx dma read paddr=%#x len=%d\n",
1115 DPRINTF(EthernetDMA,
"rx dma write paddr=%#x len=%d\n",
1132 "receive kick rxState=%s (rxBuf.size=%d) %d-bit\n",
1141 DPRINTF(EthernetSM,
"receive kick exiting, can't run till %d\n",
1176 DPRINTF(EthernetSM,
"Receive Disabled! Nothing to do.\n");
1221 DPRINTF(EthernetDesc,
"rxDesc: addr=%08x read descriptor\n",
1224 "rxDesc: link=%#x bufptr=%#x cmdsts=%08x extsts=%08x\n",
1225 link, bufptr, cmdsts, extsts);
1248 DPRINTF(EthernetSM,
"****processing receive of new packet****\n");
1259 DPRINTF(Ethernet,
"ID is %d\n", ip->
id());
1263 "Src Port=%d, Dest Port=%d, Seq=%d, Ack=%d\n",
1264 tcp->sport(), tcp->dport(), tcp->seq(),
1298 DPRINTF(EthernetSM,
"done with receiving packet\n");
1303 cmdsts &= 0xffff0000;
1316 const EthAddr &dst = rxFifoFront()->dst();
1330 if (
cksum(ip) != 0) {
1331 DPRINTF(EthernetCksum,
"Rx IP Checksum Error\n");
1339 if (
cksum(tcp) != 0) {
1340 DPRINTF(EthernetCksum,
"Rx TCP Checksum Error\n");
1347 if (
cksum(udp) != 0) {
1348 DPRINTF(EthernetCksum,
"Rx UDP Checksum Error\n");
1363 "rxDesc: addr=%08x writeback cmdsts extsts\n",
1366 "rxDesc: link=%#x bufptr=%#x cmdsts=%08x extsts=%08x\n",
1367 link, bufptr, cmdsts, extsts);
1403 assert(cmdsts & CMDSTS_OWN);
1412 DPRINTF(EthernetSM,
"Halting the RX state machine\n");
1443 panic(
"Invalid rxState!");
1446 DPRINTF(EthernetSM,
"entering next rxState=%s\n",
1454 DPRINTF(EthernetSM,
"rx state machine exited rxState=%s\n",
1465 DPRINTF(Ethernet,
"nothing to transmit\n");
1469 DPRINTF(Ethernet,
"Attempt Pkt Transmit: txFifo length=%d\n",
1476 DPRINTF(Ethernet,
"ID is %d\n",
ip->id());
1480 "Src Port=%d, Dest Port=%d, Seq=%d, Ack=%d\n",
1481 tcp->sport(), tcp->dport(), tcp->seq(),
1492 DPRINTF(Ethernet,
"Successful Xmit! now txFifoAvail is %d\n",
1507 DPRINTF(Ethernet,
"reschedule transmit\n");
1532 DPRINTF(EthernetDMA,
"tx dma read paddr=%#x len=%d\n",
1562 DPRINTF(EthernetDMA,
"tx dma write paddr=%#x len=%d\n",
1578 DPRINTF(EthernetSM,
"transmit kick txState=%s %d-bit\n",
1587 DPRINTF(EthernetSM,
"transmit kick exiting, can't run till %d\n",
1613 DPRINTF(EthernetSM,
"Transmit disabled. Nothing to do.\n");
1659 DPRINTF(EthernetDesc,
"txDesc: addr=%08x read descriptor\n",
1662 "txDesc: link=%#x bufptr=%#x cmdsts=%#08x extsts=%#08x\n",
1663 link, bufptr, cmdsts, extsts);
1678 DPRINTF(EthernetSM,
"****starting the tx of a new packet****\n");
1679 txPacket = make_shared<EthPacketData>(16384);
1684 DPRINTF(EthernetSM,
"the txDescCnt == 0, done with descriptor\n");
1686 DPRINTF(EthernetSM,
"there are more descriptors to come\n");
1689 cmdsts &= ~CMDSTS_OWN;
1706 DPRINTF(EthernetSM,
"This packet is done, let's wrap it up\n");
1718 warn_once(
"UDPPKT set, but not UDP!\n");
1727 warn_once(
"TCPPKT set, but not UDP!\n");
1746 panic(
"transmit packet too large, %s > 1514\n",
1767 cmdsts &= ~CMDSTS_OWN;
1771 "txDesc writeback: cmdsts=%08x extsts=%08x\n",
1794 DPRINTF(EthernetSM,
"halting TX state machine\n");
1804 DPRINTF(EthernetSM,
"this descriptor isn't done yet\n");
1853 DPRINTF(EthernetSM,
"halting TX state machine\n");
1883 panic(
"invalid state");
1886 DPRINTF(EthernetSM,
"entering next txState=%s\n",
1894 DPRINTF(EthernetSM,
"tx state machine exited txState=%s\n",
1929 panic(
"only EEPROM reads are implemented!");
1947 panic(
"EEPROM read access out of range!");
1970 panic(
"FreeBSD driver only uses EEPROM to read PMATCH!");
1997 panic(
"invalid EEPROM state");
2006 DPRINTF(Ethernet,
"transfer complete: txFifo empty...nothing to do\n");
2010 DPRINTF(Ethernet,
"transfer complete: data in txFifo...schedule xmit\n");
2051 DPRINTF(Ethernet,
"rxFilter drop\n");
2052 DDUMP(EthernetData, packet->data, packet->length);
2064 DPRINTF(Ethernet,
"Receiving packet from wire, rxFifoAvail=%d\n",
2068 DPRINTF(Ethernet,
"receive disabled...packet dropped\n");
2074 "receive packet filtering disabled . . . packet dropped\n");
2079 DPRINTF(Ethernet,
"packet filtered...dropped\n");
2089 "packet won't fit in receive buffer...pkt ID %d dropped\n",
2187 bool txPacketExists =
txPacket !=
nullptr;
2189 if (txPacketExists) {
2192 txPacket->serialize(
"txPacket", cp);
2197 bool rxPacketExists =
rxPacket !=
nullptr;
2199 if (rxPacketExists) {
2200 rxPacket->serialize(
"rxPacket", cp);
2290 Tick intrEventTick = 0;
2352 bool txPacketExists;
2354 if (txPacketExists) {
2355 txPacket = make_shared<EthPacketData>(16384);
2356 txPacket->unserialize(
"txPacket", cp);
2357 uint32_t txPktBufPtr;
2363 bool rxPacketExists;
2366 if (rxPacketExists) {
2367 rxPacket = make_shared<EthPacketData>();
2368 rxPacket->unserialize(
"rxPacket", cp);
2369 uint32_t rxPktBufPtr;
2404 this->txState = (
TxState) txState;
2411 this->txDmaState = (
DmaState) txDmaState;
2421 this->rxState = (
RxState) rxState;
2429 this->rxDmaState = (
DmaState) rxDmaState;
2472 if (intrEventTick) {
2479 NSGigEParams::create()
void unserialize(CheckpointIn &cp) override
Unserialize an object.
void set(T v, ByteOrder endian)
Set the value in the data pointer to v using the specified endianness.
EventWrapper< NSGigE,&NSGigE::cpuInterrupt > IntrEvent
Cycles is a wrapper class for representing cycle counts, i.e.
void unserialize(CheckpointIn &cp) override
Reconstruct the state of this object from a checkpoint.
Stats::Scalar totalRxIdle
const uint8_t EEPROM_READ
void dmaRead(Addr addr, int size, Event *event, uint8_t *data, Tick delay=0)
Stats::Scalar descDmaReads
Addr rxFragPtr
ptr to the next byte in current fragment
void unserialize(const std::string &base, CheckpointIn &cp)
Stats::Scalar descDmaWrites
void cpuIntrPost(Tick when)
Dummy class to keep the Python class hierarchy in sync with the C++ object hierarchy.
dp_regs regs
device register file
uint16_t cksum(const IpPtr &ptr)
EEPROMState
EEPROM State Machine States.
const char * NsRxStateStrings[]
bool cpuIntrPending() const
Stats::Scalar rxIpChecksums
const uint8_t EEPROM_PMATCH2_ADDR
Stats::Scalar rxUdpChecksums
bool scheduled() const
Determine if the current event is scheduled.
#define DDUMP(x, data, count)
EventWrapper< NSGigE,&NSGigE::txDmaReadDone > txDmaReadEvent
TxState
Transmit State Machine states.
Stats::Scalar postedRxIdle
EEPROMState eepromState
EEPROM State Machine.
void dmaWrite(Addr addr, int size, Event *event, uint8_t *data, Tick delay=0)
Stats::Scalar totalRxDesc
Stats::Scalar rxTcpChecksums
const uint16_t FHASH_SIZE
T * getPtr()
get a pointer to the data ptr.
uint32_t rxDescCnt
count of bytes remaining in the current descriptor
void serialize(const std::string &base, CheckpointOut &cp) const
Serialization stuff.
T get(ByteOrder endian) const
Get the data in the packet byte swapped from the specified endianness.
Stats::Scalar postedTxDesc
Device module for modelling the National Semiconductor DP83820 ethernet controller.
Addr txFragPtr
ptr to the next byte in the current fragment
#define UNSERIALIZE_SCALAR(scalar)
ns_desc32 txDesc32
DescCaches.
Tick clockEdge(Cycles cycles=Cycles(0)) const
Determine the tick when a cycle begins, by default the current one, but the argument also enables the...
Tick curTick()
The current simulated tick.
const uint8_t EEPROM_PMATCH0_ADDR
Tick when() const
Get the time that the event is scheduled.
Tick write(PacketPtr pkt) override
Pure virtual function that the device must implement.
void makeAtomicResponse()
Stats::Scalar totalTxDesc
uint64_t Tick
Tick count type.
const uint8_t EEPROM_SIZE
virtual Tick writeConfig(PacketPtr pkt)
Write to the PCI config space data that is stored locally.
const Params * params() const
void drainResume() override
Resume execution after a successful drain.
const uint8_t EEPROM_PMATCH1_ADDR
#define SERIALIZE_ARRAY(member, size)
bool CTDD
Current Transmit Descriptor Done.
virtual Tick readConfig(PacketPtr pkt)
Read from the PCI config space data that is stored locally.
EventWrapper< NSGigE,&NSGigE::txDmaWriteDone > txDmaWriteEvent
Stats::Scalar descDmaWrBytes
Stats::Scalar txIpChecksums
Stats::Scalar postedTxIdle
std::shared_ptr< EthPacketData > EthPacketPtr
Stats::Scalar droppedPackets
Stats::Scalar descDmaRdBytes
#define PCI_DEVICE_SPECIFIC
unsigned reserve(unsigned len=0)
void squash()
Squash the current event.
void transmit()
Retransmit event.
bool ioEnable
pci settings
Defines global host-dependent types: Counter, Tick, and (indirectly) {int,uint}{8,16,32,64}_t.
uint64_t Addr
Address type This will probably be moved somewhere else in the near future.
EtherInt * getEthPort(const std::string &if_name, int idx) override
Additional function to return the Port of a memory object.
const uint16_t FHASH_ADDR
A Packet is used to encapsulate a transfer between two objects in the memory system (e...
bool rxFilter(const EthPacketPtr &packet)
Stats::Scalar totalTxIdle
RxState
Receive State Machine States.
#define SERIALIZE_SCALAR(scalar)
const char * NsTxStateStrings[]
#define UNSERIALIZE_ARRAY(member, size)
bool sendPacket(EthPacketPtr packet)
void serialize(CheckpointOut &cp) const override
Serialize an object.
void reschedule(Event &event, Tick when, bool always=false)
Stats::Scalar txUdpChecksums
EthPacketPtr txPacket
various helper vars
Stats::Scalar postedRxOrn
uint8_t filterHash[FHASH_SIZE]
for hash table memory.
Stats::Scalar postedRxDesc
Tick writeConfig(PacketPtr pkt) override
This is to write to the PCI general configuration registers.
EventWrapper< NSGigE,&NSGigE::rxDmaReadDone > rxDmaReadEvent
Tick read(PacketPtr pkt) override
This reads the device registers, which are detailed in the NS83820 spec sheet.
Declaration of the Packet class.
std::ostream CheckpointOut
virtual void drainResume()
Resume execution after a successful drain.
const EthAddr & dst() const
uint8_t perfectMatch[ETH_ADDR_LEN]
for perfect match memory.
uint32_t txDescCnt
count of bytes remaining in the current descriptor
void schedule(Event &event, Tick when)
EventWrapper< NSGigE,&NSGigE::rxDmaWriteDone > rxDmaWriteEvent
void devIntrPost(uint32_t interrupts)
Interrupt management.
DrainState drainState() const
Return the current drain state of an object.
bool rxFilterEnable
receive address filter
RxState rxState
rx State Machine
NS DP83820 Ethernet device model.
bool CRDD
Current Receive Descriptor Done.
void devIntrClear(uint32_t interrupts)
bool push(EthPacketPtr ptr)
PCIConfig config
The current config space.
Stats::Scalar postedInterrupts
const char * NsDmaState[]
void eepromKick()
Advance the EEPROM state machine Called on rising edge of EEPROM clock bit in MEAR.
uint32_t rxPktBytes
num of bytes in the current packet being drained from rxDataFifo
void serialize(CheckpointOut &cp) const override
Serialize this object to the given output stream.
Stats::Scalar txTcpChecksums
bool recvPacket(EthPacketPtr packet)