当前位置:网站首页>[Stanford Jiwang cs144 project] lab3: tcpsender
[Stanford Jiwang cs144 project] lab3: tcpsender
2022-07-07 07:43:00 【Altair_ alpha】
In this section TCP The sender in the protocol TCPSender The implementation of the .Sender Have an input ByteStream, On behalf of the data provided by the user to be sent , and Sender Be responsible for assembling it into TCP Packet and send it out . So called sending , That is to put the data package push To a queue _segments_out Then you can , The next section realizes TCPConnection class ( That is to say Sender and Receiver Owner ) It will be responsible for taking packets from the queue and actually sending them .
Except for the guarantee TCPSegment Data in the 、 Serial number and SYN,FIN Wait until the logo is set correctly ,Sender There are two main issues to consider . First, the receiving window ,Receiver The amount of data that can be received at one time is limited , Will pass Header in Window Size Field to Sender Dynamic feedback of this information .Sender It should be ensured that ( That is, it has been sent and has not been confirmed to receive ) The amount of data is less than or equal to this window .
Second, data retransmission , Because the data packet may be lost during transmission ,Sender You cannot discard a packet immediately after sending it , Instead, it is placed in the temporary storage area ( be called outstanding data), If you haven't received it within a period of time Receiver Confirmation signal of ( adopt ackno) You need to retransmit . The handout stipulates that it will be true TCP A series of rules after the agreement is slightly simplified are as follows :
- Perception of time . In order to ensure the certainty of program testing ,Sender The implementation does not actively call any actual time API, Instead, it passively invokes its
tickThe function perceives the passage of time , The parameter of this function is from the last calltickThe number of milliseconds elapsed after . - The concept of timer . There needs to be a Timer, It can be activated , Triggered after a set time interval , It can also be stopped manually . Because the perception of time is passive , therefore Timer It can only be in
tickFunction . - Sender Accept an initial Retransmission timeout (retransmission timeout, RTO) Parameters , This initial parameter is fixed , At the same time, there is a current RTO Parameters . Every time a packet is sent , If Timer Not activated , Start and make it current RTO Triggered in milliseconds . When all data in the staging area is ack when , stop it Timer.
- When Timer stay
tickWhen triggered in , Will not be completely ack Of One of the earliest ( That is, the one with the smallest serial number ) Temporary packet retransmission . meanwhile , If the window size is not 0, Record the number of consecutive retransmissions , This information will be implemented in the next section TCPConnection Used to determine whether to end the connection , and Make current RTO Double ( Index retreat ). Then according to the current RTO( Probably just updated ) start-up Timer. - When receiving a request for newly sent data ack when , Will the current RTO Reset to initial RTO, And set the number of consecutive retransmissions to zero . If the staging area is not empty , start-up Timer.
Implementation , Mainly Timer + Three main functions . Refer to the code of many students on the Internet Timer The function is put in Sender In the class implementation , I still have a separate class here as follows :
// Helper class to determine whether a given timeout has reached (i.e., expired) since started.
// It won't emit any signal but provide accessor for caller to check its state
// Also the class won't call any system time function but rely on its update() called to
// know time elapsed and whether timeout is reached.
class Timer {
public:
// start the timer with given timeout.
// call start() on a started timer acts like reset() called first
void start(unsigned int timeout);
// update the timer with info of time elapsed since start/last update
void update(unsigned int time_elapsed);
// reset(stop) the timer
void reset();
// check whether the timer is active
bool active() const {
return _active; }
// check whether the timer has timed out (if the timer is inactive, return value is false)
bool expired() const {
return _active && _expired; }
private:
bool _active{
false};
bool _expired{
false};
unsigned int _current_time{
0};
unsigned int _timeout{
0};
};
One of the main functions : void ack_received(const WrappingInt32 ackno, const uint16_t window_size). The window size is determined by the members of a class _window_size Record updates , This parameter is used in the following sending function .ackno the unwrap Then compare with the packet number in the temporary storage area one by one , Remove the completely confirmed packets ( Note that the packet number in the staging area can be used to order from small to large ). If you can remove , Reset by rule RTO And retransmission count . If the staging area is empty after removal , take Timer stop it . Because the temporary storage area may be vacated , Last call fill_window( See below ) Try sending a new packet . The code is as follows :
void TCPSender::ack_received(const WrappingInt32 ackno, const uint16_t window_size) {
_window_size = window_size;
// use next seqno as checkpoint
uint64_t ack_seqno = unwrap(ackno, _isn, _next_seqno);
// it's impossible that ackno > _next_seqno, because that byte hasn't been sent yet!
if (ack_seqno > _next_seqno) {
return;
}
// remove completely ack-ed segments from the retransmission buffer
// because the segment in retrans buffer is ordered by seqno,
// it's ok to break once current seg can't be erased (subsequent seg has larger seqno)
for (auto it = _retrans_buf.begin(); it != _retrans_buf.end();) {
if (unwrap((*it).header().seqno, _isn, _next_seqno) + (*it).length_in_sequence_space() <= ack_seqno) {
it = _retrans_buf.erase(it);
_retrans_timeout = _initial_retransmission_timeout;
_timer.start(_retrans_timeout);
_consec_retrans_count = 0;
} else
break;
}
// stop the timer if retransmission buffer is clear
if (_retrans_buf.empty())
_timer.reset();
// refill the window
fill_window();
}
The second of the main functions :void tick(const size_t ms_since_last_tick). If Timer Started , Then update the time according to the parameters , Then check whether it triggers . If the trigger , Then retransmit according to the rules , Increase retransmission count , send RTO Double , And restart Timer. The code is as follows :
void TCPSender::tick(const size_t ms_since_last_tick) {
if (_timer.active())
_timer.update(ms_since_last_tick);
if (_timer.expired()) {
_segments_out.emplace(_retrans_buf.front());
if (_window_size > 0) {
_consec_retrans_count++;
_retrans_timeout *= 2;
}
_timer.start(_retrans_timeout);
}
}
The third of the main functions :void fill_window(). That is, the one mentioned at the beginning “ send data 、 Serial number and SYN,FIN Wait for the packet with the correct identification setting ”. Generally speaking, the process is : Determine whether the window is not filled → If it is not filled , Make one TCPSegment, Specifically, it is divided into judgment and release SIN identification , Put the data , Judge release FIN Identify three steps → take TCPSegment Add to _segments_out And staging area , Update the serial number and remaining space . Cycle until the window is filled . See the following source file for details , Don't paste it .
Full code link :
tcp_sender.hh
tcp_sender.cc
Screenshot of customs clearance 
边栏推荐
- UWB learning 1
- Robot technology innovation and practice old version outline
- Interviewer: what development models do you know?
- L'externalisation a duré trois ans.
- [2022 CISCN]初赛 web题目复现
- Determining the full type of a variable
- JS get all date or time stamps between two time stamps
- Talk about seven ways to realize asynchronous programming
- 微信小程序中的路由跳转
- 外包干了三年,废了...
猜你喜欢

