当前位置: 首页 > wzjs >正文

手机网站自适应布局怎么做seo域名综合查询

手机网站自适应布局怎么做,seo域名综合查询,哪有做网站,校园网站建设的缺陷Socket函数详解&#xff1a;完整指南 1. 函数概述 socket()函数是网络编程中创建通信端点的基础API&#xff0c;它在不同的操作系统上都有实现&#xff0c;是跨平台网络编程的核心。 #include <sys/socket.h> int socket(int domain, int type, int protocol);成功时返…

Socket函数详解:完整指南

1. 函数概述

socket()函数是网络编程中创建通信端点的基础API,它在不同的操作系统上都有实现,是跨平台网络编程的核心。

#include <sys/socket.h>
int socket(int domain, int type, int protocol);

成功时返回非负整数(socket文件描述符),失败时返回-1并设置errno。

2. 参数详解

2.1 domain(协议族/地址族)

决定了socket如何解释地址以及它可以通信的网络范围。

值(宏)描述典型用途地址结构
AF_UNIX/AF_LOCAL本地通信,基于文件路径同一主机上的进程间通信(IPC)struct sockaddr_un
AF_INETIPv4网络协议基于IPv4的网络通信struct sockaddr_in
AF_INET6IPv6网络协议基于IPv6的网络通信struct sockaddr_in6
AF_PACKET底层数据包接口,直接访问链路层网络嗅探、自定义协议开发struct sockaddr_ll
AF_NETLINK内核与用户空间通信路由表配置、防火墙规则管理struct sockaddr_nl
AF_BLUETOOTH蓝牙通信蓝牙设备间数据传输struct sockaddr_bt

注意:在大多数实现中,AF_*(Address Family)和PF_*(Protocol Family)宏的值相同。历史上曾打算让它们具有不同含义,但这种区分在实践中并未实现。

2.2 type(Socket类型)

定义socket的通信特性,如数据传输方式、可靠性和消息边界处理。

值(宏)描述特性典型应用场景
SOCK_STREAM面向连接的可靠字节流可靠性、有序性、流式传输HTTP、FTP、SSH、数据库连接
SOCK_DGRAM无连接的消息传递(数据报)快速、低开销、可能丢失DNS查询、实时音视频、游戏
SOCK_RAW原始socket,可直接访问底层协议自定义协议头、更多控制权网络监控、协议开发、安全工具
SOCK_SEQPACKET有序、可靠、保留消息边界的数据包结合STREAM和DGRAM的优点SCTP协议、特定IPC场景

可与以下标志组合使用(按位或|操作)

  • SOCK_NONBLOCK:创建非阻塞模式的socket
  • SOCK_CLOEXEC:设置close-on-exec标志,防止socket描述符在执行exec()时被继承

2.3 protocol(具体协议)

通常设为 0,表示根据 domaintype 自动选择默认协议。也可显式指定:

协议值描述适用domain和type组合
IPPROTO_TCP传输控制协议AF_INET/AF_INET6 + SOCK_STREAM
IPPROTO_UDP用户数据报协议AF_INET/AF_INET6 + SOCK_DGRAM
IPPROTO_SCTP流控制传输协议AF_INET/AF_INET6 + SOCK_SEQPACKET
IPPROTO_ICMPInternet控制消息协议AF_INET + SOCK_RAW
IPPROTO_RAW原始IP包AF_INET/AF_INET6 + SOCK_RAW

3. 常见用例示例

3.1 创建TCP Socket (IPv4)

int tcp_sock = socket(AF_INET, SOCK_STREAM, 0);
if (tcp_sock == -1) {perror("socket creation failed");exit(EXIT_FAILURE);
}

3.2 创建UDP Socket (IPv6)

int udp_sock = socket(AF_INET6, SOCK_DGRAM, 0);
if (udp_sock == -1) {perror("socket creation failed");exit(EXIT_FAILURE);
}

3.3 创建Unix Domain Socket(UDS)

int uds_sock = socket(AF_UNIX, SOCK_STREAM, 0);
if (uds_sock == -1) {perror("socket creation failed");exit(EXIT_FAILURE);
}

3.4 创建非阻塞TCP Socket

