Skip to content

Commit b9746b3

Browse files
committed
Add peer-MSS based logic and fix option-parsing bug in rx_engine
1 parent 693ec94 commit b9746b3

5 files changed

Lines changed: 204 additions & 65 deletions

File tree

hls/toe/rx_engine/rx_engine.cpp

Lines changed: 60 additions & 20 deletions
Original file line numberDiff line numberDiff line change
@@ -638,30 +638,37 @@ void drop_optional_header_fields( hls::stream<optionalFieldsMeta>& metaIn,
638638
* kind | length | description
639639
* 0 | 1B | End of options list
640640
* 1 | 1B | NOP/Padding
641-
* 2 | 4B | MSS (Maximum segment size)
641+
* 2 | 4B | MSS (Maximum segment size) - If omitted, 536B for IPv4
642642
* 3 | 3B | Window scale
643643
* 4 | 2B | SACK permitted (Selective Acknowledgment)
644644
*/
645645
void parse_optional_header_fields( hls::stream<ap_uint<4> >& dataOffsetIn,
646646
hls::stream<ap_uint<320> >& optionalHeaderFieldsIn,
647-
hls::stream<ap_uint<4> >& windowScaleOut)
647+
hls::stream<ap_uint<4> >& windowScaleOut,
648+
hls::stream<ap_uint<16> >& mssOut)
648649
{
649650
#pragma HLS PIPELINE II=1
650651
#pragma HLS INLINE off
651652

652653
enum fsmStateType {IDLE, PARSE};
653654
static fsmStateType state = IDLE;
654-
static ap_uint<4> dataOffset;
655+
static ap_uint<4> dataOffsetDword;
656+
static ap_uint<6> dataOffsetByte;
655657
static ap_uint<320> fields;
658+
static bool got_ws = false;
659+
static bool got_mss = false;
656660

657661
switch (state)
658662
{
659663
case IDLE:
660664
if (!dataOffsetIn.empty() && !optionalHeaderFieldsIn.empty())
661665
{
662666
// std::cout << "PARSE IDLE" << std::endl;
663-
dataOffsetIn.read(dataOffset);
667+
dataOffsetIn.read(dataOffsetDword);
668+
dataOffsetByte = 4 * (ap_int<6>)dataOffsetDword;
664669
optionalHeaderFieldsIn.read(fields);
670+
got_ws = false;
671+
got_mss = false;
665672
state = PARSE;
666673
}
667674
break;
@@ -671,35 +678,64 @@ void parse_optional_header_fields( hls::stream<ap_uint<4> >& dataOffsetIn,
671678

672679
switch (optionKind)
673680
{
674-
case 0: //End of option list
675-
windowScaleOut.write(0);
681+
case 0:{//End of option list
682+
if(!got_mss) mssOut.write(536);
683+
if(!got_ws) windowScaleOut.write(0);
676684
// std::cout << "PARSE EOL" << std::endl;
677685
state = IDLE;
678686
break;
679-
case 1:
680-
optionLength = 1;
687+
}
688+
case 1:{ // NOP
689+
if(dataOffsetByte == 1){
690+
if(!got_mss) mssOut.write(536);
691+
if(!got_ws) windowScaleOut.write(0);
692+
state = IDLE;
693+
}
694+
else optionLength = 1;
681695
break;
682-
case 3:
696+
}
697+
case 2:{
698+
ap_uint<16> mss;
699+
mss(15,8) = fields(23,16);
700+
mss( 7,0) = fields(31,24);
701+
mssOut.write(mss);
702+
if (dataOffsetByte == 4 || got_ws){
703+
if(!got_ws) windowScaleOut.write(0);
704+
state = IDLE;
705+
}
706+
got_mss = true;
707+
optionLength = 4;
708+
break;
709+
}
710+
case 3:{
683711
// std::cout << "PARSE WS: " << (uint16_t)fields(19, 16) << std::endl;
684712
windowScaleOut.write(fields(19, 16));
685-
state = IDLE;
713+
if (dataOffsetByte == 3 || got_mss){
714+
if(!got_mss) mssOut.write((ap_uint<16>)536);
715+
state = IDLE;
716+
}
717+
optionLength = 3;
718+
got_ws = true;
686719
break;
687-
default:
688-
if (dataOffset == optionLength)
689-
{
690-
windowScaleOut.write(0);
720+
}
721+
default:{
722+
if(dataOffsetByte == optionLength){
723+
if(!got_mss) mssOut.write((ap_uint<16>)536);
724+
if(!got_ws) windowScaleOut.write(0);
691725
// std::cout << "PARSE DONE" << std::endl;
692726
state = IDLE;
693727
}
694728
break;
729+
}
695730
}//switch
696-
dataOffset -= optionLength;
731+
dataOffsetByte -= optionLength;
697732
fields = (fields >> (optionLength*8));
698733
break;
699734
}//switch
700735
}
701736

702737
void merge_header_meta(hls::stream<ap_uint<4> >& rxEng_winScaleFifo,
738+
hls::stream<ap_uint<16> >& rxEng_mssFifo,
703739
hls::stream<rxEngineMetaData>& rxEng_headerMetaFifo,
704740
hls::stream<rxEngineMetaData>& rxEng_metaDataFifo)
705741
{
@@ -723,15 +759,17 @@ void merge_header_meta(hls::stream<ap_uint<4> >& rxEng_winScaleFifo,
723759
else
724760
{
725761
meta.winScale = 0;
762+
meta.mss = 536;
726763
rxEng_metaDataFifo.write(meta);
727764
}
728765
}
729766
break;
730767
case 1:
731-
if (!rxEng_winScaleFifo.empty())
768+
if (!rxEng_winScaleFifo.empty() && !rxEng_mssFifo.empty())
732769
{
733770
// std::cout << "META MERGE 1" << std::endl;
734771
meta.winScale = rxEng_winScaleFifo.read();
772+
meta.mss = rxEng_mssFifo.read();
735773
rxEng_metaDataFifo.write(meta);
736774
state = 0;
737775
}
@@ -1368,7 +1406,7 @@ void rxTcpFSM( stream<rxFsmMetaData>& fsmMetaDataFifo,
13681406
// Initialize rxSar, SEQ + phantom byte for recvd and head pointer, offset to 0, gap set to false
13691407
rxEng2rxSar_upd_req.write(rxSarRecvd(fsm_meta.sessionID, fsm_meta.meta.seqNumb+1, fsm_meta.meta.seqNumb+1, 0, false, rx_win_shift));
13701408
// Initialize receive window
1371-
rxEng2txSar_upd_req.write((rxTxSarQuery(fsm_meta.sessionID, 0, fsm_meta.meta.winSize, txSar.cong_window, 0, false, tx_win_shift))); //TODO maybe include count check
1409+
rxEng2txSar_upd_req.write((rxTxSarQuery(fsm_meta.sessionID, 0, fsm_meta.meta.winSize, txSar.cong_window, 0, false, tx_win_shift, fsm_meta.meta.mss))); //TODO maybe include count check
13721410
#else
13731411
// Initialize rxSar, SEQ + phantom byte, last '1' for makes sure appd is initialized
13741412
rxEng2rxSar_upd_req.write(rxSarRecvd(fsm_meta.sessionID, fsm_meta.meta.seqNumb+1, fsm_meta.meta.seqNumb+1, 0, false, 1));
@@ -1432,7 +1470,7 @@ void rxTcpFSM( stream<rxFsmMetaData>& fsmMetaDataFifo,
14321470
ap_uint<4> rx_win_shift = (fsm_meta.meta.winScale == 0) ? 0 : WINDOW_SCALE_BITS;
14331471
ap_uint<4> tx_win_shift = fsm_meta.meta.winScale;
14341472
rxEng2rxSar_upd_req.write(rxSarRecvd(fsm_meta.sessionID, fsm_meta.meta.seqNumb+1, fsm_meta.meta.seqNumb+1, 0, false, rx_win_shift));
1435-
rxEng2txSar_upd_req.write((rxTxSarQuery(fsm_meta.sessionID, fsm_meta.meta.ackNumb, fsm_meta.meta.winSize, txSar.cong_window, 0, false, tx_win_shift))); //TODO maybe include count check
1473+
rxEng2txSar_upd_req.write((rxTxSarQuery(fsm_meta.sessionID, fsm_meta.meta.ackNumb, fsm_meta.meta.winSize, txSar.cong_window, 0, false, tx_win_shift, fsm_meta.meta.mss))); //TODO maybe include count check
14361474
#else
14371475
//initialize rx_sar, SEQ + phantom byte, last '1' for appd init
14381476
rxEng2rxSar_upd_req.write(rxSarRecvd(fsm_meta.sessionID, fsm_meta.meta.seqNumb+1, fsm_meta.meta.seqNumb+1, 0, false, 1));
@@ -2103,10 +2141,12 @@ void rx_engine( stream<net_axis<WIDTH> >& ipRxData,
21032141
static hls::stream<ap_uint<4> > rxEng_dataOffsetFifo("rxEng_dataOffsetFifo");
21042142
static hls::stream<ap_uint<320> > rxEng_optionalFieldsFifo("rxEng_optionalFieldsFifo");
21052143
static hls::stream<ap_uint<4> > rxEng_winScaleFifo("rxEng_winScaleFifo");
2144+
static hls::stream<ap_uint<16> > rxEng_mssFifo("rxEng_mssFifo");
21062145
#pragma HLS stream variable=rxEng_headerMetaFifo depth=16
21072146
#pragma HLS stream variable=rxEng_dataOffsetFifo depth=2
21082147
#pragma HLS stream variable=rxEng_optionalFieldsFifo depth=2
21092148
#pragma HLS stream variable=rxEng_winScaleFifo depth=2
2149+
#pragma HLS stream variable=rxEng_mssFifo depth=2
21102150
//TODO data pack
21112151
#endif
21122152

@@ -2136,8 +2176,8 @@ void rx_engine( stream<net_axis<WIDTH> >& ipRxData,
21362176
//rxTcpInvalidDropper<WIDTH>(rxEng_dataBuffer3b, rxEng_tcpValidFifo, rxEng_dataBuffer3);
21372177

21382178
#if (WINDOW_SCALE)
2139-
parse_optional_header_fields(rxEng_dataOffsetFifo, rxEng_optionalFieldsFifo, rxEng_winScaleFifo);
2140-
merge_header_meta(rxEng_winScaleFifo, rxEng_headerMetaFifo, rxEng_metaDataFifo);
2179+
parse_optional_header_fields(rxEng_dataOffsetFifo, rxEng_optionalFieldsFifo, rxEng_winScaleFifo, rxEng_mssFifo);
2180+
merge_header_meta(rxEng_winScaleFifo, rxEng_mssFifo, rxEng_headerMetaFifo, rxEng_metaDataFifo);
21412181
#endif
21422182

21432183
rxMetadataHandler( rxEng_metaDataFifo,

hls/toe/rx_engine/rx_engine.hpp

Lines changed: 1 addition & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -66,6 +66,7 @@ struct rxEngineMetaData
6666
ap_uint<1> fin;
6767
ap_uint<4> dataOffset;
6868
//ap_uint<16> dstPort;
69+
ap_uint<16> mss; // peer MSS
6970
};
7071

7172
/** @ingroup rx_engine

hls/toe/toe_internals.hpp

Lines changed: 27 additions & 3 deletions
Original file line numberDiff line numberDiff line change
@@ -185,6 +185,7 @@ struct txSarEntry
185185
ap_uint<16> recv_window;
186186
#if (WINDOW_SCALE)
187187
ap_uint<4> win_shift;
188+
ap_uint<16> peer_mss;
188189
#endif
189190
ap_uint<WINDOW_BITS> cong_window;
190191
ap_uint<WINDOW_BITS> slowstart_threshold;
@@ -205,6 +206,7 @@ struct rxTxSarQuery
205206
bool fastRetransmitted;
206207
#if (WINDOW_SCALE)
207208
ap_uint<4> win_shift;
209+
ap_uint<16> peer_mss;
208210
#endif
209211
ap_uint<1> write;
210212
ap_uint<1> init;
@@ -215,7 +217,9 @@ struct rxTxSarQuery
215217
:sessionID(id), ackd(ackd), recv_window(recv_win), cong_window(cong_win), count(count), fastRetransmitted(fastRetransmitted), write(1), init(0) {}
216218
#if (WINDOW_SCALE)
217219
rxTxSarQuery(ap_uint<16> id, ap_uint<32> ackd, ap_uint<16> recv_win, ap_uint<WINDOW_BITS> cong_win, ap_uint<2> count, bool fastRetransmitted, ap_uint<4> win_shift)
218-
:sessionID(id), ackd(ackd), recv_window(recv_win), cong_window(cong_win), count(count), fastRetransmitted(fastRetransmitted), win_shift(win_shift), write(1), init(1) {}
220+
:sessionID(id), ackd(ackd), recv_window(recv_win), cong_window(cong_win), count(count), fastRetransmitted(fastRetransmitted), win_shift(win_shift), write(1), init(1), peer_mss(0) {}
221+
rxTxSarQuery(ap_uint<16> id, ap_uint<32> ackd, ap_uint<16> recv_win, ap_uint<WINDOW_BITS> cong_win, ap_uint<2> count, bool fastRetransmitted, ap_uint<4> win_shift, ap_uint<16> peer_mss)
222+
:sessionID(id), ackd(ackd), recv_window(recv_win), cong_window(cong_win), count(count), fastRetransmitted(fastRetransmitted), win_shift(win_shift), write(1), init(1), peer_mss(peer_mss) {}
219223
#endif
220224
};
221225

@@ -241,6 +245,17 @@ struct txTxSarQuery
241245
:sessionID(id), not_ackd(not_ackd), write(write), init(init), finReady(finReady), finSent(finSent), isRtQuery(isRt) {}
242246
};
243247

248+
struct txDDRbypassPush
249+
{
250+
bool isBypass;
251+
ap_uint<16> session_mss;
252+
txDDRbypassPush() {}
253+
txDDRbypassPush(bool en)
254+
:isBypass(en),session_mss(576) {}
255+
txDDRbypassPush(bool en, ap_uint<16> mss)
256+
:isBypass(en),session_mss(mss) {}
257+
};
258+
244259
struct txTxSarRtQuery : public txTxSarQuery
245260
{
246261
txTxSarRtQuery() {}
@@ -338,12 +353,21 @@ struct txTxSarReply
338353
ap_uint<WINDOW_BITS> usedLength;
339354
bool finReady;
340355
bool finSent;
341-
//#if (WINDOW_SCALE)
342356
ap_uint<4> win_shift;
343-
//#endif
357+
#if (WINDOW_SCALE)
358+
ap_uint<16> peer_mss;
359+
#endif
344360
txTxSarReply() {}
361+
#if (WINDOW_SCALE)
362+
txTxSarReply(ap_uint<32> ack, ap_uint<32> nack, ap_uint<WINDOW_BITS> usableWindow, ap_uint<WINDOW_BITS> app, ap_uint<WINDOW_BITS> usedLength, bool finReady, bool finSent)
363+
:ackd(ack), not_ackd(nack), usableWindow(usableWindow), app(app), usedLength(usedLength), finReady(finReady), finSent(finSent), peer_mss(0) {}
364+
txTxSarReply(ap_uint<32> ack, ap_uint<32> nack, ap_uint<WINDOW_BITS> usableWindow, ap_uint<WINDOW_BITS> app, ap_uint<WINDOW_BITS> usedLength, bool finReady, bool finSent, ap_uint<16> peer_mss)
365+
:ackd(ack), not_ackd(nack), usableWindow(usableWindow), app(app), usedLength(usedLength), finReady(finReady), finSent(finSent), peer_mss(peer_mss) {}
366+
#else
345367
txTxSarReply(ap_uint<32> ack, ap_uint<32> nack, ap_uint<WINDOW_BITS> usableWindow, ap_uint<WINDOW_BITS> app, ap_uint<WINDOW_BITS> usedLength, bool finReady, bool finSent)
346368
:ackd(ack), not_ackd(nack), usableWindow(usableWindow), app(app), usedLength(usedLength), finReady(finReady), finSent(finSent) {}
369+
#endif
370+
347371
};
348372

349373
struct rxRetransmitTimerUpdate {

0 commit comments

Comments
 (0)