ns_gige.hh revision 1817
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 29/** @file 30 * Device module for modelling the National Semiconductor 31 * DP83820 ethernet controller 32 */ 33 34#ifndef __DEV_NS_GIGE_HH__ 35#define __DEV_NS_GIGE_HH__ 36 37#include "base/inet.hh" 38#include "base/statistics.hh" 39#include "dev/etherint.hh" 40#include "dev/etherpkt.hh" 41#include "dev/io_device.hh" 42#include "dev/ns_gige_reg.h" 43#include "dev/pcidev.hh" 44#include "dev/pktfifo.hh" 45#include "mem/bus/bus.hh" 46#include "sim/eventq.hh" 47 48/** 49 * Ethernet device registers 50 */ 51struct dp_regs { 52 uint32_t command; 53 uint32_t config; 54 uint32_t mear; 55 uint32_t ptscr; 56 uint32_t isr; 57 uint32_t imr; 58 uint32_t ier; 59 uint32_t ihr; 60 uint32_t txdp; 61 uint32_t txdp_hi; 62 uint32_t txcfg; 63 uint32_t gpior; 64 uint32_t rxdp; 65 uint32_t rxdp_hi; 66 uint32_t rxcfg; 67 uint32_t pqcr; 68 uint32_t wcsr; 69 uint32_t pcr; 70 uint32_t rfcr; 71 uint32_t rfdr; 72 uint32_t srr; 73 uint32_t mibc; 74 uint32_t vrcr; 75 uint32_t vtcr; 76 uint32_t vdr; 77 uint32_t ccsr; 78 uint32_t tbicr; 79 uint32_t tbisr; 80 uint32_t tanar; 81 uint32_t tanlpar; 82 uint32_t taner; 83 uint32_t tesr; 84}; 85 86struct dp_rom { 87 /** 88 * for perfect match memory. 89 * the linux driver doesn't use any other ROM 90 */ 91 uint8_t perfectMatch[ETH_ADDR_LEN]; 92}; 93 94class NSGigEInt; 95class PhysicalMemory; 96class BaseInterface; 97class HierParams; 98class Bus; 99class PciConfigAll; 100 101/** 102 * NS DP83820 Ethernet device model 103 */ 104class NSGigE : public PciDev 105{ 106 public: 107 /** Transmit State Machine states */ 108 enum TxState 109 { 110 txIdle, 111 txDescRefr, 112 txDescRead, 113 txFifoBlock, 114 txFragRead, 115 txDescWrite, 116 txAdvance 117 }; 118 119 /** Receive State Machine States */ 120 enum RxState 121 { 122 rxIdle, 123 rxDescRefr, 124 rxDescRead, 125 rxFifoBlock, 126 rxFragWrite, 127 rxDescWrite, 128 rxAdvance 129 }; 130 131 enum DmaState 132 { 133 dmaIdle, 134 dmaReading, 135 dmaWriting, 136 dmaReadWaiting, 137 dmaWriteWaiting 138 }; 139 140 private: 141 Addr addr; 142 static const Addr size = sizeof(dp_regs); 143 144 protected: 145 typedef std::deque<PacketPtr> pktbuf_t; 146 typedef pktbuf_t::iterator pktiter_t; 147 148 /** device register file */ 149 dp_regs regs; 150 dp_rom rom; 151 152 /** pci settings */ 153 bool ioEnable; 154#if 0 155 bool memEnable; 156 bool bmEnable; 157#endif 158 159 /*** BASIC STRUCTURES FOR TX/RX ***/ 160 /* Data FIFOs */ 161 PacketFifo txFifo; 162 PacketFifo rxFifo; 163 164 /** various helper vars */ 165 PacketPtr txPacket; 166 PacketPtr rxPacket; 167 uint8_t *txPacketBufPtr; 168 uint8_t *rxPacketBufPtr; 169 uint32_t txXferLen; 170 uint32_t rxXferLen; 171 bool rxDmaFree; 172 bool txDmaFree; 173 174 /** DescCaches */ 175 ns_desc txDescCache; 176 ns_desc rxDescCache; 177 178 /* state machine cycle time */ 179 Tick clock; 180 inline Tick cycles(int numCycles) const { return numCycles * clock; } 181 182 /* tx State Machine */ 183 TxState txState; 184 bool txEnable; 185 186 /** Current Transmit Descriptor Done */ 187 bool CTDD; 188 /** halt the tx state machine after next packet */ 189 bool txHalt; 190 /** ptr to the next byte in the current fragment */ 191 Addr txFragPtr; 192 /** count of bytes remaining in the current descriptor */ 193 uint32_t txDescCnt; 194 DmaState txDmaState; 195 196 /** rx State Machine */ 197 RxState rxState; 198 bool rxEnable; 199 200 /** Current Receive Descriptor Done */ 201 bool CRDD; 202 /** num of bytes in the current packet being drained from rxDataFifo */ 203 uint32_t rxPktBytes; 204 /** halt the rx state machine after current packet */ 205 bool rxHalt; 206 /** ptr to the next byte in current fragment */ 207 Addr rxFragPtr; 208 /** count of bytes remaining in the current descriptor */ 209 uint32_t rxDescCnt; 210 DmaState rxDmaState; 211 212 bool extstsEnable; 213 214 protected: 215 Tick dmaReadDelay; 216 Tick dmaWriteDelay; 217 218 Tick dmaReadFactor; 219 Tick dmaWriteFactor; 220 221 void *rxDmaData; 222 Addr rxDmaAddr; 223 int rxDmaLen; 224 bool doRxDmaRead(); 225 bool doRxDmaWrite(); 226 void rxDmaReadCopy(); 227 void rxDmaWriteCopy(); 228 229 void *txDmaData; 230 Addr txDmaAddr; 231 int txDmaLen; 232 bool doTxDmaRead(); 233 bool doTxDmaWrite(); 234 void txDmaReadCopy(); 235 void txDmaWriteCopy(); 236 237 void rxDmaReadDone(); 238 friend class EventWrapper<NSGigE, &NSGigE::rxDmaReadDone>; 239 EventWrapper<NSGigE, &NSGigE::rxDmaReadDone> rxDmaReadEvent; 240 241 void rxDmaWriteDone(); 242 friend class EventWrapper<NSGigE, &NSGigE::rxDmaWriteDone>; 243 EventWrapper<NSGigE, &NSGigE::rxDmaWriteDone> rxDmaWriteEvent; 244 245 void txDmaReadDone(); 246 friend class EventWrapper<NSGigE, &NSGigE::txDmaReadDone>; 247 EventWrapper<NSGigE, &NSGigE::txDmaReadDone> txDmaReadEvent; 248 249 void txDmaWriteDone(); 250 friend class EventWrapper<NSGigE, &NSGigE::txDmaWriteDone>; 251 EventWrapper<NSGigE, &NSGigE::txDmaWriteDone> txDmaWriteEvent; 252 253 bool dmaDescFree; 254 bool dmaDataFree; 255 256 257 protected: 258 Tick txDelay; 259 Tick rxDelay; 260 261 void txReset(); 262 void rxReset(); 263 void regsReset(); 264 265 void rxKick(); 266 Tick rxKickTick; 267 typedef EventWrapper<NSGigE, &NSGigE::rxKick> RxKickEvent; 268 friend void RxKickEvent::process(); 269 RxKickEvent rxKickEvent; 270 271 void txKick(); 272 Tick txKickTick; 273 typedef EventWrapper<NSGigE, &NSGigE::txKick> TxKickEvent; 274 friend void TxKickEvent::process(); 275 TxKickEvent txKickEvent; 276 277 /** 278 * Retransmit event 279 */ 280 void transmit(); 281 void txEventTransmit() 282 { 283 transmit(); 284 if (txState == txFifoBlock) 285 txKick(); 286 } 287 typedef EventWrapper<NSGigE, &NSGigE::txEventTransmit> TxEvent; 288 friend void TxEvent::process(); 289 TxEvent txEvent; 290 291 void txDump() const; 292 void rxDump() const; 293 294 /** 295 * receive address filter 296 */ 297 bool rxFilterEnable; 298 bool rxFilter(const PacketPtr &packet); 299 bool acceptBroadcast; 300 bool acceptMulticast; 301 bool acceptUnicast; 302 bool acceptPerfect; 303 bool acceptArp; 304 305 PhysicalMemory *physmem; 306 307 /** 308 * Interrupt management 309 */ 310 void devIntrPost(uint32_t interrupts); 311 void devIntrClear(uint32_t interrupts); 312 void devIntrChangeMask(); 313 314 Tick intrDelay; 315 Tick intrTick; 316 bool cpuPendingIntr; 317 void cpuIntrPost(Tick when); 318 void cpuInterrupt(); 319 void cpuIntrClear(); 320 321 typedef EventWrapper<NSGigE, &NSGigE::cpuInterrupt> IntrEvent; 322 friend void IntrEvent::process(); 323 IntrEvent *intrEvent; 324 NSGigEInt *interface; 325 326 public: 327 struct Params : public PciDev::Params 328 { 329 PhysicalMemory *pmem; 330 HierParams *hier; 331 Bus *header_bus; 332 Bus *payload_bus; 333 Tick clock; 334 Tick intr_delay; 335 Tick tx_delay; 336 Tick rx_delay; 337 Tick pio_latency; 338 bool dma_desc_free; 339 bool dma_data_free; 340 Tick dma_read_delay; 341 Tick dma_write_delay; 342 Tick dma_read_factor; 343 Tick dma_write_factor; 344 bool rx_filter; 345 Net::EthAddr eaddr; 346 uint32_t tx_fifo_size; 347 uint32_t rx_fifo_size; 348 uint32_t m5reg; 349 bool dma_no_allocate; 350 }; 351 352 NSGigE(Params *params); 353 ~NSGigE(); 354 const Params *params() const { return (const Params *)_params; } 355 356 virtual void writeConfig(int offset, int size, const uint8_t *data); 357 virtual void readConfig(int offset, int size, uint8_t *data); 358 359 virtual Fault read(MemReqPtr &req, uint8_t *data); 360 virtual Fault write(MemReqPtr &req, const uint8_t *data); 361 362 bool cpuIntrPending() const; 363 void cpuIntrAck() { cpuIntrClear(); } 364 365 bool recvPacket(PacketPtr packet); 366 void transferDone(); 367 368 void setInterface(NSGigEInt *i) { assert(!interface); interface = i; } 369 370 virtual void serialize(std::ostream &os); 371 virtual void unserialize(Checkpoint *cp, const std::string §ion); 372 373 public: 374 void regStats(); 375 376 private: 377 Stats::Scalar<> txBytes; 378 Stats::Scalar<> rxBytes; 379 Stats::Scalar<> txPackets; 380 Stats::Scalar<> rxPackets; 381 Stats::Scalar<> txIpChecksums; 382 Stats::Scalar<> rxIpChecksums; 383 Stats::Scalar<> txTcpChecksums; 384 Stats::Scalar<> rxTcpChecksums; 385 Stats::Scalar<> txUdpChecksums; 386 Stats::Scalar<> rxUdpChecksums; 387 Stats::Scalar<> descDmaReads; 388 Stats::Scalar<> descDmaWrites; 389 Stats::Scalar<> descDmaRdBytes; 390 Stats::Scalar<> descDmaWrBytes; 391 Stats::Formula totBandwidth; 392 Stats::Formula totPackets; 393 Stats::Formula totBytes; 394 Stats::Formula totPacketRate; 395 Stats::Formula txBandwidth; 396 Stats::Formula rxBandwidth; 397 Stats::Formula txPacketRate; 398 Stats::Formula rxPacketRate; 399 Stats::Scalar<> postedSwi; 400 Stats::Formula coalescedSwi; 401 Stats::Scalar<> totalSwi; 402 Stats::Scalar<> postedRxIdle; 403 Stats::Formula coalescedRxIdle; 404 Stats::Scalar<> totalRxIdle; 405 Stats::Scalar<> postedRxOk; 406 Stats::Formula coalescedRxOk; 407 Stats::Scalar<> totalRxOk; 408 Stats::Scalar<> postedRxDesc; 409 Stats::Formula coalescedRxDesc; 410 Stats::Scalar<> totalRxDesc; 411 Stats::Scalar<> postedTxOk; 412 Stats::Formula coalescedTxOk; 413 Stats::Scalar<> totalTxOk; 414 Stats::Scalar<> postedTxIdle; 415 Stats::Formula coalescedTxIdle; 416 Stats::Scalar<> totalTxIdle; 417 Stats::Scalar<> postedTxDesc; 418 Stats::Formula coalescedTxDesc; 419 Stats::Scalar<> totalTxDesc; 420 Stats::Scalar<> postedRxOrn; 421 Stats::Formula coalescedRxOrn; 422 Stats::Scalar<> totalRxOrn; 423 Stats::Formula coalescedTotal; 424 Stats::Scalar<> postedInterrupts; 425 Stats::Scalar<> droppedPackets; 426 427 public: 428 Tick cacheAccess(MemReqPtr &req); 429}; 430 431/* 432 * Ethernet Interface for an Ethernet Device 433 */ 434class NSGigEInt : public EtherInt 435{ 436 private: 437 NSGigE *dev; 438 439 public: 440 NSGigEInt(const std::string &name, NSGigE *d) 441 : EtherInt(name), dev(d) { dev->setInterface(this); } 442 443 virtual bool recvPacket(PacketPtr pkt) { return dev->recvPacket(pkt); } 444 virtual void sendDone() { dev->transferDone(); } 445}; 446 447#endif // __DEV_NS_GIGE_HH__ 448