Leetcode-206. Reverse Linked List

图解GPT3的工作原理

Advanced practice of C language (high level) pointer

1140_ SiCp learning notes_ Use Newton's method to solve the square root

The annual salary of general test is 15W, and the annual salary of test and development is 30w+. What is the difference between the two?

【Unity】物体做圆周运动的几个思路

Detailed explanation of uboot image generation process of Hisilicon chip (hi3516dv300)

Tencent's one-day life

Model application of time series analysis - stock price prediction

为什么要了解现货黄金走势?
随机推荐
Detailed explanation of uboot image generation process of Hisilicon chip (hi3516dv300)
Wx is used in wechat applet Showtoast() for interface interaction
After the interview, the interviewer roast in the circle of friends
leetcode:105. 从前序与中序遍历序列构造二叉树
抽絲剝繭C語言(高階)數據的儲存+練習
Invalid table alias or column reference`xxx`
Mutual conversion between InputStream, int, shot, long and byte arrays
1089: highest order of factorial
ROS2规划系统plansys2简单的例子
Live broadcast platform source code, foldable menu bar
通信设备商,到底有哪些岗位?
Bi she - college student part-time platform system based on SSM
解决:Could NOT find KF5 (missing: CoreAddons DBusAddons DocTools XmlGui)
知识点滴 - 关于苹果认证MFI
I failed in the postgraduate entrance examination and couldn't get into the big factory. I feel like it's over
Six methods of flattening arrays with JS
Interviewer: what development models do you know?
How can a 35 year old programmer build a technological moat?
Outsourcing for four years, abandoned
How to * * labelimg