TFTP的工作都是由客户端发起一个RRQ或者WRQ开始的。这里分别以WRQ和RRQ为例,讲述读写的工作过程,以及错误处理等内容。 用S表示Server,C表示Client。 1. WRQ工作流程 l S在端口为69的UDP上等待C发出写文件请求包 在TFTP中,一次请求中所有包的源和目标都由Transfer ID(TID)来标示。TFTP规定TID值就是UDP包中的源和目标端口。也就是说,一次请求过程中,S和C通过UDP包的源和目标端口来判断这个包是不是发给自己的。 以WRQ为例,C向S的69端口发送一个文件请求包,这个文件请求包中UDP的源端口号为C的TID(假设C选择4845作为它的TID),目标端口为69(这个时候由于请求还未接受,所以这次请求的UDP包中目标端口不是TID)。S收到这个请求后,将另外采用一个UDP端口(应该另启动了一个UDP Socket)假设为4849来回复这个请求的ACK。这样,这个回复的UDP包的源端口就是S的TID(=4849),目标就是C的UDP端口(TID=4845)。以后,这次请求的后续所有包都在端口为4845和4849中来往。 上述过程隐含了一定程度上的容错处理。例如,C收到一个TID不是4849的包,则认为这个包是错误的。 另外,S对于每个请求,都要采用一个不重复的新的UDP端口号作为它的TID,也就是说,S上同时存在的n个请求的TID都将不同。 这里再介绍下TFTP的回复ACK机制。虽然TFTP中有指定的ACK包作为回应,但在普遍意义上,DATA包和ERROR包都可以作为上一次发送包的响应。 一般来说,C发送了一个非结束DATA包给S,如果在超时时间内,C未收到S发送的ACK,则C继续发送这个DATA直到S回复ACK。这种情况是比较好理解的。 但假如S回复了上一个非结束DATA包ACK后,C在S的超时时间内没有发送下一个DATA包,则S将继续发送这个ACK。从这个角度看,S等待的这个新DATA包是对上一次ACK的确认。 2. RRQ的工作流程 RRQ和WRQ类似。 l S在端口为69的UDP上等待C发出读文件请求包 UDP实际上没有连接的概念。但从上面分析的RRQ和WRQ看,S在69端口上等待请求,而且S总是生成一个新的UDP来完成和C的交互。这个过程和TCP的listen以及Accept非常类似。所以TFTP把这种交互也称作connection。只不过这种连接是隐含在请求中的。 一般情况下,连接的建立由一次成功的请求来发起,当最后一个DATA包发送完毕并且ACK回复了后,则连接正常关闭。在传输过程中,如果出现错误,假设S向C发送了一个ERROR包,如果C收到ERROR包,则连接关闭。如果C没有收到ERROR包,则需要启动ERROR超时检测机制。需要强调的是对于ERROR包,S和C都不会重传也不需要ACK确认。 TFTP建议在连接正常关闭的情况,S可在发送确认结束DATA包的ACK后稍等片刻后再关闭连接。例如,当C发送结束DATA包后,S回复ACK后再等一段时间才关闭。再次等待时间中,如果ACK包丢失,C将再次发送结束DATA包或者超时处理。S如果又收到一次结束DATA包后,就知道ACK包丢失了。S可以关闭连接也可以再次发送ACK包。
任何传输起自一个读取或写入文件的请求,这个请求也是连接请求。如果服务器批准此请求,则服务器打开连接,数据以定长512字节传输。每个数据包包括一块数据,服务器发出下一个数据包以前必须得到客户对上一个数据包的确认。如果一个数据包的大小小于512字节,则表示传输结束。如果数据包在传输过程中丢失,发出方会在超时后重新传输最后一个未被确认的数据包。通信的双方都是数据的发出者与接收者,一方传输数据接收应答,另一方发出应答接收数据。大部分的错误会导致连接中断,错误由一个错误的数据包引起。这个包不会被确认,也不会被重新发送,因此另一方无法接收到。如果错误包丢失,则使用超时机制。错误主要是由下面三种情况引起的:不能满足请求,收到的数据包内容错误,而这种错误不能由延时或重发解释,对需要资源的访问丢失(如硬盘满)。TFTP只在一种情况下不中断连接,这种情况是源端口不正确,在这种情况下,指示错误的包会被发送到源机。这个协议限制很多,这是都是为了实现起来比较方便而进行的。通过下边的图片来了解tftp协议的通信流程: |
|