ns_gige.hh revision 2760
1/* 2 * Copyright (c) 2004-2005 The Regents of The University of Michigan 3 * All rights reserved. 4 * 5 * Redistribution and use in source and binary forms, with or without 6 * modification, are permitted provided that the following conditions are 7 * met: redistributions of source code must retain the above copyright 8 * notice, this list of conditions and the following disclaimer; 9 * redistributions in binary form must reproduce the above copyright 10 * notice, this list of conditions and the following disclaimer in the 11 * documentation and/or other materials provided with the distribution; 12 * neither the name of the copyright holders nor the names of its 13 * contributors may be used to endorse or promote products derived from 14 * this software without specific prior written permission. 15 * 16 * THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS 17 * "AS IS" AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT 18 * LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR 19 * A PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT 20 * OWNER OR CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, 21 * SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT 22 * LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, 23 * DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY 24 * THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT 25 * (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE 26 * OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE. 27 * 28 * Authors: Nathan Binkert 29 * Lisa Hsu 30 */ 31 32/** @file 33 * Device module for modelling the National Semiconductor 34 * DP83820 ethernet controller 35 */ 36 37#ifndef __DEV_NS_GIGE_HH__ 38#define __DEV_NS_GIGE_HH__ 39 40#include "base/inet.hh" 41#include "base/statistics.hh" 42#include "dev/etherint.hh" 43#include "dev/etherpkt.hh" 44#include "dev/io_device.hh" 45#include "dev/ns_gige_reg.h" 46#include "dev/pcidev.hh" 47#include "dev/pktfifo.hh" 48#include "sim/eventq.hh" 49 50// Hash filtering constants 51const uint16_t FHASH_ADDR = 0x100; 52const uint16_t FHASH_SIZE = 0x100; 53 54// EEPROM constants 55const uint8_t EEPROM_READ = 0x2; 56const uint8_t EEPROM_SIZE = 64; // Size in words of NSC93C46 EEPROM 57const uint8_t EEPROM_PMATCH2_ADDR = 0xA; // EEPROM Address of PMATCH word 2 58const uint8_t EEPROM_PMATCH1_ADDR = 0xB; // EEPROM Address of PMATCH word 1 59const uint8_t EEPROM_PMATCH0_ADDR = 0xC; // EEPROM Address of PMATCH word 0 60 61/** 62 * Ethernet device registers 63 */ 64struct dp_regs { 65 uint32_t command; 66 uint32_t config; 67 uint32_t mear; 68 uint32_t ptscr; 69 uint32_t isr; 70 uint32_t imr; 71 uint32_t ier; 72 uint32_t ihr; 73 uint32_t txdp; 74 uint32_t txdp_hi; 75 uint32_t txcfg; 76 uint32_t gpior; 77 uint32_t rxdp; 78 uint32_t rxdp_hi; 79 uint32_t rxcfg; 80 uint32_t pqcr; 81 uint32_t wcsr; 82 uint32_t pcr; 83 uint32_t rfcr; 84 uint32_t rfdr; 85 uint32_t brar; 86 uint32_t brdr; 87 uint32_t srr; 88 uint32_t mibc; 89 uint32_t vrcr; 90 uint32_t vtcr; 91 uint32_t vdr; 92 uint32_t ccsr; 93 uint32_t tbicr; 94 uint32_t tbisr; 95 uint32_t tanar; 96 uint32_t tanlpar; 97 uint32_t taner; 98 uint32_t tesr; 99}; 100 101struct dp_rom { 102 /** 103 * for perfect match memory. 104 * the linux driver doesn't use any other ROM 105 */ 106 uint8_t perfectMatch[ETH_ADDR_LEN]; 107 108 /** 109 * for hash table memory. 110 * used by the freebsd driver 111 */ 112 uint8_t filterHash[FHASH_SIZE]; 113}; 114 115class NSGigEInt; 116class Packet; 117class PciConfigAll; 118 119/** 120 * NS DP83820 Ethernet device model 121 */ 122class NSGigE : public PciDev 123{ 124 public: 125 /** Transmit State Machine states */ 126 enum TxState 127 { 128 txIdle, 129 txDescRefr, 130 txDescRead, 131 txFifoBlock, 132 txFragRead, 133 txDescWrite, 134 txAdvance 135 }; 136 137 /** Receive State Machine States */ 138 enum RxState 139 { 140 rxIdle, 141 rxDescRefr, 142 rxDescRead, 143 rxFifoBlock, 144 rxFragWrite, 145 rxDescWrite, 146 rxAdvance 147 }; 148 149 enum DmaState 150 { 151 dmaIdle, 152 dmaReading, 153 dmaWriting, 154 dmaReadWaiting, 155 dmaWriteWaiting 156 }; 157 158 /** EEPROM State Machine States */ 159 enum EEPROMState 160 { 161 eepromStart, 162 eepromGetOpcode, 163 eepromGetAddress, 164 eepromRead 165 }; 166 167 protected: 168 /** device register file */ 169 dp_regs regs; 170 dp_rom rom; 171 172 /** pci settings */ 173 bool ioEnable; 174#if 0 175 bool memEnable; 176 bool bmEnable; 177#endif 178 179 /*** BASIC STRUCTURES FOR TX/RX ***/ 180 /* Data FIFOs */ 181 PacketFifo txFifo; 182 PacketFifo rxFifo; 183 184 /** various helper vars */ 185 EthPacketPtr txPacket; 186 EthPacketPtr rxPacket; 187 uint8_t *txPacketBufPtr; 188 uint8_t *rxPacketBufPtr; 189 uint32_t txXferLen; 190 uint32_t rxXferLen; 191 bool rxDmaFree; 192 bool txDmaFree; 193 194 /** DescCaches */ 195 ns_desc32 txDesc32; 196 ns_desc32 rxDesc32; 197 ns_desc64 txDesc64; 198 ns_desc64 rxDesc64; 199 200 /* state machine cycle time */ 201 Tick clock; 202 inline Tick cycles(int numCycles) const { return numCycles * clock; } 203 204 /* tx State Machine */ 205 TxState txState; 206 bool txEnable; 207 208 /** Current Transmit Descriptor Done */ 209 bool CTDD; 210 /** halt the tx state machine after next packet */ 211 bool txHalt; 212 /** ptr to the next byte in the current fragment */ 213 Addr txFragPtr; 214 /** count of bytes remaining in the current descriptor */ 215 uint32_t txDescCnt; 216 DmaState txDmaState; 217 218 /** rx State Machine */ 219 RxState rxState; 220 bool rxEnable; 221 222 /** Current Receive Descriptor Done */ 223 bool CRDD; 224 /** num of bytes in the current packet being drained from rxDataFifo */ 225 uint32_t rxPktBytes; 226 /** halt the rx state machine after current packet */ 227 bool rxHalt; 228 /** ptr to the next byte in current fragment */ 229 Addr rxFragPtr; 230 /** count of bytes remaining in the current descriptor */ 231 uint32_t rxDescCnt; 232 DmaState rxDmaState; 233 234 bool extstsEnable; 235 236 /** EEPROM State Machine */ 237 EEPROMState eepromState; 238 bool eepromClk; 239 uint8_t eepromBitsToRx; 240 uint8_t eepromOpcode; 241 uint8_t eepromAddress; 242 uint16_t eepromData; 243 244 protected: 245 Tick dmaReadDelay; 246 Tick dmaWriteDelay; 247 248 Tick dmaReadFactor; 249 Tick dmaWriteFactor; 250 251 void *rxDmaData; 252 Addr rxDmaAddr; 253 int rxDmaLen; 254 bool doRxDmaRead(); 255 bool doRxDmaWrite(); 256 257 void *txDmaData; 258 Addr txDmaAddr; 259 int txDmaLen; 260 bool doTxDmaRead(); 261 bool doTxDmaWrite(); 262 263 void rxDmaReadDone(); 264 friend class EventWrapper<NSGigE, &NSGigE::rxDmaReadDone>; 265 EventWrapper<NSGigE, &NSGigE::rxDmaReadDone> rxDmaReadEvent; 266 267 void rxDmaWriteDone(); 268 friend class EventWrapper<NSGigE, &NSGigE::rxDmaWriteDone>; 269 EventWrapper<NSGigE, &NSGigE::rxDmaWriteDone> rxDmaWriteEvent; 270 271 void txDmaReadDone(); 272 friend class EventWrapper<NSGigE, &NSGigE::txDmaReadDone>; 273 EventWrapper<NSGigE, &NSGigE::txDmaReadDone> txDmaReadEvent; 274 275 void txDmaWriteDone(); 276 friend class EventWrapper<NSGigE, &NSGigE::txDmaWriteDone>; 277 EventWrapper<NSGigE, &NSGigE::txDmaWriteDone> txDmaWriteEvent; 278 279 bool dmaDescFree; 280 bool dmaDataFree; 281 282 protected: 283 Tick txDelay; 284 Tick rxDelay; 285 286 void txReset(); 287 void rxReset(); 288 void regsReset(); 289 290 void rxKick(); 291 Tick rxKickTick; 292 typedef EventWrapper<NSGigE, &NSGigE::rxKick> RxKickEvent; 293 friend void RxKickEvent::process(); 294 RxKickEvent rxKickEvent; 295 296 void txKick(); 297 Tick txKickTick; 298 typedef EventWrapper<NSGigE, &NSGigE::txKick> TxKickEvent; 299 friend void TxKickEvent::process(); 300 TxKickEvent txKickEvent; 301 302 void eepromKick(); 303 304 /** 305 * Retransmit event 306 */ 307 void transmit(); 308 void txEventTransmit() 309 { 310 transmit(); 311 if (txState == txFifoBlock) 312 txKick(); 313 } 314 typedef EventWrapper<NSGigE, &NSGigE::txEventTransmit> TxEvent; 315 friend void TxEvent::process(); 316 TxEvent txEvent; 317 318 void txDump() const; 319 void rxDump() const; 320 321 /** 322 * receive address filter 323 */ 324 bool rxFilterEnable; 325 bool rxFilter(const EthPacketPtr &packet); 326 bool acceptBroadcast; 327 bool acceptMulticast; 328 bool acceptUnicast; 329 bool acceptPerfect; 330 bool acceptArp; 331 bool multicastHashEnable; 332 333 /** 334 * Interrupt management 335 */ 336 void devIntrPost(uint32_t interrupts); 337 void devIntrClear(uint32_t interrupts); 338 void devIntrChangeMask(); 339 340 Tick intrDelay; 341 Tick intrTick; 342 bool cpuPendingIntr; 343 void cpuIntrPost(Tick when); 344 void cpuInterrupt(); 345 void cpuIntrClear(); 346 347 typedef EventWrapper<NSGigE, &NSGigE::cpuInterrupt> IntrEvent; 348 friend void IntrEvent::process(); 349 IntrEvent *intrEvent; 350 NSGigEInt *interface; 351 352 public: 353 struct Params : public PciDev::Params 354 { 355 Tick clock; 356 Tick intr_delay; 357 Tick tx_delay; 358 Tick rx_delay; 359 bool dma_desc_free; 360 bool dma_data_free; 361 Tick dma_read_delay; 362 Tick dma_write_delay; 363 Tick dma_read_factor; 364 Tick dma_write_factor; 365 bool rx_filter; 366 Net::EthAddr eaddr; 367 uint32_t tx_fifo_size; 368 uint32_t rx_fifo_size; 369 bool rx_thread; 370 bool tx_thread; 371 bool rss; 372 bool dma_no_allocate; 373 }; 374 375 NSGigE(Params *params); 376 ~NSGigE(); 377 const Params *params() const { return (const Params *)_params; } 378 379 virtual void writeConfig(int offset, const uint16_t data); 380 381 virtual Tick read(Packet *pkt); 382 virtual Tick write(Packet *pkt); 383 384 bool cpuIntrPending() const; 385 void cpuIntrAck() { cpuIntrClear(); } 386 387 bool recvPacket(EthPacketPtr packet); 388 void transferDone(); 389 390 void setInterface(NSGigEInt *i) { assert(!interface); interface = i; } 391 392 virtual void serialize(std::ostream &os); 393 virtual void unserialize(Checkpoint *cp, const std::string §ion); 394 395 public: 396 void regStats(); 397 398 private: 399 Stats::Scalar<> txBytes; 400 Stats::Scalar<> rxBytes; 401 Stats::Scalar<> txPackets; 402 Stats::Scalar<> rxPackets; 403 Stats::Scalar<> txIpChecksums; 404 Stats::Scalar<> rxIpChecksums; 405 Stats::Scalar<> txTcpChecksums; 406 Stats::Scalar<> rxTcpChecksums; 407 Stats::Scalar<> txUdpChecksums; 408 Stats::Scalar<> rxUdpChecksums; 409 Stats::Scalar<> descDmaReads; 410 Stats::Scalar<> descDmaWrites; 411 Stats::Scalar<> descDmaRdBytes; 412 Stats::Scalar<> descDmaWrBytes; 413 Stats::Formula totBandwidth; 414 Stats::Formula totPackets; 415 Stats::Formula totBytes; 416 Stats::Formula totPacketRate; 417 Stats::Formula txBandwidth; 418 Stats::Formula rxBandwidth; 419 Stats::Formula txPacketRate; 420 Stats::Formula rxPacketRate; 421 Stats::Scalar<> postedSwi; 422 Stats::Formula coalescedSwi; 423 Stats::Scalar<> totalSwi; 424 Stats::Scalar<> postedRxIdle; 425 Stats::Formula coalescedRxIdle; 426 Stats::Scalar<> totalRxIdle; 427 Stats::Scalar<> postedRxOk; 428 Stats::Formula coalescedRxOk; 429 Stats::Scalar<> totalRxOk; 430 Stats::Scalar<> postedRxDesc; 431 Stats::Formula coalescedRxDesc; 432 Stats::Scalar<> totalRxDesc; 433 Stats::Scalar<> postedTxOk; 434 Stats::Formula coalescedTxOk; 435 Stats::Scalar<> totalTxOk; 436 Stats::Scalar<> postedTxIdle; 437 Stats::Formula coalescedTxIdle; 438 Stats::Scalar<> totalTxIdle; 439 Stats::Scalar<> postedTxDesc; 440 Stats::Formula coalescedTxDesc; 441 Stats::Scalar<> totalTxDesc; 442 Stats::Scalar<> postedRxOrn; 443 Stats::Formula coalescedRxOrn; 444 Stats::Scalar<> totalRxOrn; 445 Stats::Formula coalescedTotal; 446 Stats::Scalar<> postedInterrupts; 447 Stats::Scalar<> droppedPackets; 448}; 449 450/* 451 * Ethernet Interface for an Ethernet Device 452 */ 453class NSGigEInt : public EtherInt 454{ 455 private: 456 NSGigE *dev; 457 458 public: 459 NSGigEInt(const std::string &name, NSGigE *d) 460 : EtherInt(name), dev(d) { dev->setInterface(this); } 461 462 virtual bool recvPacket(EthPacketPtr pkt) { return dev->recvPacket(pkt); } 463 virtual void sendDone() { dev->transferDone(); } 464}; 465 466#endif // __DEV_NS_GIGE_HH__ 467