socket编程---SCTP
sctp_sndrcvinfo结构体
sctp_event_subscribe结构体
更多的关于SCTP的结构体http://aisxyz.iteye.com/blog/2408978
SCTP套接字编程相关函数
client.c
/*************************************************************************
> File Name: client.c
> Author: Chen
> Mail: 971859774@qq.com
> Created Time: 2018年11月14日 星期三 17时06分56秒
************************************************************************/ #include <stdio.h>
#include <stdlib.h>
#include <arpa/inet.h>
#include <netinet/sctp.h>
#include <sys/socket.h>
#include <sys/types.h>
#include <strings.h>
#include <string.h>
#include <ctype.h>
#include "my_err.h" #define SERV_PORT 9877
#define SCTP_MAXLINE 800
#define SERV_MAX_SCTP_STRM 10 void sctp_cli(int sockfd,struct sockaddr * to,socklen_t tolen)
{
struct sctp_sndrcvinfo sri;
bzero(&sri,sizeof(sri)); char rdbuf[MAXLINE],rvbuf[MAXLINE];
struct sockaddr_in peeraddr;
int flag;
while(fgets(rdbuf,MAXLINE,stdin)!=NULL)
{
if(rdbuf[]!='[')
{
fprintf(stderr,"Error,line must be of the form '[strnum]text'\n");
continue;
} if(isdigit(rdbuf[]))
{
sri.sinfo_stream=strtol(&rdbuf[],NULL,);
int out_sz=strlen(rdbuf);
sctp_sendmsg(sockfd,rdbuf,out_sz,to,tolen,,,sri.sinfo_stream,,);
socklen_t len=sizeof(peeraddr);
int rd_sz=sctp_recvmsg(sockfd,rvbuf,sizeof(rvbuf),(struct sockaddr *)&peeraddr,&len,&sri,&flag); printf("From str:%d seq:%d (assoc:0x%x):",sri.sinfo_stream,sri.sinfo_ssn,(u_int)sri.sinfo_assoc_id);
printf("%.*s",rd_sz,rvbuf);
}
}
return;
} //是否有头端阻塞
void sctp_cli_all(int sockfd,struct sockaddr *to,socklen_t tolen)
{
struct sctp_sndrcvinfo sri;
bzero(&sri,sizeof(sri)); char rdbuf[MAXLINE],rvbuf[MAXLINE];
bzero(&rdbuf,sizeof(rdbuf));
bzero(&rvbuf,sizeof(rvbuf)); while(fgets(rdbuf,SCTP_MAXLINE-,stdin)!=NULL)
{
int rd_sz=strlen(rdbuf);
if(rdbuf[rd_sz-]=='\n')
{
rdbuf[rd_sz-]='\0';
--rd_sz;
} int i=;
for(;i<SERV_MAX_SCTP_STRM;++i)
{
snprintf(rdbuf+rd_sz,sizeof(rdbuf)-rd_sz,".msg.%d",i);
sctp_sendmsg(sockfd,rdbuf,sizeof(rdbuf),to,tolen,,,i,,);
} struct sockaddr_in peeraddr;
int flag;
for(i=;i<SERV_MAX_SCTP_STRM;++i)
{
socklen_t len=sizeof(peeraddr);
rd_sz=sctp_recvmsg(sockfd,rvbuf,sizeof(rdbuf),(struct sockaddr *)&peeraddr,&len,&sri,&flag); printf("From str:%d seq:%d (assoc:0x%x):",sri.sinfo_stream,sri.sinfo_ssn,(u_int)sri.sinfo_assoc_id);
printf("%.*s\n",rd_sz,rvbuf);
}
}
return;
} int main(int argc,char **argv)
{
int flag=;
if(argc<)
err_quit("please input server ip");
else if(argc>)
flag=;
//sock
int sockfd=socket(AF_INET,SOCK_SEQPACKET,IPPROTO_SCTP); struct sockaddr_in servaddr;
bzero(&servaddr,sizeof(servaddr));
servaddr.sin_family=AF_INET;
servaddr.sin_port=htons(SERV_PORT);
inet_pton(AF_INET,argv[],&servaddr.sin_addr); struct sctp_event_subscribe events;
bzero(&events,sizeof(events));
events.sctp_data_io_event=;
setsockopt(sockfd,IPPROTO_SCTP,SCTP_EVENTS,&events,sizeof(events)); if(flag==)
sctp_cli(sockfd,(struct sockaddr *)&servaddr,sizeof(servaddr));
else
sctp_cli_all(sockfd,(struct sockaddr *)&servaddr,sizeof(servaddr)); /*
* ABORT类似于tcp的rst分节,无延迟的终止任何关联,尚未发送的任何数据都
* 丢弃,也没有TCP的TIME_WAIT的不良影响,
*/
/*
char beymsg[20];
strcpy(beymsg,"goodbey");
sctp_sendmsg(sockfd,beymsg,strlen(beymsg),(struct sockaddr *)&servaddr,sizeof(servaddr),0,MSG_ABORT,0,0,0);*/
close(sockfd);
return ;
}
server.c
/*************************************************************************
> File Name: client.c
> Author: Chen
> Mail: 971859774@qq.com
> Created Time: 2018年11月14日 星期三 14时56分38秒
************************************************************************/ #include <stdio.h>
#include <stdlib.h>
#include <netinet/in.h>
#include <arpa/inet.h>
#include <sys/socket.h>
#include <sys/types.h>
#include <string.h>
#include <strings.h>
#include <netinet/sctp.h>
#include "my_err.h" #define SERV_PORT 9877
#define LISTENQ 1024 sctp_assoc_t sctp_get_no_strms(int sock_fd,struct sockaddr *to,socklen_t tolen,struct sctp_sndrcvinfo sri)
{
int retsz;
struct sctp_status status;
retsz=sizeof(status);
bzero(&status,sizeof(status)); status.sstat_assoc_id=sri.sinfo_assoc_id;
getsockopt(sock_fd,IPPROTO_SCTP,SCTP_STATUS,&status,&retsz);
return status.sstat_outstrms;
} int main(int argc,char **argv)
{
//socket
int sockfd=socket(AF_INET,SOCK_SEQPACKET,IPPROTO_SCTP); struct sockaddr_in servaddr,cliaddr;
bzero(&servaddr,sizeof(servaddr));
servaddr.sin_family=AF_INET;
servaddr.sin_port=htons(SERV_PORT);
servaddr.sin_addr.s_addr=htonl(INADDR_ANY); //bind
bind(sockfd,(struct sockaddr *)&servaddr,sizeof(servaddr)); struct sctp_event_subscribe events;
bzero(&events,sizeof(events));
events.sctp_data_io_event=;//预定,每次recvmsg返回sctp_sndrcvifo
setsockopt(sockfd,IPPROTO_SCTP,SCTP_EVENTS,&events,sizeof(events)); //listen
listen(sockfd,LISTENQ); char rdbuf[MAXLINE];
struct sctp_sndrcvinfo sri;
int flag,index=;
while()
{
socklen_t len=sizeof(struct sockaddr_in);
size_t rd_sz=sctp_recvmsg(sockfd,rdbuf,sizeof(rdbuf),(struct sockaddr *)&cliaddr,&len,&sri,&flag); if(index)
{
++sri.sinfo_stream;
if(sri.sinfo_stream>=
sctp_get_no_strms(sockfd,(struct sockaddr *)&cliaddr,len,sri))//如果流号增长到大于等于最大流号,重新置为0
sri.sinfo_stream=;
}
/*
* 服务器在发送完消息后终止关联,设置MSG_EOF标志。该标志迫使发送消
* 被客户确认后,相应的关联终止
*/
sctp_sendmsg(sockfd,rdbuf,rd_sz,(struct sockaddr *)&cliaddr,len,sri.sinfo_ppid,(sri.sinfo_flags),sri.sinfo_stream,,);
}
return ; }
socket编程---SCTP的更多相关文章
- socket编程:客户端与服务器间的连接以及各函数的用法
在认真的看UNP之前,一直被socket编程说的云里雾里,今天我要让大家从整天上认识socket编程,让我们知道socket编程的整个流程和各个函数的用法.这样:我们在写一些简单的socket编程时就 ...
- 2018.12.02 Socket编程之初识Socket
Socket编程主要分为TCP/UDP/SCTP三种,每一种都有各自的优点,所以会根据实际情况决定选用何种Socket,今天开始我将会逐步学习Socket编程,并将学习过程记录于此. 今天学习的是TC ...
- socket编程:recvmsg 和 sendmsg 函数
背景 复习 socket 编程的时候发现了以前没有留意到的 2个函数:recvmsg 和 sendmsg ref : Linux编程之recvmsg和sendmsg函数 知识 先来看看函数原型: #i ...
- Linux下的C Socket编程 -- server端的继续研究
Linux下的C Socket编程(四) 延长server的生命周期 在前面的一个个例子中,server在处理完一个连接后便会立即结束掉自己,然而这种server并不科学啊,server应该是能够一直 ...
- java socket编程(li)
一.网络编程中两个主要的问题 一个是如何准确的定位网络上一台或多台主机,另一个就是找到主机后如何可靠高效的进行数据传输.在TCP/IP协议中IP层主要负责网络主机的定位,数据传输的路由,由IP地址可以 ...
- Python Socket 编程——聊天室示例程序
上一篇 我们学习了简单的 Python TCP Socket 编程,通过分别写服务端和客户端的代码了解基本的 Python Socket 编程模型.本文再通过一个例子来加强一下对 Socket 编程的 ...
- Linux下的C Socket编程 -- server端的简单示例
Linux下的C Socket编程(三) server端的简单示例 经过前面的client端的学习,我们已经知道了如何创建socket,所以接下来就是去绑定他到具体的一个端口上面去. 绑定socket ...
- Linux下的C Socket编程 -- 获取对方IP地址
Linux下的C Socket编程(二) 获取域名对应的IP地址 经过上面的讨论,如果我们想要连接到远程的服务器,我们需要知道对方的IP地址,系统函数gethostbyname便能够实现这个目的.它能 ...
- Linux下的C Socket编程 -- 简介与client端的处理
Linux下的C Socket编程(一) 介绍 Socket是进程间通信的方式之一,是进程间的通信.这里说的进程并不一定是在同一台机器上也有可能是通过网络连接的不同机器上.只要他们之间建立起了sock ...
随机推荐
- Core Java 6
p277~p279: 1.使用解耦合的 try/catch 和 try/finally 语句块可以提高代码的清晰度,并且会报告 finally 子句中出现的错误. 2.假设利用 return 语句从 ...
- Python3.x:定时获取页面数据存入数据库
Python3.x:定时获取页面数据存入数据库 #间隔五分钟采集一次数据入库 import pymysql import urllib.request from bs4 import Beautifu ...
- MAC nginx代理设置
问题: 10.154.156.83:10081私服不存在了.但是不能改.用nginx代理至maven.xx.cn 增加换回地址: sudo ifconfig lo0 add 10.154.156.83 ...
- 期末总结20135320赵瀚青LINUX内核分析与设计期末总结
赵瀚青原创作品转载请注明出处<Linux内核分析>MOOC课程http://mooc.study.163.com/course/USTC-1000029000 对LINUX内核分析与设计这 ...
- tensorflow 安装GPU版本,个人总结,步骤比较详细【转】
本文转载自:https://blog.csdn.net/gangeqian2/article/details/79358543 手把手教你windows安装tensorflow的教程参考另一篇博文ht ...
- Vim 的光标移动定位
一.光标移动以单个字符为单位: 在命令模式中 h向左 l 向右 j 向上 k 向下 二.光标移动以word 为单位: w 将光标向前移动一个word; b 将光标向后移动一个word: 以上2个命令光 ...
- 近期(17年三月至四月) TODOlist
前言 今天突然发现好久没有更新博客了,最近确实记录的内容不多,也沉迷Gayhub无法自拔,和那只北极熊愉快的玩耍.不知道为什么记性变差了许多,所以简单的列一个近期的TODOlist给自己一个提醒. T ...
- Spring Cloud组件
Spring Cloud Eureka Eureka负责服务的注册于发现,Eureka的角色和 Zookeeper差不多,都是服务的注册和发现,构成Eureka体系的包括:服务注册中心.服务提供者.服 ...
- 雷林鹏分享:Ruby 范围(Range)
Ruby 范围(Range) 范围(Range)无处不在:January 到 December. 0 到 9.等等.Ruby 支持范围,并允许我们以不同的方式使用范围: 作为序列的范围 作为条件的范围 ...
- 谈谈WPF中的CollectionView与CollectionViewSource
https://www.cnblogs.com/zhouyinhui/archive/2007/12/07/987076.html