// 方法1: 使用socket()的标志
int nonblock_sock = socket(AF_INET, SOCK_STREAM | SOCK_NONBLOCK, 0);// 方法2: 使用fcntl()修改已创建的socket
#include <fcntl.h>
int sock = socket(AF_INET, SOCK_STREAM, 0);
fcntl(sock, F_SETFL, fcntl(sock, F_GETFL, 0) | O_NONBLOCK);

3.5 创建原始Socket (需要特权)

// 抓取ICMP包
int raw_sock = socket(AF_INET, SOCK_RAW, IPPROTO_ICMP);
if (raw_sock == -1) {perror("raw socket creation failed (may require root privileges)");exit(EXIT_FAILURE);
}

4. 网络Socket与Unix Domain Socket对比

4.1 通信机制对比

特性Unix Domain Socket (UDS)网络Socket (TCP/IP)
地址格式文件路径 (例如:“/tmp/my.sock”)IP地址+端口号 (例如:“127.0.0.1:8080”)
通信范围仅限同一主机上的进程可跨网络与远程主机通信
性能更高效(无网络协议栈开销)需经过完整网络协议栈
数据传输直接内核内存拷贝经过网络缓冲区和协议处理
安全性基于文件系统权限控制需要额外的网络安全措施
支持的功能可传递文件描述符无法直接传递文件描述符

4.2 性能差异

UDS比本地环回TCP套接字(127.0.0.1)具有显著优势:

  • 吞吐量通常高50%-100%
  • 延迟更低(无TCP/IP协议栈开销)
  • CPU使用率更低

5. 完整示例:Unix Domain Socket

5.1 服务器端

#include <sys/socket.h>
#include <sys/un.h>
#include <unistd.h>
#include <stdio.h>
#include <stdlib.h>
#include <string.h>int main()
{// 创建socketint server_fd = socket(AF_UNIX, SOCK_STREAM, 0);if (server_fd == -1){perror("socket");return EXIT_FAILURE;}// 准备地址结构struct sockaddr_un addr;memset(&addr, 0, sizeof(struct sockaddr_un));addr.sun_family = AF_UNIX;strncpy(addr.sun_path, "/tmp/uds_socket", sizeof(addr.sun_path) - 1);// 删除可能存在的老socket文件unlink(addr.sun_path);// 绑定socket到地址if (bind(server_fd, (struct sockaddr *)&addr, sizeof(addr)) == -1){perror("bind");close(server_fd);return EXIT_FAILURE;}// 监听连接请求if (listen(server_fd, 5) == -1){perror("listen");close(server_fd);return EXIT_FAILURE;}printf("UDS Server waiting for connections on %s\n", addr.sun_path);// 接受连接int client_fd = accept(server_fd, NULL, NULL);if (client_fd == -1){perror("accept");close(server_fd);return EXIT_FAILURE;}// 通信示例char buf[100] = {0};ssize_t bytes_read = read(client_fd, buf, sizeof(buf) - 1);if (bytes_read > 0){printf("UDS Server received: %s\n", buf);write(client_fd, "Hello from UDS Server!", 22);}// 清理资源close(client_fd);close(server_fd);unlink(addr.sun_path);return EXIT_SUCCESS;
}

5.2 客户端

#include <sys/socket.h>
#include <sys/un.h>
#include <unistd.h>
#include <stdio.h>
#include <stdlib.h>
#include <string.h>int main() {// 创建socketint sock = socket(AF_UNIX, SOCK_STREAM, 0);if (sock == -1) {perror("socket");return EXIT_FAILURE;}// 准备服务器地址struct sockaddr_un addr;memset(&addr, 0, sizeof(struct sockaddr_un));addr.sun_family = AF_UNIX;strncpy(addr.sun_path, "/tmp/uds_socket", sizeof(addr.sun_path) - 1);// 连接到服务器if (connect(sock, (struct sockaddr*)&addr, sizeof(addr)) == -1) {perror("connect");close(sock);return EXIT_FAILURE;}// 发送数据write(sock, "Hello from UDS Client!", 22);// 接收响应char buf[100] = {0};ssize_t bytes_read = read(sock, buf, sizeof(buf) - 1);if (bytes_read > 0) {printf("UDS Client received: %s\n", buf);}// 清理close(sock);return EXIT_SUCCESS;
}

