套接字之 getsockname && getpeername
getsockname-获取本地地址;比如,在绑定的时候设置端口号为0由系统自动选择端口绑定,或者使用了INADDR_ANY通配所有地址的情况下,后面需要用到具体的地址和端口,就可以用getsockname获取地址信息;
getpeername-获取建立连接的对端的地址和端口;
下面为源码分析:
/*
* Get the local address ('name') of a socket object. Move the obtained
* name to user space.
*/ SYSCALL_DEFINE3(getsockname, int, fd, struct sockaddr __user *, usockaddr,
int __user *, usockaddr_len)
{
struct socket *sock;
struct sockaddr_storage address;
int len, err, fput_needed; /* 查找socket */
sock = sockfd_lookup_light(fd, &err, &fput_needed);
if (!sock)
goto out; err = security_socket_getsockname(sock);
if (err)
goto out_put; /* 调用socket操作的getname函数 */
err = sock->ops->getname(sock, (struct sockaddr *)&address, &len, );
if (err)
goto out_put; /* 拷贝地址到用户空间 */
err = move_addr_to_user(&address, len, usockaddr, usockaddr_len); out_put:
fput_light(sock->file, fput_needed);
out:
return err;
}
/*
* Get the remote address ('name') of a socket object. Move the obtained
* name to user space.
*/ SYSCALL_DEFINE3(getpeername, int, fd, struct sockaddr __user *, usockaddr,
int __user *, usockaddr_len)
{
struct socket *sock;
struct sockaddr_storage address;
int len, err, fput_needed; /* 查找socket */
sock = sockfd_lookup_light(fd, &err, &fput_needed);
if (sock != NULL) {
err = security_socket_getpeername(sock);
if (err) {
fput_light(sock->file, fput_needed);
return err;
} /* 调用socket操作的getname获取对端地址,此时最后一个参数为1 */
err =
sock->ops->getname(sock, (struct sockaddr *)&address, &len,
); /* 将地址拷贝到用户空间 */
if (!err)
err = move_addr_to_user(&address, len, usockaddr,
usockaddr_len);
fput_light(sock->file, fput_needed);
}
return err;
}
ipv4情况下,getsockname和getpeername都会调用下面的inet_getname函数;
/*
* This does both peername and sockname.
*/
int inet_getname(struct socket *sock, struct sockaddr *uaddr,
int *uaddr_len, int peer)
{
struct sock *sk = sock->sk;
struct inet_sock *inet = inet_sk(sk);
DECLARE_SOCKADDR(struct sockaddr_in *, sin, uaddr); /* 设置地址族 */
sin->sin_family = AF_INET; /* 获取对端地址 */
if (peer) {
/* 目的端口为空或者为未连接状态 */
if (!inet->inet_dport ||
((( << sk->sk_state) & (TCPF_CLOSE | TCPF_SYN_SENT)) &&
peer == ))
return -ENOTCONN;
/* 设置目的端口和地址 */
sin->sin_port = inet->inet_dport;
sin->sin_addr.s_addr = inet->inet_daddr;
}
/* 获取本地地址 */
else {
/* 获取接收时ip */
__be32 addr = inet->inet_rcv_saddr; /* 不存在则获取发送时ip */
if (!addr)
addr = inet->inet_saddr; /* 设置端口和地址 */
sin->sin_port = inet->inet_sport;
sin->sin_addr.s_addr = addr;
} /* 填充部分 */
memset(sin->sin_zero, , sizeof(sin->sin_zero)); /* 设置地址长度 */
*uaddr_len = sizeof(*sin);
return ;
}
套接字之 getsockname && getpeername的更多相关文章
- <网络编程>基本TCP套接字编程
tcp提供了可靠传输,当tcp向另一端发送数据的时候,要求对端返回一个确认.如果没有接收到确认,tcp就重传数据并且等待更长时间,数次重传失败后,tcp才放弃. 建立一个tcp连接会发生如下事情: 服 ...
- 17.3.13---socket网络套接字介绍--函数和数据类型
1----Socket类型 套接字格式:socket(family,type[,protocal])使用给定的地址族,套接字类型,协议编号(默认为0)来创建套接字 socket类型 描述 socket ...
- 基本TCP套接字编程
1.listen函数 将主动套接字转换成一个被动套接字 backlog指定相应套接字连接队列的大小. 监听套接字有2个队列: (1)未完成连接队列,接收客户SYN,发出SYN.ACK,等待完成三次握手 ...
- [16]APUE:套接字
[a] socket / socketpair #include <sys/socket.h> int socket(int domain, int type, int protocol) ...
- python套接字基本使用
socket socket通常也称作"套接字",用于描述IP地址和端口,应用程序通常通过"套接字"向网络发出请求或者应答网络请求,可以认为是一种计算机网络的数据 ...
- liunx 套接字编程(Linux_C++)
网络中的进程是如何通信的? 在网络中进程之间进行通信的时候,那么每个通信的进程必须知道它要和哪个计算机上的哪个进程通信.否则通信无从谈起!在本地可以通过进程PID来唯一标识一个进程,但是在网络中这是行 ...
- Linux套接字编程
网络中的进程是如何通信的? 在网络中进程之间进行通信的时候,那么每个通信的进程必须知道它要和哪个计算机上的哪个进程通信.否则通信无从谈起!在本地可以通过进程PID来唯一标识一个进程,但是在网络中这是行 ...
- Python之socket(套接字)
Socket 一.概述 socket通常也称作"套接字",用于描述IP地址和端口,是一个通信链的句柄,应用程序通常通过"套接字"向网络发出请求或者应答网络请求. ...
- 第十六章:网络IPC:套接字
16.1.引言 上一章考查了各种Unix系统所提供的经典进程间通信(IPC)机制:管道.先进先出.消息队列.信号量以及共享内存.通过这些机制,同一台计算机上运行的进程可以相互通信.本章将考查不同计算机 ...
随机推荐
- 前端页面多级联动传输数据类型问题(数组or字符串)后端处理
在最近的工作中,遇到一个问题,个人所做的简历模块中有两个字段,分别是个人信息中的户口所在地和现居住城市. 前端界面中这两个选项框是用到了二级和三级联动,在向后端传输时希望可以通过数组类型进行传输,例如 ...
- 关于记录log日志的几种方法
最近在记录日志的时候总结了几种方式: 1.使用log4j2记录 2.使用log4j记录 3.使用logback配置,记录前使用 private final Logger logger = Logge ...
- java实现spark常用算子之mapPartitions
import org.apache.spark.SparkConf;import org.apache.spark.api.java.JavaRDD;import org.apache.spark.a ...
- Echarts常见问题汇总
关于echarts使用的常见问题总结 来源:李文杨 关于echarts使用的问题总结1.legend图例不显示的问题:在legend中的data为一个数组项,数组项通常为一个字符串,每一项需要对应一 ...
- java apache-commons-collections中Map辅助类的使用
前言 apache-commons-collections中Map辅助类,很是有用.尽管我们通过原生Map经过业务逻辑处理也能达到相同的作用与效果,但毕竟作为一个开源的工具类辅助类,对它有个了解还是有 ...
- monkey 进阶使用手册,monkey随机测试后怎么定位问题
首先我们知道使用monkey后,我们可以查看三种类型的日志,一种是安卓内核日志,一种是安卓系统自己的日志,还有一种是monkey日志. 当我们使用monkey进行随机测试时,如何才知道我们这次随机测试 ...
- xml_dom4j
1.用dom4j解析文件 package Xml3; import java.io.File; import java.util.Iterator; import org.dom4j.Attribut ...
- python、mysql三-1:存储引擎
一 什么是存储引擎 mysql中建立的库===>文件夹 库中建立的表===>文件 现实生活中我们用来存储数据的文件有不同的类型,每种文件类型对应各自不同的处理机制:比如处理文本用txt类型 ...
- Powershell - 获取服务器启动时间
www.orangeisland.cn 使用以下命令,直接获取服务器启动时间: 通过以下脚本,批量获取服务器的启动时间: $TextPath = "C:\Users\admin\Deskto ...
- string::find_first_not_of
string (1) size_t find_first_not_of (const string& str, size_t pos = 0) const noexcept; c-string ...