计算机网络二(TCP/IP模型)

目录

1:TCP/IP模型

1.1什么是TCP/IP

1.2在TCP/IP模型图例

2:详解TCP通信 

2.1三次握手创建:

2.2四次握手断开:

2.3为何什么3次握手创建,但是分手需要四次

3:socket通信代码实现

3.1什么是socket

3.2socket代码简单实现


1:TCP/IP模型

1.1什么是TCP/IP

tcp/ip是一个网络通信模型,以及整个网络传输协议家族,是互联网的基础通信架构。他被成为是tcp/ip协议族,简称tcp/ip。该协议家族的两个最核心的通信协议是TCP和IP协议

TCP(传输控制协议):主要用于规范数据怎么建立连接传输,怎么传输数据,

TCP

TCP是面向通信的协议,会建通过三次握手来建立连接,然后在传递数据,并且断开连接需要四次握手。并且在数据传输的时候会通过底层复杂的算法来对数据进行确认,确认机制,重传机制,拥塞机制,等保证数据的时序性和完整性。不容易丢失数据,只能用于端到端的通信。什么时候应该使用TCP: 当对网络通讯质量有要求的时候,比如:整个数据要准确无误的传递给对方,这往往用于一些要求可靠的应用,比如HTTP、HTTPS、FTP等传输文件的协议,POP、SMTP等邮件传输的协议,均使用了TCP协议。但是开销大

UDP

UDP是面向无连接的通讯协议,硬件之间不需要创建连接,UDP数据包括目的端口号和源端口号信息,由于通讯不需要连接,所以可以实现广播(广播的形式在局域网中大家都能都听到)发送,能够一对多,。UDP通讯时不需要接收方确认,属于不可靠的传输,可能会出现丢包现象,实际应用中要求程序员编程验证。UDP只用于特殊服务采用该协议。例如例如IP电话,视频会议

 

 

IP(网际协议):主要用于规范通信双方处于网络的地址,地址规范化

    IP层接受更底层网络接口层(网络接口层例如以太网设备驱动程序)发送的数据包,并且将数据发送给更高层的TCP或者UDP,相反IP层也会从TCP或者UDP接受数据传送到更底层,每一台设备在互联网上的IP都是唯一的。

UDP和TCP对比

1、TCP面向连接(如打电话要先拨号建立连接);UDP是无连接的,即发送数据之前不需要建立连接

2、TCP提供可靠的服务。也就是说,通过TCP连接传送的数据,无差错,不丢失,不重复,且按序到达;UDP尽最大努力交付,即不保证可靠交付 Tcp通过校验和,重传控制,序号标识,滑动窗口、确认应答实现可靠传输。如丢包时的重发控制,还可以对次序乱掉的分包进行顺序控制。

3、UDP具有较好的实时性,工作效率比TCP高,适用于对高速传输和实时性有较高的通信或广播通信。

4.每一条TCP连接只能是点到点的;UDP支持一对一,一对多,多对一和多对多的交互通信

5、TCP对系统资源要求较多,UDP对系统资源要求较少。

 

我们在用Socket编程时,UDP协议要求包小于64K。TCP没有限定;虽然在传输层,TCP不会对数据长度作出限制, 由于TCP是数据流协议,因此不存在包大小的限制(暂不考虑缓冲区的大小),这是指在用send函数时,数据长度参数不受限制。而实际上,所指定的这段数据并不一定会一次性发送出去,如果这段数据比较长,会被分段发送,如果比较短,可能会等待和下一次数据一起发送。UDP协议要求包小于64K。

但是在网络层(IP) 中都会对数据超过1500字节做出拆分,分批发送。TCP保证顺序,但是UDP不保证顺序。

数据链路层以太网协议下TCP和IP的数据长度:

UDP 包的大小就应该是 1500 - IP头(20) - UDP头(8) = 1472(Bytes)
TCP 包的大小就应该是 1500 - IP头(20) - TCP头(20) = 1460 (Bytes)

1.2在TCP/IP模型图例

在上一章节中,我们理解了OSI(open system internation)七层网络模型,那么做在tcp/ip通信模型中会将整个网络划分为5层,以此对应OSI,图例如下。

 

2:详解TCP通信 

我们知道了TCP(传输控制协议)是实现端对端的通信,需要建立三次握手连接,来保证端到端的通道创建。

TCP/IP协议的详细信息参看《TCP/IP协议详解》三卷本。下面是TCP报文格式图:

 

上图中有几个字段需要重点介绍下:
  (1)序号:Seq序号,占32位,用来标识从TCP源端向目的端发送的字节流,发起方发送数据时对此进行标记。
  (2)确认序号:Ack序号,占32位,只有ACK标志位为1时,确认序号字段才有效,Ack=Seq+1。
  (3)标志位:共6个,即URG、ACK、PSH、RST、SYN、FIN等,具体含义如下:
  (A)URG:紧急指针(urgent pointer)有效。
  (B)ACK:确认序号有效。
  (C)PSH:接收方应该尽快将这个报文交给应用层。
  (D)RST:重置连接。
  (E)SYN:发起一个新连接。
  (F)FIN:释放一个连接。

