`include "timescale.v" module eth_maccontrol (MTxClk, MRxClk, TxReset, RxReset, TPauseRq, TxDataIn, TxStartFrmIn, TxUsedDataIn, TxEndFrmIn, TxDoneIn, TxAbortIn, RxData, RxValid, RxStartFrm, RxEndFrm, ReceiveEnd, ReceivedPacketGood, ReceivedLengthOK, TxFlow, RxFlow, DlyCrcEn, TxPauseTV, MAC, PadIn, PadOut, CrcEnIn, CrcEnOut, TxDataOut, TxStartFrmOut, TxEndFrmOut, TxDoneOut, TxAbortOut, TxUsedDataOut, WillSendControlFrame, TxCtrlEndFrm, ReceivedPauseFrm, ControlFrmAddressOK, SetPauseTimer, r_PassAll, RxStatusWriteLatched_sync2 ); input MTxClk; // Transmit clock (from PHY) input MRxClk; // Receive clock (from PHY) input TxReset; // Transmit reset input RxReset; // Receive reset input TPauseRq; // Transmit control frame (from host) input [7:0] TxDataIn; // Transmit packet data byte (from host) input TxStartFrmIn; // Transmit packet start frame input (from host) input TxUsedDataIn; // Transmit packet used data (from TxEthMAC) input TxEndFrmIn; // Transmit packet end frame input (from host) input TxDoneIn; // Transmit packet done (from TxEthMAC) input TxAbortIn; // Transmit packet abort (input from TxEthMAC) input PadIn; // Padding (input from registers) input CrcEnIn; // Crc append (input from registers) input [7:0] RxData; // Receive Packet Data (from RxEthMAC) input RxValid; // Received a valid packet input RxStartFrm; // Receive packet start frame (input from RxEthMAC) input RxEndFrm; // Receive packet end frame (input from RxEthMAC) input ReceiveEnd; // End of receiving of the current packet (input from RxEthMAC) input ReceivedPacketGood; // Received packet is good input ReceivedLengthOK; // Length of the received packet is OK input TxFlow; // Tx flow control (from registers) input RxFlow; // Rx flow control (from registers) input DlyCrcEn; // Delayed CRC enabled (from registers) input [15:0] TxPauseTV; // Transmit Pause Timer Value (from registers) input [47:0] MAC; // MAC address (from registers) input RxStatusWriteLatched_sync2; input r_PassAll; output [7:0] TxDataOut; // Transmit Packet Data (to TxEthMAC) output TxStartFrmOut; // Transmit packet start frame (output to TxEthMAC) output TxEndFrmOut; // Transmit packet end frame (output to TxEthMAC) output TxDoneOut; // Transmit packet done (to host) output TxAbortOut; // Transmit packet aborted (to host) output TxUsedDataOut; // Transmit packet used data (to host) output PadOut; // Padding (output to TxEthMAC) output CrcEnOut; // Crc append (output to TxEthMAC) output WillSendControlFrame; output TxCtrlEndFrm; output ReceivedPauseFrm; output ControlFrmAddressOK; output SetPauseTimer; reg TxUsedDataOutDetected; reg TxAbortInLatched; reg TxDoneInLatched; reg MuxedDone; reg MuxedAbort; wire Pause; wire TxCtrlStartFrm; wire [7:0] ControlData; wire CtrlMux; wire SendingCtrlFrm; // Sending Control Frame (enables padding and CRC) wire BlockTxDone; // Signal TxUsedDataOut was detected (a transfer is already in progress) always @ (posedge MTxClk or posedge TxReset) begin if(TxReset) TxUsedDataOutDetected <= 1'b0; else if(TxDoneIn | TxAbortIn) TxUsedDataOutDetected <= 1'b0; else if(TxUsedDataOut) TxUsedDataOutDetected <= 1'b1; end // Latching variables always @ (posedge MTxClk or posedge TxReset) begin if(TxReset) begin TxAbortInLatched <= 1'b0; TxDoneInLatched <= 1'b0; end else begin TxAbortInLatched <= TxAbortIn; TxDoneInLatched <= TxDoneIn; end end // Generating muxed abort signal always @ (posedge MTxClk or posedge TxReset) begin if(TxReset) MuxedAbort <= 1'b0; else if(TxStartFrmIn) MuxedAbort <= 1'b0; else if(TxAbortIn & ~TxAbortInLatched & TxUsedDataOutDetected) MuxedAbort <= 1'b1; end // Generating muxed done signal always @ (posedge MTxClk or posedge TxReset) begin if(TxReset) MuxedDone <= 1'b0; else if(TxStartFrmIn) MuxedDone <= 1'b0; else if(TxDoneIn & (~TxDoneInLatched) & TxUsedDataOutDetected) MuxedDone <= 1'b1; end // TxDoneOut assign TxDoneOut = CtrlMux? ((~TxStartFrmIn) & (~BlockTxDone) & MuxedDone) : ((~TxStartFrmIn) & (~BlockTxDone) & TxDoneIn); // TxAbortOut assign TxAbortOut = CtrlMux? ((~TxStartFrmIn) & (~BlockTxDone) & MuxedAbort) : ((~TxStartFrmIn) & (~BlockTxDone) & TxAbortIn); // TxUsedDataOut assign TxUsedDataOut = ~CtrlMux & TxUsedDataIn; // TxStartFrmOut assign TxStartFrmOut = CtrlMux? TxCtrlStartFrm : (TxStartFrmIn & ~Pause); // TxEndFrmOut assign TxEndFrmOut = CtrlMux? TxCtrlEndFrm : TxEndFrmIn; // TxDataOut[7:0] assign TxDataOut[7:0] = CtrlMux? ControlData[7:0] : TxDataIn[7:0]; // PadOut assign PadOut = PadIn | SendingCtrlFrm; // CrcEnOut assign CrcEnOut = CrcEnIn | SendingCtrlFrm; // Connecting receivecontrol module eth_receivecontrol receivecontrol1 ( .MTxClk(MTxClk), .MRxClk(MRxClk), .TxReset(TxReset), .RxReset(RxReset), .RxData(RxData), .RxValid(RxValid), .RxStartFrm(RxStartFrm), .RxEndFrm(RxEndFrm), .RxFlow(RxFlow), .ReceiveEnd(ReceiveEnd), .MAC(MAC), .DlyCrcEn(DlyCrcEn), .TxDoneIn(TxDoneIn), .TxAbortIn(TxAbortIn), .TxStartFrmOut(TxStartFrmOut), .ReceivedLengthOK(ReceivedLengthOK), .ReceivedPacketGood(ReceivedPacketGood), .TxUsedDataOutDetected(TxUsedDataOutDetected), .Pause(Pause), .ReceivedPauseFrm(ReceivedPauseFrm), .AddressOK(ControlFrmAddressOK), .r_PassAll(r_PassAll), .RxStatusWriteLatched_sync2(RxStatusWriteLatched_sync2), .SetPauseTimer(SetPauseTimer) ); eth_transmitcontrol transmitcontrol1 ( .MTxClk(MTxClk), .TxReset(TxReset), .TxUsedDataIn(TxUsedDataIn), .TxUsedDataOut(TxUsedDataOut), .TxDoneIn(TxDoneIn), .TxAbortIn(TxAbortIn), .TxStartFrmIn(TxStartFrmIn), .TPauseRq(TPauseRq), .TxUsedDataOutDetected(TxUsedDataOutDetected), .TxFlow(TxFlow), .DlyCrcEn(DlyCrcEn), .TxPauseTV(TxPauseTV), .MAC(MAC), .TxCtrlStartFrm(TxCtrlStartFrm), .TxCtrlEndFrm(TxCtrlEndFrm), .SendingCtrlFrm(SendingCtrlFrm), .CtrlMux(CtrlMux), .ControlData(ControlData), .WillSendControlFrame(WillSendControlFrame), .BlockTxDone(BlockTxDone) ); endmodule