From cb2e60309b698d80b85113e67599486314e0a974 Mon Sep 17 00:00:00 2001 From: zhe <zhe@inf.ethz.ch> Date: Mon, 9 Mar 2020 21:16:21 +0100 Subject: [PATCH] try to make ooo running --- hls/toe/event_engine/event_engine.cpp | 3 + hls/toe/rx_engine/rx_engine.cpp | 312 ++++++++++++++++++++++---- hls/toe/rx_sar_table/rx_sar_table.cpp | 3 + hls/toe/toe_internals.hpp | 26 ++- hls/toe/tx_engine/tx_engine.cpp | 139 +++++++++--- 5 files changed, 400 insertions(+), 83 deletions(-) diff --git a/hls/toe/event_engine/event_engine.cpp b/hls/toe/event_engine/event_engine.cpp index 50fe72a..e7c7359 100755 --- a/hls/toe/event_engine/event_engine.cpp +++ b/hls/toe/event_engine/event_engine.cpp @@ -77,6 +77,7 @@ void event_engine( stream<event>& txApp2eventEng_setEvent, { rxEng2eventEng_setEvent.read(ev); eventEng2txEng_event.write(ev); + std::cout<<"rxEng2eventEng_setEvent:"<<ev.type<<std::endl; ee_writeCounter++; } else if (ee_writeCounter == ee_adReadCounter && ee_adWriteCounter == ee_txEngReadCounter) @@ -86,12 +87,14 @@ void event_engine( stream<event>& txApp2eventEng_setEvent, { timer2eventEng_setEvent.read(ev); eventEng2txEng_event.write(ev); + std::cout<<"timer2eventEng_setEvent:"<<ev.type<<std::endl; ee_writeCounter++; } else if (!txApp2eventEng_setEvent.empty()) { txApp2eventEng_setEvent.read(ev); eventEng2txEng_event.write(ev); + std::cout<<"txApp2eventEng_setEvent:"<<ev.type<<std::endl; ee_writeCounter++; } } diff --git a/hls/toe/rx_engine/rx_engine.cpp b/hls/toe/rx_engine/rx_engine.cpp index 8eb1871..9d16f75 100755 --- a/hls/toe/rx_engine/rx_engine.cpp +++ b/hls/toe/rx_engine/rx_engine.cpp @@ -49,9 +49,9 @@ void process_ipv4( stream<net_axis<WIDTH> >& dataIn, if (!dataIn.empty()) { net_axis<WIDTH> currWord = dataIn.read(); - std::cout << "IP process: "; - printLE(std::cout, currWord); - std::cout << std::endl; + // std::cout << "IP process: "; + // printLE(std::cout, currWord); + // std::cout << std::endl; header.parseWord(currWord.data); if (header.isReady()) @@ -171,7 +171,7 @@ void prependPseudoHeader( hls::stream<net_axis<WIDTH> >& headerIn, if (currWord.last) { - std::cout << "PREPEND" << std::endl; + // std::cout << "PREPEND" << std::endl; state = HEADER; } } @@ -397,11 +397,13 @@ void rxCheckTCPchecksum(stream<net_axis<64> >& dataIn, if (csa_meta.length != 0) { validFifoOut.write(true); + std::cout<<"checksum correct"<<std::endl; } } else if(csa_meta.length != 0) { validFifoOut.write(false); + std::cout<<"checksum not correct!!!"<<std::endl; } csa_checkChecksum = false; csa_tcp_sums[0] = 0; @@ -435,9 +437,9 @@ void processPseudoHeader(stream<net_axis<WIDTH> >& dataIn, if (!dataIn.empty() && (!firstWord || !validFifoIn.empty())) { net_axis<WIDTH> word = dataIn.read(); - std::cout << "PROCESS TCP: "; - printLE(std::cout, word); - std::cout << std::endl; + // std::cout << "PROCESS TCP: "; + // printLE(std::cout, word); + // std::cout << std::endl; header.parseWord(word.data); if (firstWord) { @@ -480,7 +482,7 @@ void processPseudoHeader(stream<net_axis<WIDTH> >& dataIn, } if (meta.length != 0) { - std::cout << "VALID WRITE: " << std::dec << meta.length << ", " << header.getLength() << ", " << header.getDataOffset() << std::endl; + // std::cout << "VALID WRITE: " << std::dec << meta.length << ", " << header.getLength() << ", " << header.getDataOffset() << std::endl; } metaWritten = true; @@ -527,10 +529,10 @@ void drop_optional_header_fields( hls::stream<optionalFieldsMeta>& metaIn, optionalFieldsMeta meta = metaIn.read(); net_axis<WIDTH> currWord = dataIn.read(); dataOffset = meta.dataOffset;// - 5; - std::cout << "OFFSET: " << dataOffset << std::endl; - std::cout << "DROP OO: "; - printLE(std::cout, currWord); - std::cout << std::endl; + // std::cout << "OFFSET: " << dataOffset << std::endl; + // std::cout << "DROP OO: "; + // printLE(std::cout, currWord); + // std::cout << std::endl; optionalHeader.parseWord(currWord.data); parseHeader = false; @@ -545,7 +547,7 @@ void drop_optional_header_fields( hls::stream<optionalFieldsMeta>& metaIn, if (meta.syn) { parseHeader = true; - std::cout << "WRITE Optional Fields" << std::endl; + // std::cout << "WRITE Optional Fields" << std::endl; dataOffsetOut.write(dataOffset); if (optionalHeader.isReady() || currWord.last) { @@ -657,7 +659,7 @@ void parse_optional_header_fields( hls::stream<ap_uint<4> >& dataOffsetIn, case IDLE: if (!dataOffsetIn.empty() && !optionalHeaderFieldsIn.empty()) { - std::cout << "PARSE IDLE" << std::endl; + // std::cout << "PARSE IDLE" << std::endl; dataOffsetIn.read(dataOffset); optionalHeaderFieldsIn.read(fields); state = PARSE; @@ -671,14 +673,14 @@ void parse_optional_header_fields( hls::stream<ap_uint<4> >& dataOffsetIn, { case 0: //End of option list windowScaleOut.write(0); - std::cout << "PARSE EOL" << std::endl; + // std::cout << "PARSE EOL" << std::endl; state = IDLE; break; case 1: optionLength = 1; break; case 3: - std::cout << "PARSE WS: " << (uint16_t)fields(19, 16) << std::endl; + // std::cout << "PARSE WS: " << (uint16_t)fields(19, 16) << std::endl; windowScaleOut.write(fields(19, 16)); state = IDLE; break; @@ -686,7 +688,7 @@ void parse_optional_header_fields( hls::stream<ap_uint<4> >& dataOffsetIn, if (dataOffset == optionLength) { windowScaleOut.write(0); - std::cout << "PARSE DONE" << std::endl; + // std::cout << "PARSE DONE" << std::endl; state = IDLE; } break; @@ -712,7 +714,7 @@ void merge_header_meta(hls::stream<ap_uint<4> >& rxEng_winScaleFifo, case 0: if (!rxEng_headerMetaFifo.empty()) { - std::cout << "META MERGE 0" << std::endl; + // std::cout << "META MERGE 0" << std::endl; rxEng_headerMetaFifo.read(meta); if (meta.syn && meta.dataOffset > 5) { @@ -728,7 +730,7 @@ void merge_header_meta(hls::stream<ap_uint<4> >& rxEng_winScaleFifo, case 1: if (!rxEng_winScaleFifo.empty()) { - std::cout << "META MERGE 1" << std::endl; + // std::cout << "META MERGE 1" << std::endl; meta.winScale = rxEng_winScaleFifo.read(); rxEng_metaDataFifo.write(meta); state = 0; @@ -1067,29 +1069,188 @@ void rxTcpFSM( stream<rxFsmMetaData>& fsmMetaDataFifo, rxEng2txSar_upd_req.write((rxTxSarQuery(fsm_meta.sessionID, fsm_meta.meta.ackNumb, fsm_meta.meta.winSize, txSar.cong_window, txSar.count, ((txSar.count == 3) || txSar.fastRetransmitted)))); } +// // Check if packet contains payload +// if (fsm_meta.meta.length != 0) +// { +// ap_uint<32> newRecvd = fsm_meta.meta.seqNumb+fsm_meta.meta.length; +// // Second part makes sure that app pointer is not overtaken +// #if !(RX_DDR_BYPASS) +// ap_uint<WINDOW_BITS> free_space = ((rxSar.appd - rxSar.recvd(WINDOW_BITS-1, 0)) - 1); +// // Check if segment in order and if enough free space is available +// if ((fsm_meta.meta.seqNumb == rxSar.recvd) && (free_space > fsm_meta.meta.length)) +// #else +// if ((fsm_meta.meta.seqNumb == rxSar.recvd) && ((rxbuffer_max_data_count - rxbuffer_data_count) > 375)) +// #endif +// { +// rxEng2rxSar_upd_req.write(rxSarRecvd(fsm_meta.sessionID, newRecvd)); +// // Build memory address +// ap_uint<32> pkgAddr; +// pkgAddr(31, 30) = 0x0; +// pkgAddr(29, WINDOW_BITS) = fsm_meta.sessionID(13, 0); +// pkgAddr(WINDOW_BITS-1, 0) = fsm_meta.meta.seqNumb(WINDOW_BITS-1, 0); +// #if !(RX_DDR_BYPASS) +// rxBufferWriteCmd.write(mmCmd(pkgAddr, fsm_meta.meta.length)); +// #endif +// // Only notify about new data available +// rxEng2rxApp_notification.write(appNotification(fsm_meta.sessionID, fsm_meta.meta.length, fsm_meta.srcIpAddress, fsm_meta.dstIpPort)); +// dropDataFifoOut.write(false); +// } +// else +// { +// dropDataFifoOut.write(true); +// } + + +// // Sent ACK +// //rxEng2eventEng_setEvent.write(event(ACK, fsm_meta.sessionID)); +// } + +#if !(RX_DDR_BYPASS) //if enable DDR, OOO is enabled + // Check if packet contains payload + // Second part makes sure that app pointer is not overtaken + ap_uint<WINDOW_BITS> free_space = ((rxSar.appd - rxSar.head(WINDOW_BITS-1, 0)) - 1); + + if (fsm_meta.meta.length != 0) + { + + // Build memory address + ap_uint<32> pkgAddr; + pkgAddr(31, 30) = 0x0; + pkgAddr(29, WINDOW_BITS) = fsm_meta.sessionID(13, 0); + pkgAddr(WINDOW_BITS-1, 0) = fsm_meta.meta.seqNumb(WINDOW_BITS-1, 0); + + ap_uint<32> newRecvd = 0; + ap_uint<32> newHead = 0; + ap_uint<WINDOW_BITS> newOffset = 0; + // ### No gap, packet comes in order + if (!rxSar.gap && (fsm_meta.meta.seqNumb == rxSar.recvd) && (free_space > fsm_meta.meta.length)) + { + std::cout<<"RX_ACK: no gap in order"; + std::cout<<std::dec<<" session id:"<<fsm_meta.sessionID; + std::cout<<" seqNum:"<<fsm_meta.meta.seqNumb; + std::cout<<" recvd:"<<rxSar.recvd; + std::cout<<" head:"<<rxSar.head; + std::cout<<" offset:"<<rxSar.offset; + std::cout<<" length:"<<fsm_meta.meta.length; + std::cout<<" gap:"<<rxSar.gap; + std::cout<<" free_space:"<<free_space<<std::endl; + //increment both head and recvd pointers + newRecvd = fsm_meta.meta.seqNumb+fsm_meta.meta.length; + newHead = fsm_meta.meta.seqNumb+fsm_meta.meta.length; + //update head and recvd pointers + rxEng2rxSar_upd_req.write(rxSarRecvd(fsm_meta.sessionID, newRecvd, newHead, rxSar.offset, rxSar.gap)); + //write to memory + rxBufferWriteCmd.write(mmCmd(pkgAddr, fsm_meta.meta.length)); + // Notify app length bytes available + rxEng2rxApp_notification.write(appNotification(fsm_meta.sessionID, fsm_meta.meta.length, fsm_meta.srcIpAddress, fsm_meta.dstIpPort)); + dropDataFifoOut.write(false); + } + // ### No gap, packet comes out-of-order + else if (!rxSar.gap && (fsm_meta.meta.seqNumb > rxSar.recvd) && (free_space > (fsm_meta.meta.seqNumb+fsm_meta.meta.length- rxSar.head)(WINDOW_BITS-1, 0))) + { + std::cout<<"RX_ACK: no gap ooo"; + std::cout<<std::dec<<" session id:"<<fsm_meta.sessionID; + std::cout<<" seqNum:"<<fsm_meta.meta.seqNumb; + std::cout<<" recvd:"<<rxSar.recvd; + std::cout<<" head:"<<rxSar.head; + std::cout<<" offset:"<<rxSar.offset; + std::cout<<" length:"<<fsm_meta.meta.length; + std::cout<<" gap:"<<rxSar.gap; + std::cout<<" free_space:"<<free_space<<std::endl; + //increment head pointer, set offset to ooo sequence number + newHead = fsm_meta.meta.seqNumb+fsm_meta.meta.length; + newOffset = fsm_meta.meta.seqNumb(WINDOW_BITS-1, 0); + //update head and offset pointer, set gap to true + rxEng2rxSar_upd_req.write(rxSarRecvd(fsm_meta.sessionID, rxSar.recvd, newHead, newOffset, true)); + //notification for matching the mem write status in notificationDelayer + rxEng2rxApp_notification.write(appNotification(fsm_meta.sessionID, 0, fsm_meta.srcIpAddress, fsm_meta.dstIpPort)); + //write to memory + rxBufferWriteCmd.write(mmCmd(pkgAddr, fsm_meta.meta.length)); + dropDataFifoOut.write(false); + } + // ### Gap already exists, packet comes in-order after the head pointer + else if (rxSar.gap && (fsm_meta.meta.seqNumb == rxSar.head) && (free_space > fsm_meta.meta.length) ) + { + std::cout<<"RX_ACK: gap in order after head"; + std::cout<<std::dec<<" session id:"<<fsm_meta.sessionID; + std::cout<<" seqNum:"<<fsm_meta.meta.seqNumb; + std::cout<<" recvd:"<<rxSar.recvd; + std::cout<<" head:"<<rxSar.head; + std::cout<<" offset:"<<rxSar.offset; + std::cout<<" length:"<<fsm_meta.meta.length; + std::cout<<" gap:"<<rxSar.gap; + std::cout<<" free_space:"<<free_space<<std::endl; + //increment head pointer + newHead = fsm_meta.meta.seqNumb+fsm_meta.meta.length; + //update head pointer + rxEng2rxSar_upd_req.write(rxSarRecvd(fsm_meta.sessionID, rxSar.recvd, newHead, rxSar.offset, rxSar.gap)); + //write to memory + rxBufferWriteCmd.write(mmCmd(pkgAddr, fsm_meta.meta.length)); + //notification for matching the mem write status in notificationDelayer + rxEng2rxApp_notification.write(appNotification(fsm_meta.sessionID, 0, fsm_meta.srcIpAddress, fsm_meta.dstIpPort)); + dropDataFifoOut.write(false); + } + // ### Gap alread exists, packet comes in-order after the recvd pointer + else if (rxSar.gap && (fsm_meta.meta.seqNumb == rxSar.recvd)) + { + std::cout<<"RX_ACK: gap in order after recvd"; + std::cout<<std::dec<<" session id:"<<fsm_meta.sessionID; + std::cout<<" seqNum:"<<fsm_meta.meta.seqNumb; + std::cout<<" recvd:"<<rxSar.recvd; + std::cout<<" head:"<<rxSar.head; + std::cout<<" offset:"<<rxSar.offset; + std::cout<<" length:"<<fsm_meta.meta.length; + std::cout<<" gap:"<<rxSar.gap; + std::cout<<" free_space:"<<free_space<<std::endl; + //fill the gap + if ((fsm_meta.meta.seqNumb + fsm_meta.meta.length)(WINDOW_BITS-1, 0) == rxSar.offset) + { + newRecvd = rxSar.head; + rxEng2rxSar_upd_req.write(rxSarRecvd(fsm_meta.sessionID, newRecvd, rxSar.head, rxSar.offset, false)); + //write to memory + rxBufferWriteCmd.write(mmCmd(pkgAddr, fsm_meta.meta.length)); + // Only notify about new data available + rxEng2rxApp_notification.write(appNotification(fsm_meta.sessionID, (rxSar.head - fsm_meta.meta.seqNumb)(WINDOW_BITS-1, 0), fsm_meta.srcIpAddress, fsm_meta.dstIpPort)); + dropDataFifoOut.write(false); + } + //gap can not be filled + else if ((fsm_meta.meta.seqNumb + fsm_meta.meta.length)(WINDOW_BITS-1, 0) < rxSar.offset) + { + newRecvd = fsm_meta.meta.seqNumb + fsm_meta.meta.length; + rxEng2rxSar_upd_req.write(rxSarRecvd(fsm_meta.sessionID, newRecvd, rxSar.head, rxSar.offset, rxSar.gap)); + //write to memory + rxBufferWriteCmd.write(mmCmd(pkgAddr, fsm_meta.meta.length)); + // Only notify about new data available + rxEng2rxApp_notification.write(appNotification(fsm_meta.sessionID, fsm_meta.meta.length, fsm_meta.srcIpAddress, fsm_meta.dstIpPort)); + dropDataFifoOut.write(false); + } + } + // ### drop the packet in all other cases + else + { + dropDataFifoOut.write(true); + } + + } + + +#else //if DDR is not used, OOO is disabled // Check if packet contains payload if (fsm_meta.meta.length != 0) { ap_uint<32> newRecvd = fsm_meta.meta.seqNumb+fsm_meta.meta.length; + ap_uint<32> newHead = fsm_meta.meta.seqNumb+fsm_meta.meta.length; // Second part makes sure that app pointer is not overtaken -#if !(RX_DDR_BYPASS) - ap_uint<WINDOW_BITS> free_space = ((rxSar.appd - rxSar.recvd(WINDOW_BITS-1, 0)) - 1); // Check if segment in order and if enough free space is available - if ((fsm_meta.meta.seqNumb == rxSar.recvd) && (free_space > fsm_meta.meta.length)) -#else if ((fsm_meta.meta.seqNumb == rxSar.recvd) && ((rxbuffer_max_data_count - rxbuffer_data_count) > 375)) -#endif { - rxEng2rxSar_upd_req.write(rxSarRecvd(fsm_meta.sessionID, newRecvd)); + rxEng2rxSar_upd_req.write(rxSarRecvd(fsm_meta.sessionID, newRecvd, newHead, rxSar.offset, rxSar.gap)); // Build memory address ap_uint<32> pkgAddr; pkgAddr(31, 30) = 0x0; pkgAddr(29, WINDOW_BITS) = fsm_meta.sessionID(13, 0); pkgAddr(WINDOW_BITS-1, 0) = fsm_meta.meta.seqNumb(WINDOW_BITS-1, 0); -#if !(RX_DDR_BYPASS) - rxBufferWriteCmd.write(mmCmd(pkgAddr, fsm_meta.meta.length)); -#endif - // Only notify about new data available + // Only notify about new data available rxEng2rxApp_notification.write(appNotification(fsm_meta.sessionID, fsm_meta.meta.length, fsm_meta.srcIpAddress, fsm_meta.dstIpPort)); dropDataFifoOut.write(false); } @@ -1097,11 +1258,10 @@ void rxTcpFSM( stream<rxFsmMetaData>& fsmMetaDataFifo, { dropDataFifoOut.write(true); } + } +#endif - // Sent ACK - //rxEng2eventEng_setEvent.write(event(ACK, fsm_meta.sessionID)); - } #if FAST_RETRANSMIT if (txSar.count == 3 && !txSar.fastRetransmitted) { @@ -1112,7 +1272,21 @@ void rxTcpFSM( stream<rxFsmMetaData>& fsmMetaDataFifo, if (fsm_meta.meta.length != 0) #endif { - rxEng2eventEng_setEvent.write(event(ACK, fsm_meta.sessionID)); + //send ack only when packet in-order +#if !(RX_DDR_BYPASS) + if (!rxSar.gap && (fsm_meta.meta.seqNumb == rxSar.recvd) && (free_space > fsm_meta.meta.length)) +#else + if ((fsm_meta.meta.seqNumb == rxSar.recvd) && ((rxbuffer_max_data_count - rxbuffer_data_count) > 375)) +#endif + { + rxEng2eventEng_setEvent.write(event(ACK, fsm_meta.sessionID)); + } + //send duplicate ack with ack_nodelay + else + { + rxEng2eventEng_setEvent.write(event(ACK_NODELAY, fsm_meta.sessionID)); + } + } @@ -1165,18 +1339,27 @@ void rxTcpFSM( stream<rxFsmMetaData>& fsmMetaDataFifo, { stateTable2rxEng_upd_rsp.read(tcpState); rxSar2rxEng_upd_rsp.read(rxSar); + std::cout<<"RX_SYN: "; + std::cout<<std::dec<<" session id:"<<fsm_meta.sessionID; + std::cout<<" seqNum:"<<fsm_meta.meta.seqNumb; + std::cout<<" recvd:"<<rxSar.recvd; + std::cout<<" head:"<<rxSar.head; + std::cout<<" offset:"<<rxSar.offset; + std::cout<<" length:"<<fsm_meta.meta.length; + std::cout<<" gap:"<<rxSar.gap<<std::endl; + // std::cout<<" free_space"<<free_space<<std::endl; if (tcpState == CLOSED || tcpState == SYN_SENT) // Actually this is LISTEN || SYN_SENT { #if (WINDOW_SCALE) ap_uint<4> rx_win_shift = (fsm_meta.meta.winScale == 0) ? 0 : WINDOW_SCALE_BITS; ap_uint<4> tx_win_shift = fsm_meta.meta.winScale; - // Initialize rxSar, SEQ + phantom byte - rxEng2rxSar_upd_req.write(rxSarRecvd(fsm_meta.sessionID, fsm_meta.meta.seqNumb+1, rx_win_shift)); + // Initialize rxSar, SEQ + phantom byte for recvd and head pointer, offset to 0, gap set to false + rxEng2rxSar_upd_req.write(rxSarRecvd(fsm_meta.sessionID, fsm_meta.meta.seqNumb+1, fsm_meta.meta.seqNumb+1, 0, false, rx_win_shift)); // Initialize receive window 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 #else // Initialize rxSar, SEQ + phantom byte, last '1' for makes sure appd is initialized - rxEng2rxSar_upd_req.write(rxSarRecvd(fsm_meta.sessionID, fsm_meta.meta.seqNumb+1, 1)); + rxEng2rxSar_upd_req.write(rxSarRecvd(fsm_meta.sessionID, fsm_meta.meta.seqNumb+1, fsm_meta.meta.seqNumb+1, 0, false, 1)); // Initialize receive window rxEng2txSar_upd_req.write((rxTxSarQuery(fsm_meta.sessionID, 0, fsm_meta.meta.winSize, txSar.cong_window, 0, false))); //TODO maybe include count check #endif @@ -1219,16 +1402,25 @@ void rxTcpFSM( stream<rxFsmMetaData>& fsmMetaDataFifo, rxSar2rxEng_upd_rsp.read(rxSar); txSar2rxEng_upd_rsp.read(txSar); rxEng2timer_clearRetransmitTimer.write(rxRetransmitTimerUpdate(fsm_meta.sessionID, (fsm_meta.meta.ackNumb == txSar.nextByte))); + std::cout<<"RX_SYN_ACK: "; + std::cout<<std::dec<<" session id:"<<fsm_meta.sessionID; + std::cout<<" seqNum:"<<fsm_meta.meta.seqNumb; + std::cout<<" recvd:"<<rxSar.recvd; + std::cout<<" head:"<<rxSar.head; + std::cout<<" offset:"<<rxSar.offset; + std::cout<<" length:"<<fsm_meta.meta.length; + std::cout<<" gap:"<<rxSar.gap<<std::endl; + // std::cout<<" free_space"<<free_space<<std::endl; if ((tcpState == SYN_SENT) && (fsm_meta.meta.ackNumb == txSar.nextByte))// && !mh_lup.created) { #if (WINDOW_SCALE) ap_uint<4> rx_win_shift = (fsm_meta.meta.winScale == 0) ? 0 : WINDOW_SCALE_BITS; ap_uint<4> tx_win_shift = fsm_meta.meta.winScale; - rxEng2rxSar_upd_req.write(rxSarRecvd(fsm_meta.sessionID, fsm_meta.meta.seqNumb+1, rx_win_shift)); + rxEng2rxSar_upd_req.write(rxSarRecvd(fsm_meta.sessionID, fsm_meta.meta.seqNumb+1, fsm_meta.meta.seqNumb+1, 0, false, rx_win_shift)); 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 #else //initialize rx_sar, SEQ + phantom byte, last '1' for appd init - rxEng2rxSar_upd_req.write(rxSarRecvd(fsm_meta.sessionID, fsm_meta.meta.seqNumb+1, 1)); + rxEng2rxSar_upd_req.write(rxSarRecvd(fsm_meta.sessionID, fsm_meta.meta.seqNumb+1, fsm_meta.meta.seqNumb+1, 0, false, 1)); rxEng2txSar_upd_req.write((rxTxSarQuery(fsm_meta.sessionID, fsm_meta.meta.ackNumb, fsm_meta.meta.winSize, txSar.cong_window, 0, false))); //TODO maybe include count check #endif @@ -1259,6 +1451,15 @@ void rxTcpFSM( stream<rxFsmMetaData>& fsmMetaDataFifo, stateTable2rxEng_upd_rsp.read(tcpState); rxSar2rxEng_upd_rsp.read(rxSar); txSar2rxEng_upd_rsp.read(txSar); + std::cout<<"RX_FIN: "; + std::cout<<std::dec<<" session id:"<<fsm_meta.sessionID; + std::cout<<" seqNum:"<<fsm_meta.meta.seqNumb; + std::cout<<" recvd:"<<rxSar.recvd; + std::cout<<" head:"<<rxSar.head; + std::cout<<" offset:"<<rxSar.offset; + std::cout<<" length:"<<fsm_meta.meta.length; + std::cout<<" gap:"<<rxSar.gap<<std::endl; + // std::cout<<" free_space"<<free_space<<std::endl; rxEng2timer_clearRetransmitTimer.write(rxRetransmitTimerUpdate(fsm_meta.sessionID, (fsm_meta.meta.ackNumb == txSar.nextByte))); // Check state and if FIN in order, Current out of order FINs are not accepted if ((tcpState == ESTABLISHED || tcpState == FIN_WAIT_1 || tcpState == FIN_WAIT_2) && (rxSar.recvd == fsm_meta.meta.seqNumb)) @@ -1266,7 +1467,7 @@ void rxTcpFSM( stream<rxFsmMetaData>& fsmMetaDataFifo, rxEng2txSar_upd_req.write((rxTxSarQuery(fsm_meta.sessionID, fsm_meta.meta.ackNumb, fsm_meta.meta.winSize, txSar.cong_window, txSar.count, txSar.fastRetransmitted))); //TODO include count check // +1 for phantom byte, there might be data too - rxEng2rxSar_upd_req.write(rxSarRecvd(fsm_meta.sessionID, fsm_meta.meta.seqNumb+fsm_meta.meta.length+1)); //diff to ACK + rxEng2rxSar_upd_req.write(rxSarRecvd(fsm_meta.sessionID, fsm_meta.meta.seqNumb+fsm_meta.meta.length+1, fsm_meta.meta.seqNumb+fsm_meta.meta.length+1, rxSar.offset,rxSar.gap)); //diff to ACK // Clear the probe timer rxEng2timer_clearProbeTimer.write(fsm_meta.sessionID); @@ -1482,7 +1683,10 @@ void rxAppNotificationDelayer( stream<mmStatus>& rxWriteStatusIn, stream<appN rxWriteStatusIn.read(rxAppNotificationStatus2); rand_fifoCount--; if (rxAppNotificationStatus1.okay && rxAppNotificationStatus2.okay) - notificationOut.write(rxAppNotification); + if (rxAppNotification.length != 0) + { + notificationOut.write(rxAppNotification); + } rxAppNotificationDoubleAccessFlag = false; } } @@ -1494,18 +1698,32 @@ void rxAppNotificationDelayer( stream<mmStatus>& rxWriteStatusIn, stream<appN if (rxAppNotificationDoubleAccessFlag == 0) { // if the memory access was not broken down in two for this segment rand_fifoCount--; if (rxAppNotificationStatus1.okay) - notificationOut.write(rxAppNotification); // Output the notification + if (rxAppNotification.length!=0) + { + notificationOut.write(rxAppNotification); // Output the notification + } } //TODO else, we are screwed since the ACK is already sent } else if (!internalNotificationFifoIn.empty() && (rand_fifoCount < 31)) { internalNotificationFifoIn.read(rxAppNotification); - if (rxAppNotification.length != 0) { + //if (rxAppNotification.length != 0) { + // rand_notificationBuffer.write(rxAppNotification); + // rand_fifoCount++; + //} + //else + // notificationOut.write(rxAppNotification); + + if (rxAppNotification.closed & rxAppNotification.length == 0) + { + notificationOut.write(rxAppNotification); + } + else + { rand_notificationBuffer.write(rxAppNotification); rand_fifoCount++; } - else - notificationOut.write(rxAppNotification); + } } } @@ -1613,9 +1831,9 @@ void rxEngMemWrite( hls::stream<net_axis<WIDTH> >& dataIn, if (!dataIn.empty()) { net_axis<WIDTH> currWord = dataIn.read(); - std::cout << "HELP: "; - printLE(std::cout, currWord); - std::cout << std::endl; + // std::cout << "HELP: "; + // printLE(std::cout, currWord); + // std::cout << std::endl; dataOut.write(currWord); if (currWord.last) { diff --git a/hls/toe/rx_sar_table/rx_sar_table.cpp b/hls/toe/rx_sar_table/rx_sar_table.cpp index 74c8ae3..aac2708 100755 --- a/hls/toe/rx_sar_table/rx_sar_table.cpp +++ b/hls/toe/rx_sar_table/rx_sar_table.cpp @@ -93,6 +93,9 @@ void rx_sar_table( stream<rxSarRecvd>& rxEng2rxSar_upd_req, if (in_recvd.write) { rx_table[in_recvd.sessionID].recvd = in_recvd.recvd; + rx_table[in_recvd.sessionID].head = in_recvd.head; + rx_table[in_recvd.sessionID].offset = in_recvd.offset; + rx_table[in_recvd.sessionID].gap = in_recvd.gap; if (in_recvd.init) { rx_table[in_recvd.sessionID].appd = in_recvd.recvd; diff --git a/hls/toe/toe_internals.hpp b/hls/toe/toe_internals.hpp index 3803e8a..78a14a5 100755 --- a/hls/toe/toe_internals.hpp +++ b/hls/toe/toe_internals.hpp @@ -106,13 +106,21 @@ struct stateQuery * @ingroup tx_engine * This struct defines an entry of the @ref rx_sar_table */ + +/* A gap caused by out-of-order packet: +* v- appd v- recvd v- offset v- head +* | <- undef -> | <committed> | <gap> | <pre-mature> | <- undef -> | +*/ struct rxSarEntry { - ap_uint<32> recvd; + ap_uint<32> recvd; ap_uint<WINDOW_BITS> appd; #if (WINDOW_SCALE) ap_uint<4> win_shift; #endif + ap_uint<32> head; + ap_uint<16> offset; + bool gap; }; struct rxSarReply @@ -139,13 +147,21 @@ struct rxSarRecvd ap_uint<4> win_shift; //TODO name ap_uint<1> write; ap_uint<1> init; + ap_uint<32> head; + ap_uint<WINDOW_BITS> offset; + bool gap; rxSarRecvd() {} rxSarRecvd(ap_uint<16> id) :sessionID(id), recvd(0), write(0), init(0) {} - rxSarRecvd(ap_uint<16> id, ap_uint<32> recvd) - :sessionID(id), recvd(recvd), write(1), init(0) {} - rxSarRecvd(ap_uint<16> id, ap_uint<32> recvd, ap_uint<4> win_shift) - :sessionID(id), recvd(recvd), win_shift(win_shift), write(1), init(1) {} + // rxSarRecvd(ap_uint<16> id, ap_uint<32> recvd) + // :sessionID(id), recvd(recvd), write(1), init(0) {} + // rxSarRecvd(ap_uint<16> id, ap_uint<32> recvd, ap_uint<4> win_shift) + // :sessionID(id), recvd(recvd), win_shift(win_shift), write(1), init(1) {} + + rxSarRecvd(ap_uint<16> id, ap_uint<32> recvd, ap_uint<32> head, ap_uint<WINDOW_BITS>offset, bool gap) + :sessionID(id), recvd(recvd), head(head), offset(offset), gap(gap), write(1), init(0) {} + rxSarRecvd(ap_uint<16> id, ap_uint<32> recvd, ap_uint<32> head, ap_uint<WINDOW_BITS>offset, bool gap, ap_uint<4> win_shift) + :sessionID(id), recvd(recvd), head(head), offset(offset), gap(gap), win_shift(win_shift), write(1), init(1) {} }; struct rxSarAppd diff --git a/hls/toe/tx_engine/tx_engine.cpp b/hls/toe/tx_engine/tx_engine.cpp index c5ab022..4885e97 100755 --- a/hls/toe/tx_engine/tx_engine.cpp +++ b/hls/toe/tx_engine/tx_engine.cpp @@ -190,6 +190,17 @@ void metaLoader(hls::stream<extendedEvent>& eventEng2txEng_event, // Only set RT timer if we actually send sth, TODO only set if we change state and sent sth txEng2timer_setRetransmitTimer.write(txRetransmitTimerSet(ml_curEvent.sessionID)); } + + std::cout<<"TX"; + std::cout<<std::dec<<" session id:"<<ml_curEvent.sessionID; + std::cout<<" seqNum:"<<txSar.not_ackd; + std::cout<<" ackNum:"<<rxSar.recvd; + std::cout<<" window_size:"<<rxSar.windowSize; + std::cout<<" ack:"<<meta.ack; + std::cout<<" rst:"<<meta.rst; + std::cout<<" syn:"<<meta.syn; + std::cout<<" fin:"<<meta.fin; + std::cout<<" length:"<<ml_curEvent.length<<std::endl; } break; @@ -303,6 +314,17 @@ void metaLoader(hls::stream<extendedEvent>& eventEng2txEng_event, txEng2timer_setRetransmitTimer.write(txRetransmitTimerSet(ml_curEvent.sessionID)); }//TODO if probe send msg length 1 ml_sarLoaded = true; + + std::cout<<"TX"; + std::cout<<std::dec<<" session id:"<<ml_curEvent.sessionID; + std::cout<<" seqNum:"<<txSar.not_ackd; + std::cout<<" ackNum:"<<rxSar.recvd; + std::cout<<" window_size:"<<rxSar.windowSize; + std::cout<<" ack:"<<meta.ack; + std::cout<<" rst:"<<meta.rst; + std::cout<<" syn:"<<meta.syn; + std::cout<<" fin:"<<meta.fin; + std::cout<<" length:"<<ml_curEvent.length<<std::endl; } break; #endif @@ -401,6 +423,17 @@ void metaLoader(hls::stream<extendedEvent>& eventEng2txEng_event, } ml_sarLoaded = true; txSarReg = txSar; + + std::cout<<"RT"; + std::cout<<std::dec<<" session id:"<<ml_curEvent.sessionID; + std::cout<<" seqNum:"<<txSar.not_ackd; + std::cout<<" ackNum:"<<rxSar.recvd; + std::cout<<" window_size:"<<rxSar.windowSize; + std::cout<<" ack:"<<meta.ack; + std::cout<<" rst:"<<meta.rst; + std::cout<<" syn:"<<meta.syn; + std::cout<<" fin:"<<meta.fin; + std::cout<<" length:"<<ml_curEvent.length<<std::endl; } break; case ACK: @@ -423,6 +456,17 @@ void metaLoader(hls::stream<extendedEvent>& eventEng2txEng_event, txEng_isLookUpFifoOut.write(true); txEng2sLookup_rev_req.write(ml_curEvent.sessionID); ml_FsmState = 0; + + std::cout<<"TX_ACK"; + std::cout<<std::dec<<" session id:"<<ml_curEvent.sessionID; + std::cout<<" seqNum:"<<txSar.not_ackd; + std::cout<<" ackNum:"<<rxSar.recvd; + std::cout<<" window_size:"<<rxSar.windowSize; + std::cout<<" ack:"<<meta.ack; + std::cout<<" rst:"<<meta.rst; + std::cout<<" syn:"<<meta.syn; + std::cout<<" fin:"<<meta.fin; + std::cout<<" length:"<<ml_curEvent.length<<std::endl; } break; case SYN: @@ -461,6 +505,17 @@ void metaLoader(hls::stream<extendedEvent>& eventEng2txEng_event, // set retransmit timer txEng2timer_setRetransmitTimer.write(txRetransmitTimerSet(ml_curEvent.sessionID, SYN)); ml_FsmState = 0; + + std::cout<<"TX_SYN"; + std::cout<<std::dec<<" session id:"<<ml_curEvent.sessionID; + std::cout<<" seqNum:"<<txSar.not_ackd; + std::cout<<" ackNum:"<<rxSar.recvd; + std::cout<<" window_size:"<<rxSar.windowSize; + std::cout<<" ack:"<<meta.ack; + std::cout<<" rst:"<<meta.rst; + std::cout<<" syn:"<<meta.syn; + std::cout<<" fin:"<<meta.fin; + std::cout<<" length:"<<ml_curEvent.length<<std::endl; } break; case SYN_ACK: @@ -506,6 +561,17 @@ void metaLoader(hls::stream<extendedEvent>& eventEng2txEng_event, // set retransmit timer txEng2timer_setRetransmitTimer.write(txRetransmitTimerSet(ml_curEvent.sessionID, SYN_ACK)); ml_FsmState = 0; + + std::cout<<"TX_SYN_ACK"; + std::cout<<std::dec<<" session id:"<<ml_curEvent.sessionID; + std::cout<<" seqNum:"<<txSar.not_ackd; + std::cout<<" ackNum:"<<rxSar.recvd; + std::cout<<" window_size:"<<rxSar.windowSize; + std::cout<<" ack:"<<meta.ack; + std::cout<<" rst:"<<meta.rst; + std::cout<<" syn:"<<meta.syn; + std::cout<<" fin:"<<meta.fin; + std::cout<<" length:"<<ml_curEvent.length<<std::endl; } break; case FIN: @@ -571,6 +637,17 @@ void metaLoader(hls::stream<extendedEvent>& eventEng2txEng_event, } ml_FsmState = 0; + + std::cout<<"TX_FIN"; + std::cout<<std::dec<<" session id:"<<ml_curEvent.sessionID; + std::cout<<" seqNum:"<<txSar.not_ackd; + std::cout<<" ackNum:"<<rxSar.recvd; + std::cout<<" window_size:"<<rxSar.windowSize; + std::cout<<" ack:"<<meta.ack; + std::cout<<" rst:"<<meta.rst; + std::cout<<" syn:"<<meta.syn; + std::cout<<" fin:"<<meta.fin; + std::cout<<" length:"<<ml_curEvent.length<<std::endl; } break; case RST: @@ -747,19 +824,19 @@ void generate_ipv4( //stream<ipv4Meta>& txEng_ipMetaDataFifoIn, //length = meta.length + 20; //was adding +40 ap_uint<16> length = metaLength + 40; - std::cout << "length: " << length << std::endl; + // std::cout << "length: " << length << std::endl; header.setLength(length); header.setDstAddr(tuples.dstIp); header.setSrcAddr(tuples.srcIp); header.setProtocol(TCP_PROTOCOL); if (IPV4_HEADER_SIZE >= WIDTH) { - std::cout << "switched to IP HEADER" << std::endl; + // std::cout << "switched to IP HEADER" << std::endl; gi_state = HEADER; } else { - std::cout << "switched to IP PARTIAL HEADER" << std::endl; + // std::cout << "switched to IP PARTIAL HEADER" << std::endl; gi_state = PARTIAL_HEADER; } } @@ -772,7 +849,7 @@ void generate_ipv4( //stream<ipv4Meta>& txEng_ipMetaDataFifoIn, /*currWord.keep = 0xFFFFFFFF; //TODO, set as much as required currWord.last = 0; m_axis_tx_data.write(currWord);*/ - std::cout << "switched to IP PARTIAL HEADER" << std::endl; + // std::cout << "switched to IP PARTIAL HEADER" << std::endl; gi_state = PARTIAL_HEADER; } //else @@ -791,9 +868,9 @@ void generate_ipv4( //stream<ipv4Meta>& txEng_ipMetaDataFifoIn, header.consumeWord(currWord.data); m_axis_tx_data.write(currWord); gi_state = BODY; - std::cout << "IP PARTIAL: "; - printLE(std::cout, currWord); - std::cout << std::endl; + // std::cout << "IP PARTIAL: "; + // printLE(std::cout, currWord); + // std::cout << std::endl; if (currWord.last) { @@ -806,9 +883,9 @@ void generate_ipv4( //stream<ipv4Meta>& txEng_ipMetaDataFifoIn, { net_axis<WIDTH> currWord = tx_shift2ipv4Fifo.read(); - std::cout << "IP BODY: ";// << std::endl; - printLE(std::cout, currWord); - std::cout << std::endl; + // std::cout << "IP BODY: ";// << std::endl; + // printLE(std::cout, currWord); + // std::cout << std::endl; m_axis_tx_data.write(currWord); if (currWord.last) @@ -1020,7 +1097,7 @@ void pseudoHeaderConstructionNew(stream<tx_engine_meta>& tcpMetaDataFifoIn, } else { - std::cout << "switch to TCP HEADER" << std::endl; + // std::cout << "switch to TCP HEADER" << std::endl; //TODO handle 512 state = HEADER; } @@ -1031,20 +1108,20 @@ void pseudoHeaderConstructionNew(stream<tx_engine_meta>& tcpMetaDataFifoIn, net_axis<WIDTH> sendWord; sendWord.last = 0; ap_uint<8> remainingLength = header.consumeWord(sendWord.data); - std::cout << std::dec << "remainingLenght: " << remainingLength << std::endl; + // std::cout << std::dec << "remainingLenght: " << remainingLength << std::endl; if (remainingLength < (WIDTH/8)) //if (header.consumeWord(sendWord.data) < WIDTH) { if (hasBody) { - std::cout << "switch to TCP BODY" << std::endl; + // std::cout << "switch to TCP BODY" << std::endl; state = BODY; //PARTIAL_HEADER; } else { if (isSYN && WIDTH <= 256) { - std::cout << "switch to MSS" << std::endl; + // std::cout << "switch to MSS" << std::endl; state = HEADER_MSS_OPTION; } else @@ -1055,9 +1132,9 @@ void pseudoHeaderConstructionNew(stream<tx_engine_meta>& tcpMetaDataFifoIn, } } sendWord.keep = 0xffffffff; //Keep for 256bit (size of the header) - std::cout << "TCP HEADER: "; - printLE(std::cout, sendWord); - std::cout << std::endl; + // std::cout << "TCP HEADER: "; + // printLE(std::cout, sendWord); + // std::cout << std::endl; //In case of WIDTH == 512, we can add the MSS option into the first word if (isSYN && WIDTH == 512) @@ -1072,7 +1149,7 @@ void pseudoHeaderConstructionNew(stream<tx_engine_meta>& tcpMetaDataFifoIn, sendWord.keep(35,32) = 0xF; #if (WINDOW_SCALE) // WSopt negotiation, only send in SYN-ACK if received with SYN as in RFC 7323 1.3 - std::cout << "PSEUDO NEW: " << win_shift << std::endl; + // std::cout << "PSEUDO NEW: " << win_shift << std::endl; if (win_shift != 0) { sendWord.data(295, 288) = 0x03; // Option Kind @@ -1125,7 +1202,7 @@ void pseudoHeaderConstructionNew(stream<tx_engine_meta>& tcpMetaDataFifoIn, #endif #if (WINDOW_SCALE) // WSopt negotiation, only send in SYN-ACK if received with SYN as in RFC 7323 1.3 - std::cout << "PSEUDO NEW: " << win_shift << std::endl; + // std::cout << "PSEUDO NEW: " << win_shift << std::endl; if (win_shift != 0) { sendWord.data(39, 32) = 0x03; // Option Kind @@ -1358,9 +1435,9 @@ void read_data_arbiter(stream<net_axis<WIDTH> >& txBufferReadData, if (!txApp2txEng_data_stream.empty()) { net_axis<WIDTH> currWord = txApp2txEng_data_stream.read(); - std::cout << "ARBITER: "; - printLE(std::cout, currWord); - std::cout << std::endl; + // std::cout << "ARBITER: "; + // printLE(std::cout, currWord); + // std::cout << std::endl; txEng_tcpSegOut.write(currWord); if (currWord.last) { @@ -1428,9 +1505,9 @@ void remove_pseudo_header(hls::stream<net_axis<WIDTH> >& dataIn, if (!dataIn.empty()) { net_axis<WIDTH> word = dataIn.read(); - std::cout << "REMOVE: "; - printLE(std::cout, word); - std::cout << std::endl; + // std::cout << "REMOVE: "; + // printLE(std::cout, word); + // std::cout << std::endl; if (!firstWord || WIDTH > 64) { @@ -1472,10 +1549,10 @@ void insert_checksum( hls::stream<ap_uint<16> >& checksumIn, if (!checksumIn.empty() && !dataIn.empty()) { ap_uint<16> checksum = checksumIn.read(); - std::cout << "INSERTING checksum: " << checksum << std::endl; + // std::cout << "INSERTING checksum: " << checksum << std::endl; net_axis<WIDTH> word = dataIn.read(); - printLE(std::cout, word); - std::cout << std::endl; + // printLE(std::cout, word); + // std::cout << std::endl; if (WIDTH > 128) { word.data(143, 128) = reverse(checksum); @@ -1485,9 +1562,9 @@ void insert_checksum( hls::stream<ap_uint<16> >& checksumIn, word.data(15, 0) = reverse(checksum); } dataOut.write(word); - std::cout << "after: "; - printLE(std::cout, word); - std::cout << std::endl; + // std::cout << "after: "; + // printLE(std::cout, word); + // std::cout << std::endl; state = 2; if (word.last) -- GitLab