6. 完整示例:TCP Socket

6.1 服务器端

#include <sys/socket.h>
#include <netinet/in.h>
#include <unistd.h>
#include <stdio.h>
#include <stdlib.h>
#include <string.h>
#include <arpa/inet.h>int main() {// 创建socketint server_fd = socket(AF_INET, SOCK_STREAM, 0);if (server_fd == -1) {perror("socket");return EXIT_FAILURE;}// 设置地址重用选项int opt = 1;if (setsockopt(server_fd, SOL_SOCKET, SO_REUSEADDR, &opt, sizeof(opt)) == -1) {perror("setsockopt");close(server_fd);return EXIT_FAILURE;}// 准备IPv4地址结构struct sockaddr_in addr;memset(&addr, 0, sizeof(struct sockaddr_in));addr.sin_family = AF_INET;addr.sin_addr.s_addr = INADDR_ANY; // 监听所有网络接口addr.sin_port = htons(8080);       // 使用8080端口// 绑定socket到地址if (bind(server_fd, (struct sockaddr*)&addr, sizeof(addr)) == -1) {perror("bind");close(server_fd);return EXIT_FAILURE;}// 监听连接请求if (listen(server_fd, 5) == -1) {perror("listen");close(server_fd);return EXIT_FAILURE;}printf("TCP Server waiting for connections on port 8080...\n");// 接受连接struct sockaddr_in client_addr;socklen_t client_len = sizeof(client_addr);int client_fd = accept(server_fd, (struct sockaddr*)&client_addr, &client_len);if (client_fd == -1) {perror("accept");close(server_fd);return EXIT_FAILURE;}// 打印客户端信息char client_ip[INET_ADDRSTRLEN];inet_ntop(AF_INET, &client_addr.sin_addr, client_ip, sizeof(client_ip));printf("Connection from %s:%d\n", client_ip, ntohs(client_addr.sin_port));// 通信示例char buf[100] = {0};ssize_t bytes_read = read(client_fd, buf, sizeof(buf) - 1);if (bytes_read > 0) {printf("TCP Server received: %s\n", buf);write(client_fd, "Hello from TCP Server!", 22);}// 清理资源close(client_fd);close(server_fd);return EXIT_SUCCESS;
}

6.2 客户端

#include <sys/socket.h>
#include <netinet/in.h>
#include <arpa/inet.h>
#include <unistd.h>
#include <stdio.h>
#include <stdlib.h>
#include <string.h>int main() {// 创建socketint sock = socket(AF_INET, SOCK_STREAM, 0);if (sock == -1) {perror("socket");return EXIT_FAILURE;}// 准备服务器地址struct sockaddr_in addr;memset(&addr, 0, sizeof(struct sockaddr_in));addr.sin_family = AF_INET;addr.sin_port = htons(8080);// 将字符串IP地址转换为网络字节序if (inet_pton(AF_INET, "127.0.0.1", &addr.sin_addr) <= 0) {perror("inet_pton");close(sock);return EXIT_FAILURE;}// 连接到服务器if (connect(sock, (struct sockaddr*)&addr, sizeof(addr)) == -1) {perror("connect");close(sock);return EXIT_FAILURE;}printf("Connected to server at 127.0.0.1:8080\n");// 发送数据write(sock, "Hello from TCP Client!", 22);// 接收响应char buf[100] = {0};ssize_t bytes_read = read(sock, buf, sizeof(buf) - 1);if (bytes_read > 0) {printf("TCP Client received: %s\n", buf);}// 清理close(sock);return EXIT_SUCCESS;
}

7. 高级Socket选项

使用setsockopt()getsockopt()可以调整socket的各种属性:

int setsockopt(int sockfd, int level, int optname, const void *optval, socklen_t optlen);
int getsockopt(int sockfd, int level, int optname, void *optval, socklen_t *optlen);

常用选项示例

