使用套接字除了可以实现网络间不同主机间的通信外,还可以实现同一主机的不同进程间的通信,且建立的通信是双向的通信。这里所指的使用套接字实现进程间通信,是由将通信域指定为PF_UNIX来实现的。该函数的形式如下:
int socket(int domain, int type, int protocol);
socket函数中的domain参数用于指定通信域,domain参数取PF_UNIX时,表示创建UNIX域的套接字。使用PF_UNIX域的套接字可以实现同一机器上的不同进程间的通信。
调用bind函数实现了套接字与地址(这里是文件名)的绑定。bind函数的具体信息如下:
int bind(int sockfd, const struct sockaddr *my_addr, socklen_t addrlen);
其参数my_addr为指向结构体sockaddr_un的指针,该结构体的定义如下:
#define UNIX_PATH_MAX 108
struct sockaddr_un {
sa_family_t sun_family; /*PF_UNIX或AF_UNIX */
char sun_path[UNIX_PATH_MAX]; /* 路径名 */
};
在该结构体中,sun_family为AF_UNIX。sun_path是套接字在文件系统中的路径名。
Unix域套接字是通过套接字API实现的简单的协议族。实际上它并不代表一个网络协议;它只能连接到同一台机器上的套接字。它提供了灵活的IPC机制。它的地址是它所在的文件系统的路径名,创建之后套接字就和路径名绑定在一起。用来表示Unix域地址的套接字文件能够使用stat()但是不能通过open()打开,而且应该使用套接字API对它进行操作。
Unix域套接字是面向连接的,每个套接字的连接都建立了一个新的通讯信道。服务器可能同时处理许多连接,但对于每个连接都有不同的文件描述符。这个属性使Unix域套接字能够比命名管道更好的适应IPC任务。
.
在一个终端运行服务器,然后在另一个终端(在相同目录下)运行客户端。当从客户端输入一行时,数据将通过套接字送到服务器。当退出客户端,服务器将等待另外一个连接。还可以通过客户端程序的重定向输入来传送文件,cat uclient.c | ./uclient 或 ./uclient < uclient.c。
服务器程序userver.c
/* userver.c - Simple Unix Domain Socket server */
/* Waits for a connection on the ./sample-socket Unix domain
socket. Once a connection has been established, copy data
from the socket to stdout until the other end closes the
connection, and then wait for another connection to the
socket. */
#include <stdio.h>
#include <sys/socket.h>
#include <sys/un.h>
#include <unistd.h>
#include "sockutil.h" /* some utility functions */
int main(void) {
struct sockaddr_un address;
int sock, conn;
size_t addrLength;
if ((sock = socket(PF_UNIX, SOCK_STREAM, 0)) < 0)
die("socket");
/* Remove any preexisting socket (or other file) */
unlink("./sample-socket");
address.sun_family = AF_UNIX; /* Unix domain socket */
strcpy(address.sun_path, "./sample-socket");
/* The total length of the address includes the sun_family
element */
addrLength = sizeof(address.sun_family) +
strlen(address.sun_path);
if (bind(sock, (struct sockaddr *) &address, addrLength))
die("bind");
if (listen(sock, 5))
die("listen");
while ((conn = accept(sock, (struct sockaddr *) &address,
&addrLength)) >= 0) {
printf("---- getting data\n");
copyData(conn, 1);
printf("---- done\n");
close(conn);
}
if (conn < 0)
die("accept");
close(sock);
return 0;
}
客户端程序uclient.c
/* uclient.c - Simple Unix Domain Socket client */
/* Connect to the ./sample-socket Unix domain socket, copy stdin
into the socket, and then exit. */
#include <sys/socket.h>
#include <sys/un.h>
#include <unistd.h>
#include "sockutil.h" /* some utility functions */
int main(void) {
struct sockaddr_un address;
int sock;
size_t addrLength;
if ((sock = socket(PF_UNIX, SOCK_STREAM, 0)) < 0)
die("socket");
address.sun_family = AF_UNIX; /* Unix domain socket */
strcpy(address.sun_path, "./sample-socket");
/* The total length of the address includes the sun_family
element */
addrLength = sizeof(address.sun_family) +
strlen(address.sun_path);
if (connect(sock, (struct sockaddr *) &address, addrLength))
die("connect");
copyData(0, sock);
close(sock);
return 0;
}
注:如果客户端在服务器bind之前进行connect操作,connect会因为缺少套接字文件而失败。
accept和connect是两个阻塞调用。
/* sockutil.c - Utility functions used in socket example programs */
#include <stdio.h>
#include <stdlib.h>
#include <unistd.h>
#include "sockutil.h"
/* issue an error message via perror() and terminate the program */
void die(char * message) {
perror(message);
exit(1);
}
/* Copies data from file descriptor 'from' to file descriptor
'to' until nothing is left to be copied. Exits if an error
occurs. This assumes both from and to are set for blocking
reads and writes. */
void copyData(int from, int to) {
char buf[1024];
int amount;
while ((amount = read(from, buf, sizeof(buf))) > 0) {
if (write(to, buf, amount) != amount) {
die("write");
return;
}
}
if (amount < 0)
die("read");
}
相关推荐
通过java socket和lettuce框架基于UNIX域套接(UNIX Domain Socket)协议实现redis连接和操作,使用redis.sock文件
代码利用UNIX域套接字,分别实现了TCP协议和UDP协议的本地通信。
UNIX域套接字实现服务器客户端之间的通信
经过几天对UNIX域套接字传送文件描述符的学习,根据自己的认识对网络和书本上的知识进行了简单的整理,希望能帮到大家,让新手们比我少走些弯路。
requests-unixsocket, 使用请求通过UNIX域套接字进行HTTP会话 请求 UNIXSocket 使用请求通过UNIX域套接字来讨论 HTTP用法你可以通过实例化一个特殊的Session 对象来使用它:import jsonimport requests_unixsocket
获取Unix域套接字的路径的 在Windows上不起作用。 安装 $ npm install unix-path-max 用法 const unixPathMax = require ( 'unix-path-max' ) ; ( async ( ) => { console . log ( await unixPathMax ( ) ) ; /...
nbudstee:非阻塞Unix域套接字Tee 将Tees输入到零个或多个非阻塞Unix域套接字,每个套接字可以具有零个或多个连接的读取器, 和/或零个或多个现有FIFO,每个FIFO可以恰好具有一个现有读取器。 除非使用-n /-no-...
unix_socket_socket编程_Unix域套接字_udpclient_tunedaa_网络编程_源码.zip
unix_socket_socket编程_Unix域套接字_udpclient_tunedaa_网络编程_源码.rar
该程序是我写的博客“一起talk C栗子吧( 第一百五十七回:C语言实例--基于AF_UNIX域的数据报套接字通信)”的配套程序,共享给大家使用
mio-uds一个用于将Unix域套接字与mio集成的库。 基于标准库对Unix套接字的支持,所有abstractio mio-uds除外一个用于将Unix域套接字与mio集成的库。 基于标准库对Unix套接字的支持,除了所有抽象和类型都是非阻塞的...
junixsocket junixsocket是一个Java / JNI库,允许使用Java的(AF_UNIX套接字)。为什么很酷junixsocket是一个小型的模块化库。 仅安装您需要的内容。 与其他实现相反, junixsocket扩展了Java Sockets API( java...
这套应用程序接口也被用于Unix域套接字(Unix domain sockets),后者可以在单机上作为进程间通讯(IPC)频道的接口。 这种基于流的传输层接口(TLI)应用程序接口为套接字应用程序接口提供了一种选择。 不过,最近...
服务器-使用UNIX域套接字的客户端通信 功能性 DomainSocket类提供Unix域套接字的抽象。 您可以创建服务器套接字和客户端套接字进行通信。 有一个Daemon类和Sender类(服务器和客户端)作为用法示例。 例子 您可以...
linux系统中通过unix域套接字实现小写到大写的转换。对理解套接字编程有点促进作用
库辅助使用 Unix 域套接字在进程之间传递文件描述符克隆概述这个库为可以在 Unix 域套接字上完成的黑魔法提供了一个简单的接口,比如将文件描述符从一个进程传递到另一个进程。 它应该 100% 符合 Single Unix ...
juds, Java的Unix域套接字库 JUDS 抽象Java Unix域套接字( JUDS ) 提供类来处理Java中访问Unix域套接字的需求。 源提供给包含编译的原生C 代码的共享库,Java UnixDomainSocket类通过Java类调用它来打开。关闭。取
转储Unix域套接字流量。 要求 密件抄送 python密件抄送绑定 例子 字符串输出 $ sudo ./sockdump.py --format string /var/run/docker.sock waiting for data 19:23:06.633 >>> process docker [31042 -> 13710] len...
东京乌兹用于Tokio的Unix域套接字的实现用法首先,将其添加到您的Cargo.toml : [ dependencies ]tokio-uds = " 0.1 " 接下来,将其添加到您的板条箱中: extern crate tokio_uds;执照该项目获得以下任一许可Apache...