Linux协议栈概括图
应用层Socket操作函数集inet_stream_opsINET层tcp_protinet_dgram_opsinet_sockraw_opsudp_protraw_prot传输层网络层sk->sk_receive_queuesk->sk_write_queue__skb_queue_tail()tcp_rcv_established()skb_queue_tail(&sk->sk_receive_queue, skb)sock_queue_rcv_skb()tcp_v4_do_rcv()ip_queue_xmit()raw_send_hdrinc()ip_route_output_flow()ip_push_pending_frames()tcp_v4_rcv()udp_queue_rcv_skb()icmp_pointers->handler()raw_rcv_skb()udp_rcv()icmp_rcv()raw_rcv()ipprot->handler()NF_HOOK(PF_INET, NF_IP_LOCAL_OUT)tcp、udpraw_v4_input()rawip_local_deliver_finish()dst_output()skb->dst->output()ip_forward_finish()NF_HOOK(PF_INET, NF_IP_FORWARD)raw_rcv()ip_call_ra_chain()NF_HOOK(PF_INET, NF_IP_LOCAL_IN)ip_defrag()ip_local_deliver()ip_mc_output()分片ip_fragment()ip_finish_output()分片ip_output()ip_forward()forwardlocal_inskb->dst->input()dst_input()NF_HOOK(PF_INET, NF_IP_POST_ROUTING)ip_finish_output2()ip_route_input_slow()单播ip_route_input_mc()多播路由处理ip_route_input()hh->hh_output()dst->neighbour->output()neigh_compat_output()dev_queue_xmit()ip_rcv_finish()NF_HOOK(PF_INET, NF_IP_PRE_ROUTING)packet_type->func()(ip_rcv、arp_rcv)dev->hard_start_xmit()驱动层如驱动中的e1000_xmit_frame()handle_bridge()桥模式netif_receive_skb()物理层OUTPUT网络设备INPUT, 调用sgtcp_replace_ts_recenttcp_sequencetcp_paws_discard!LISTEN && !ESTABLISHED4, 函数中,将i_fop指向s结构。d函数tcp_rcv_state_processtcp_fast_parse_optionstcp_rcv_establishedESTABLISHED^-tcp_output.c:1332行,tcp_transmit_skb tcp_output.c:278行,ip_queue_xmit||如果定义了NETFILTER,先进入LOCAL_OUT| ip_output.c:401行:ip_queue_xmit2 ip_output.c:317行;skb->dst->output(skb);(在route.c的ip_route_*put*函数中进 dst->output函数指针付值=ip_output或 ip_mc_output或ip_rt_bug) case TCP_SYN_RECV(收到ACK)(Server端)如果ouput tcp_set_state能会到 tcp_data_snd_check (tcp_input.c:4030) tcp_ack_snd_check (tcp_input.c:4031)LISTEN__skb_queue_tailtcp_v4_do_rcv将数据包放入队列的尾部sk->receive_queue并调用sk->data_ready通知上层数据到达在这之间做了tcp checksum校验等tcp_v4_rcvipprot->protocol = TCPProtocol.c:56行开始,初始化全局数组inet_protos,在ip_input.c:262行查找到相应的接收函数(tcp、udp、icmp、igmp)udp_rcvipprot->protocol = UDPip_local_deliver_finish如果定义了NETFILTER,则先进入LOCAL_IN转发数据包ttcpraw_v4_inputip_local_deliver数据包发往本地检查ip数据包的内容Ip_forwardTcp_output.c:278如果定义了NETFILTER,则先进入IP_FORWARDIqlter进行路由,并把skb->dst->input函数指针指向ip_local_deliver或ip_error或ip_forward或ipRoute.c:1658-1675行,在路由时会先在路由缓存中查找,没找到则由ip_route_input_slow函数从路由表中查,并加入到缓存中ip_options_compileip_forward_finiship_route_input_slow在缓存中找到ip_output.c:367ipip_forward_optionsip_output.c:397ip_ip_route_inputip_send如果定义了NETFLOCAL_OUTip_rcv_finish如果定义了NETFILTER,则先进入PRE_ROUTINGipip_fragmentip_rcv如果产生了分片即skb->len > rt->u.dst.pmtu并将ip_output函数指针做为参数给ip_fragmentDev.c:14行,调用ip_rcv函数在ip_output.c:1001行初始化了ip_packet_type,使它的成员func指向ip_rcv函数Dev.c:1553行,通过__skb_dequeue函数取得sk_buff,netif_receive_skbProcess_backlogc:1622行,调用dev->poll(dev, &budget)Net_rx_action如果定义POST_q.c:90行,产生软中断,通过全局变量q_vec的函数指针调用net_rx_action2847行,函数net_dev_init中,将_action函数指针传给softirq_vec.action,oftirq中通过h->action调用net_rx_actiondo_softirq2751行,同时将queue->blog_dev.poll指向s_backlog函数ksoftirqd内核线程,进程调度将从网卡驱动接收到的sk_buff放到内核接收队列中通过__skb_queue_tail函数实现netif_rx网络数据交互模型
服务器
Socket()客户端bind()Socket()listen()accept()建立连接connet()read()recv()请求数据write()send()write()send()应答数据read()recv()close()close()面向连接的Socket工作流程
服务器
Socket()客户端Socket()bind()recvfrom()请求数据sendto()sendto()应答数据recvfrom()close()close()面向无连接的Socket工作流程
socket调用
socket()sys_socketcall()sys_socket()sock_create()__sock_create()sock_alloc()sock_map_fd()close调用
close()sys_close()filp_close()fput()file->op->release()sock_close()sock->ops->release()tcp_close()、udp_close()bind调用
bind()sys_socketcall()sys_bind()sockfd_lookup()security_socket_bind()security_ops->socket_bind()selinux_socket_bind()sock->ops->bind()inet_bind()type=SOCK_RAWinet_bind()sockfd_put()connect调用
connect()sys_connect()sk->sk_prot->connect()tcp_v4_connect()ip_route_connect()tcp_connect()tcp_transmit_skb()listen调用
listen()sys_socketcall()sys_listen()sockfd_lookup()security_socket_listen()sock->ops->listen()inet_listen()sockfd_put()accept调用
accept()sys_socketcall()sys_accept()sockfd_lookup()sock_alloc()security_socket_accept()sock->ops->accept()inet_accept()security_socket_post_accept()read调用
read()sys_read()sock_readv()sock_readv_writev()recv调用
recv()sys_recv()recvfrom调用
recvfrom()Sock层sys_recvfrom()sock_recvmsg()sock->ops->recvmsg()inet_stream_ops->recvmsg()inet_dgram_ops->recvmsg()sock_common_recvmsg()sk->sk_prot->recvmsg()tcp_prot->recvmsg()tcp_recvmsg()udp_prot->recvmsg()udp_recvmsg()skb_recv_datagram()NOT NULL 读取skb_dequeue()读取inet_sockraw_ops->recvmsg()INET Sock层raw_prot->recvmsg()raw_recvmsg()sk->receive_queneNULLsk->sk_backlog_rcv()sk->sk_receive_queue填充tcp_v4_do_rcv()tcp_rcv_established()填充sock_queue_rcv_skb()IP 层raw_rcv()tcp_v4_rcv()udp_rcv()write调用
write()sys_write()sock_writev()sock_readv_writev()send调用
send()sys_send()sendto调用
sendto()Sock层sys_sendto()sock_sendmsg()sock->ops->sendmsg()inet_stream_ops->sendmsg()inet_dgram_ops->sendmsg()inet_sendmsg()sk->sk_prot->sendmsg()tcp_prot->sendmsg()tcp_sendmsg()skb_entail()填充发送队列udp_prot->sendmsg()udp_sendmsg()inet_sockraw_ops->sendmsg()INET Sock层raw_prot->sendmsg()raw_sendmsg()sk->sk_write_queueip_route_output_flow()__tcp_push_pending_frames()立即发送tcp_push_one()tcp_transmit_skb()raw_send_hdrinc()tp->af_specific->queue_xmit()ip_route_output_flow()IP 层ip_queue_xmit()ip_route_output_flow()udp_push_pending_frames()ip_push_pending_frames()NF_HOOK(PF_INET, NF_IP_LOCAL_OUT)dst_output()
因篇幅问题不能全部显示,请点此查看更多更全内容
Copyright © 2019- dfix.cn 版权所有 湘ICP备2024080961号-1
违法及侵权请联系:TEL:199 1889 7713 E-MAIL:2724546146@qq.com
本站由北京市万商天勤律师事务所王兴未律师提供法律服务