⭐ 欢迎来到虫虫下载站! | 📦 资源下载 📁 资源专辑 ℹ️ 关于我们
⭐ 虫虫下载站

📄 eth_subenv.sv

📁 VMM 文档加源码, synopsys公司很好的验证资料
💻 SV
📖 第 1 页 / 共 2 页
字号:
   endtask: tx_driver         task service_irq();      vmm_rw::status_e status;      bit [31:0]       val;      bit              ignore_fr;      bit              TXE, TXB;      ignore_fr = 0;      this.ral.INT_SOURCE.mirror(status);      if (status != vmm_rw::IS_OK) begin         `vmm_fatal(this.log, "Unable to read INT_SOURCE");      end      // Save the interesting flags because the mirror      // will be cleared on write-back      TXE = this.ral.TXE.get();      TXB = this.ral.TXB.get();      // Do an immediate write-back to clear the interrupts      // so we won't miss one      this.ral.INT_SOURCE.write(status, this.ral.INT_SOURCE.get());      if (status != vmm_rw::IS_OK) begin         `vmm_fatal(this.log, "Unable to write-back INT_SOURCE");      end      // Analyze the cause(s) for the interrupt      if (TXE) begin         `vmm_error(this.log, "An error occured during the transmission of a frame");      end            if (TXE || TXB) begin         integer n = 0;         if (this.busy_txbd.size() == 0) begin            `vmm_fatal(this.log, "Internal error: TXE/TXB indicated but no TxBD are busy");         end         // A frame has been transmitted, check the transmit buffers...         while (this.busy_txbd.size() > 0) begin            int bd_addr = this.busy_txbd[0];            bit RD;            // Check if that TxBD has been transmitted            ral.TxBD[bd_addr].RD.read(status, RD);            if (status != vmm_rw::IS_OK) begin               `vmm_fatal(this.log,$psprintf("Unable to READ TxBD[%0d]",                                             bd_addr));            end            // Has this frame been transmitted?            if (RD) begin               // No. This implies the subsequent frames have not               // been transmitted either               if (n == 0) `vmm_error(this.log, "No transmitted TxBD were found");               break;            end            `vmm_trace(this.log, $psprintf("Frame from TxBD[%0d] was transmitted",                                           bd_addr));            // What errors happened when the frame was transmitted?            if (ral.TxBD[bd_addr].UR.get()                || ral.TxBD[bd_addr].RL.get()                || ral.TxBD[bd_addr].LC.get()) begin               string descr = "";               string separator = " ";               if (ral.TxBD[bd_addr].UR.get()) begin                  descr = " Under-run";                  separator = "/";               end               if (ral.TxBD[bd_addr].RL.get()) begin                  descr = {descr, separator, "Retry Limit"};                  separator = "/";               end               if (ral.TxBD[bd_addr].LC.get()) begin                  descr = {descr, separator, "Late Coll"};               end               `vmm_warning(this.log, {"Frame was transmitted with following errors:", descr});            end                            // What non-errors happened?            `vmm_trace(this.log, $psprintf("Frame was transmitted with %0d attempts%s%s",                                           ral.TxBD[bd_addr].RTRY.get(),                                           (ral.TxBD[bd_addr].DF.get()) ? ",ferred" : "",                                           (ral.TxBD[bd_addr].CS.get()) ? ", carrier lost" : ""));                        // Indicate this TxBD is now available            // and free the DMA memory            n++;            this.cfg.avail_txbd.push_back(bd_addr);            this.busy_txbd.pop_front();            this.dma_mam.release_region(this.cfg.dma_bfrs[bd_addr]);         end      end // TXB   endtask: service_irqendclassclass oc_eth_subenv extends vmm_subenv;   oc_eth_subenv_cfg      cfg;   virtual mii_if.passive mii_sigs;   eth_frame_channel      tx_chan;   ral_block_oc_ethernet  ral;   wb_ram                 dma_ram;   vmm_mam                dma_mam;   scoreboard             sb;   eth_frame_atomic_gen   src;   mii_monitor            mon;   frmwr_emulator         frmwr;   function new(string                 inst,                oc_eth_subenv_cfg      cfg,                vmm_consensus          end_test,                virtual mii_if.passive mii_sigs,                eth_frame_channel      tx_chan,                ral_block_oc_ethernet  ral,                wb_ram                 dma_ram,                vmm_mam                dma_mam);      super.new("OcEth SubEnv", inst, end_test);      this.cfg      = cfg;      this.mii_sigs = mii_sigs;      if (tx_chan == null) begin         this.src = new("OcEth SubEnv Src", inst);         tx_chan = this.src.out_chan;         this.src.stop_after_n_insts = this.cfg.run_for_n_frames;         // Make sure the frame generators generate frames with the         // correct SA         this.src.randomized_obj.src = this.cfg.dut_addr;         this.src.randomized_obj.src.rand_mode(0);      end      this.tx_chan  = tx_chan;      this.ral = ral;      this.dma_ram = dma_ram;      this.dma_mam = dma_mam;      this.sb = new(inst, this.cfg);      this.mon = new(inst, 0, this.cfg.mii, this.mii_sigs);      this.frmwr = new(inst, 0, this.cfg, tx_chan, this.sb, this.ral,                       this.dma_ram, this.dma_mam);   endfunction: new   task configure();      vmm_rw::status_e status;      ral.HUGEN.set(0);      ral.CRCEN.set(0);      ral.FULLD.set(1);      ral.PRO.set(1);      ral.TXE_M.set(1);      ral.TXB_M.set(1);      ral.IPGT.set(16'h15);      ral.MINFL.set(16'h000F);      ral.MAXFL.set(cfg.max_frame_len);      ral.TXFLOW.set(1);      ral.RXFLOW.set(1);      ral.PASSALL.set(1);      ral.MAC_ADDR.set(cfg.dut_addr);      ral.TX_BD_NUM.set(cfg.n_tx_bd);      ral.update(status);      if (status !== vmm_rw::IS_OK) begin         `vmm_error(this.log, $psprintf("Unable to configure \"%s\".",                                        ral.get_name()));      end      // Initialize the required number of buffer descriptors      begin         int bd_addr = 0;         `vmm_trace(this.log, $psprintf("Configuring %0d TxBD starting at BD[%0d]",                                        cfg.n_tx_bd, bd_addr));         repeat (cfg.n_tx_bd) begin            ral.TxBD[bd_addr].TxBD_CTRL.set(32'h0000_0000);            ral.TxBD[bd_addr].IRQ.set(1);            if (bd_addr == cfg.n_tx_bd-1) ral.TxBD[bd_addr].WR.set(1'b1);                        ral.TxBD[bd_addr].RD.write(status, 0);            if (status !== vmm_rw::IS_OK) begin               `vmm_error(this.log, $psprintf("Unable to initialize (Tx)BD[%0d] in \"%s\".",                                              bd_addr, ral.get_name()));            end            cfg.avail_txbd.push_back(bd_addr);                        bd_addr++;         end      end      `vmm_trace(this.log, "Enabling Tx paths...");      ral.TXEN.write(status, 1);      if (status !== vmm_rw::IS_OK) begin         `vmm_error(this.log, $psprintf("Unable to configure \"%s\".",                                        ral.get_name()));      end      super.configured();   endtask: configure   virtual task start();      super.start();            if (this.cfg.run_for_n_frames > 0 && this.src != null) begin         this.src.start_xactor();      end      this.frmwr.start_xactor();      this.mon.start_xactor();      fork         forever begin            eth_frame fr;            this.mon.to_phy_chan.get(fr);            this.sb.received_by_phy_side(fr);         end      join_none      if (this.src != null) begin         this.end_test.register_notification(this.src.notify,                                             eth_frame_atomic_gen::DONE);      end      this.end_test.register_channel(this.tx_chan);      this.end_test.register_channel(this.mon.to_phy_chan);      this.end_test.register_xactor(this.frmwr);      this.end_test.register_xactor(this.mon);   endtask: start   virtual task stop();      super.stop();            if (this.src != null) this.src.stop_xactor();   endtask: stop   virtual task cleanup();      super.cleanup();      if (this.cfg.run_for_n_frames > 0) begin         `vmm_error(this.log,                    $psprintf("%0d frames were not seen by the scoreboard",                              this.cfg.run_for_n_frames));      end   endtask: cleanupendclass: oc_eth_subenv`endif

⌨️ 快捷键说明

复制代码 Ctrl + C
搜索代码 Ctrl + F
全屏模式 F11
切换主题 Ctrl + Shift + D
显示快捷键 ?
增大字号 Ctrl + =
减小字号 Ctrl + -