需要注意的是:
  (A)不要将确认序号Ack与标志位中的ACK搞混了。
  (B)确认方Ack=发起方Req+1,两端配对。

2.1三次握手创建:

所谓三次握手(Three-Way Handshake)即建立TCP连接,就是指建立一个TCP连接时,需要客户端和服务端总共发送3个包以确认连接的建立。在socket编程中,这一过程由客户端执行connect来触发,整个流程如下图所示:

 

(1)第一次握手:Client将标志位SYN置为1,随机产生一个值seq=J,并将该数据包发送给Server,Client进入SYN_SENT状态,等待Server确认。
  (2)第二次握手:Server收到数据包后由标志位SYN=1知道Client请求建立连接,Server将标志位SYN和ACK都置为1,ack=J+1,随机产生一个值seq=K,并将该数据包发送给Client以确认连接请求,Server进入SYN_RCVD状态。
  (3)第三次握手:Client收到确认后,检查ack是否为J+1,ACK是否为1,如果正确则将标志位ACK置为1,ack=K+1,并将该数据包发送给Server,Server检查ack是否为K+1,ACK是否为1,如果正确则连接建立成功,Client和Server进入ESTABLISHED状态,完成三次握手,随后Client与Server之间可以开始传输数据了。

2.2四次握手断开:

三次握手耳熟能详,所谓四次挥手(Four-Way Wavehand)即终止TCP连接,就是指断开一个TCP连接时,需要客户端和服务端总共发送4个包以确认连接的断开。在socket编程中,这一过程由客户端或服务端任一方执行close来触发,整个流程如下图所示:

 

由于TCP连接时全双工的,因此,每个方向都必须要单独进行关闭,这一原则是当一方完成数据发送任务后,发送一个FIN来终止这一方向的连接,收到一个FIN只是意味着这一方向上没有数据流动了,即不会再收到数据了,但是在这个TCP连接上仍然能够发送数据,直到这一方向也发送了FIN。首先进行关闭的一方将执行主动关闭,而另一方则执行被动关闭,上图描述的即是如此。


(1)第一次挥手:Client发送一个FIN,用来关闭Client到Server的数据传送,Client进入FIN_WAIT_1状态。
  (2)第二次挥手:Server收到FIN后,发送一个ACK给Client,确认序号为收到序号+1(与SYN相同,一个FIN占用一个序号),Server进入CLOSE_WAIT状态。
(3)第三次挥手:Server发送一个FIN,用来关闭Server到Client的数据传送,Server进入LAST_ACK状态。
  (4)第四次挥手:Client收到FIN后,Client进入TIME_WAIT状态,接着发送一个ACK给Server,确认序号为收到序号+1,Server进入CLOSED状态,完成四次挥手。

2.3为何什么3次握手创建,但是分手需要四次

由于TCP连接是全双工的的,因此,每个方向都必须要单独进行关闭简单来说。张三对说小红要分手(第一次),小红会把张三的东西还给张三(第二次),小红说可以跟张三分手(第三次),张三分手并把正式分手信息告诉小红(第四次)。

 

3:socket通信代码实现

3.1什么是socket

socekt是网络编程接口:socket被称作套接字,前边我们讲了TCP/IP模型,里边重要的协议TCP和UDP,那么TCP/IP也需要提供出来可以给程序员做网络开发的编程接口,这就是socket编程接口,http是轿车,提供了封装和显示数据的具体实现形式;socket就是发动机,提供网络通信的能力。

3.2socket代码简单实现

service端代码如下:

package com.thit.socket;

import java.io.InputStream;
import java.net.ServerSocket;
import java.net.Socket;

public class Service1 {
	//代码为固定套路
	public static void main(String[] args) throws Exception {
		//补充:端口范围0-65535,0-1023为系统占用端口
		//服务端指定端口
		int port=65531;
		ServerSocket service=new ServerSocket(port);
		//service将一直等待连接的到来
		System.out.println("-----service启动了!---------");

		Socket socket=service.accept();
		InputStream inputStream=socket.getInputStream();
		byte[] bytes=new byte[1024];
		int len;
		StringBuilder sBuilder=new StringBuilder();
		while ((len=inputStream.read(bytes))!=-1) {
			sBuilder.append(new String(bytes, 0, len, "UTF-8"));
		}
		System.out.println("service接受的数据是:"+sBuilder);
		inputStream.close();
		socket.close();
		service.close();
	}

}

客户端代码如下:

package com.thit.socket;

import java.io.IOException;
import java.io.OutputStream;
import java.net.Socket;

public class Client1 {

	public static void main(String[] args) throws Exception, IOException {
		// TODO Auto-generated method stub
		String host="127.0.0.1";
		int port=65531;
		//创建端到端的连接
		Socket socket=new Socket(host, port);
		OutputStream outputStream=socket.getOutputStream();
		String msg="hello word!";
		outputStream.write(msg.getBytes("UTF-8"));
		outputStream.close();
		socket.close();
	}

}

然后启动服务端和客户端,得到结果如下:

  • 1
    点赞
  • 2
    收藏
    觉得还不错? 一键收藏
  • 0
    评论
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值