// 允许地址复用(避免"Address already in use"错误)
int opt = 1;
setsockopt(sockfd, SOL_SOCKET, SO_REUSEADDR, &opt, sizeof(opt));// 设置接收超时
struct timeval tv = {.tv_sec = 5, .tv_usec = 0}; // 5秒超时
setsockopt(sockfd, SOL_SOCKET, SO_RCVTIMEO, &tv, sizeof(tv));// 启用TCP保活机制
int keepalive = 1;
setsockopt(sockfd, SOL_SOCKET, SO_KEEPALIVE, &keepalive, sizeof(keepalive));// 设置TCP保活参数(Linux特有)
int idle = 60;      // 60秒无数据则开始探测
int interval = 5;   // 每5秒发送一次探测包
int maxpkt = 5;     // 最多发送5次探测包
setsockopt(sockfd, IPPROTO_TCP, TCP_KEEPIDLE, &idle, sizeof(idle));
setsockopt(sockfd, IPPROTO_TCP, TCP_KEEPINTVL, &interval, sizeof(interval));
setsockopt(sockfd, IPPROTO_TCP, TCP_KEEPCNT, &maxpkt, sizeof(maxpkt));

8. 选择建议与最佳实践

8.1 选择合适的Socket类型

  • Unix Domain Socket
    • 同一主机上的进程间通信
    • 需要高性能、低延迟的IPC场景
    • 需要传递文件描述符的场景
    • 示例:Web服务器与本地缓存通信、数据库连接
  • TCP Socket
    • 需要可靠的、有序的数据传输
    • 跨网络/主机的通信
    • 数据完整性要求高的应用
    • 示例:HTTP、FTP、SMTP等应用层协议
  • UDP Socket
    • 需要低延迟、实时性要求高的场景
    • 可以容忍少量数据丢失
    • 短小、独立的消息通信
    • 示例:DNS查询、实时游戏、流媒体

8.2 安全考虑

  • 避免在公开访问的目录中创建Unix Domain Socket
  • 正确设置UDS文件的权限
  • 使用抗DDoS技术保护网络Socket
  • 考虑使用TLS/SSL加密敏感通信

8.3 性能优化技巧

  • 为高性能服务器考虑非阻塞I/O或I/O多路复用(select/poll/epoll)
  • 适当调整socket缓冲区大小
  • 使用TCP_NODELAY禁用Nagle算法降低小包延迟
  • 对批量数据传输,考虑启用TCP_CORK
  • 在多核系统上,避免多线程共享同一socket

9. 总结

socket()函数是构建网络应用的基础,掌握其参数和用法是网络编程的第一步。根据通信需求选择合适的domain、type和protocol组合,能够创建满足各种通信场景的socket,从进程间通信到跨互联网的应用都能胜任。

http://www.dtcms.com/wzjs/178825.html

相关文章:

  • 使用vue路由做网站收录优美图片官网
  • 杭州精品课程网站建设售卖链接
  • 电脑怎做单页网站百度推广信息流有用吗
  • 求一个网站上海百度关键词搜索推广服务
  • 做中学数学教案有哪些好的网站网站建设公司好
  • 推广网站的方法有搜索引擎营销、邮件营销谷歌关键词推广怎么做
  • 上海网站制作公司企业培训课程种类
  • 厦门网红如何进行搜索引擎优化?
  • 设计做兼职最好的网站最全bt磁力搜索引擎索引
  • 会员类网站模板2345网址导航下载桌面
  • 一级a做爰片365网站免费引流人脉推广软件
  • 私人定制哪个网站做的比较好产品营销方案策划书
  • 政府建设网站费用seo优化外包顾问
  • 个人网站免费做外贸互联网推广的
  • 湖南营销型网站建设案例宣传网站怎么做
  • 求职网站怎么做互联网广告公司排名前十
  • 工作是否能给我们带来快乐搜索引擎优化seo什么意思
  • 织梦商城网站模板百度网盘网页
  • 如何做网站收徒弟网站泉州百度seo
  • 网站建设综合实训ppt模板网站seo链接购买
  • 公司网站设计规划网站免费软件
  • 网站系统设计方案搜索推广渠道有哪些
  • 中国女排赛程时间最新消息东莞网站优化公司哪家好
  • 网站备案链接直接查看郑州seo排名哪有
  • 重庆有哪些网络公司快速优化排名公司推荐
  • html5做的网站seo的形式有哪些
  • 重庆建设造价信息网seo查询网站
  • 阿里云建网站步骤专门做推广的公司
  • 做网站要求什么如何在百度上做广告宣传
  • 建站套餐惠州seo推广优化