class="markdown_views prism-atelier-sulphurpool-light">
《UDP网络编程模型示例》
1、模型函数化
- 【服务器】:
- 创建socket
- 绑定地址
- 收发数据
- 结束连接
- 【客户端】:
- 创建socket
- 收发数据
- 结束连接
2、示例代码
/****************************************************************************************
* 文件名: service.c
* 创建者:
* 时 间:
* 联 系:
* 简 介: UDP程序设计模型,函数API参考文档《Unix环境高级编程》
*****************************************************************************************/
/***********************************************************
函数学习及流程:
1、创建socket:
2、绑定地址:
3、接收数据:ssize_t recvfrom(int socket,
void *restrict buffer,
size_t length,
int flags,
struct sockaddr *restrict address,
socklen_t *restrict address_len);
参数一:指明哪个socket
参数二:用于存放收到的数据
参数三:接收多少字节
参数四:标志,一般为0
参数五:接收数据的目标地址
参数六:接收数据的目标地址的长度
返回值:成功返回接收到的字节书,失败-1
4、发送数据:ssize_t sendto(int socket,
const void *message,
size_t length,
int flags,
const struct sockaddr *dest_addr,
socklen_t dest_len);
参数一:指明是哪个socket
参数二:要发送的数据
参数三:要发送的数据长度
参数四:标志,一般为0
参数五:目标地址
参数六:目标地址长度
返回值:成功返回发送成功的字节数,失败-1
5、关闭套接字
本例程只详细介绍了发送和接收函数,其他函数详细信息见另一篇tcp编程的博客:http://blog.csdn.net/qq153471503/article/details/79329089
【综合实例】:
服务器一直接收数据并打印,直到收到end结束接收,然后发送向客户端发送通知数据。
客户端一直获取键盘输入并发送数据,并显示发送结果,键入end结束发送,并接收服务器的通知数据并打印。
************************************************************/
int main()
{
int fd;
char buf[64];
socklen_t addr_length = sizeof(struct sockaddr_in);
struct sockaddr_in server_addr;
struct sockaddr_in client_addr;
// 1、创建socket
fd = socket(AF_INET, SOCK_DGRAM, 0);
if(fd == -1)
{
DEBUG_ERROR("service creat socket failed.
");
exit(EXIT_FAILURE);
}
// 2、绑定地址
bzero(&server_addr, sizeof(struct sockaddr_in));
server_addr.sin_addr.s_addr = htonl(INADDR_ANY);
server_addr.sin_port = htons(8080);
server_addr.sin_family = AF_INET;
bind(fd, &server_addr, sizeof(server_addr));
// 3、接收数据
bzero(&client_addr, sizeof(client_addr));
client_addr.sin_addr.s_addr = inet_addr("192.168.0.252");
client_addr.sin_port = htons(8080);
client_addr.sin_family = AF_INET;
while(1)
{
if( recvfrom(fd, buf, sizeof(buf), 0, &client_addr, &addr_length) > 0)
{
if(strncmp(buf, "end", 3) == 0)
{
break;
}
DEBUG_INFO("receive data from [%s] : %s
", inet_ntoa(client_addr.sin_addr), buf);
}
}
bzero(buf, sizeof(buf));
strcpy(buf, "server stop.
");
if( sendto(fd, buf, strlen(buf), 0, &client_addr, sizeof(client_addr)) <= 0 )
{
DEBUG_WARNING("server send to client failed.
");
}else{
DEBUG_INFO("server send result successful.
");
}
// 5、关闭
close(fd);
return 0;
}
#include "mytype.h"
int main()
{
int fd;
char buf[64];
socklen_t addr_length = sizeof(struct sockaddr_in);
struct sockaddr_in server_addr;
struct sockaddr_in client_addr;
fd = socket(AF_INET, SOCK_DGRAM, 0);
if(fd == -1)
{
DEBUG_ERROR("service creat socket failed.
");
exit(EXIT_FAILURE);
}
bzero(&server_addr, sizeof(struct sockaddr_in));
server_addr.sin_addr.s_addr = inet_addr("192.168.0.252");
server_addr.sin_port = htons(8080);
server_addr.sin_family = AF_INET;
while(1)
{
DEBUG_PRINTF("Please input : ");
fgets(buf, sizeof(buf), stdin);
if( sendto(fd, buf, strlen(buf), 0, &server_addr, sizeof(server_addr)) > 0 )
{
DEBUG_INFO("client send successful.
");
}
if(strncmp(buf, "end", 3) == 0 )
{
break;
}
}
bzero(&server_addr, sizeof(struct sockaddr_in));
server_addr.sin_addr.s_addr = htonl(INADDR_ANY);
server_addr.sin_port = htons(8080);
server_addr.sin_family = AF_INET;
if(recvfrom(fd, buf, sizeof(buf), 0, &server_addr, &addr_length) > 0)
{
DEBUG_INFO("receive server data is : %s
", buf);
}
close(fd);
return 0;
}
3、运行结果
- 【Makefile】
- 【运行结果】
4、mytype.h
#ifndef _MYTYPE_H_
#define _MYTYPE_H_
#define USE_TIME 0
#define USE_SIGNAL 0
#define USE_SHARE_MEMORY 0
#define USE_SEMAPHORE_NAME 0
#define USE_SEMAPHORE_UNNAMED 0
#define USE_MSG_QUEUE 0
#define USE_FILE_CTL 0
#define USE_THREAD 0
#define USE_SOCKET 1
#include
#include
#include
#include
#include
#if USE_SIGNAL
#include
#endif // USE_SIGNAL
#if USE_SEMAPHORE
#include
#include
#endif // USE_SEMAPHORE
#if USE_SEMAPHORE_UNNAMED
#include
#endif // USE_SEMAPHORE_UNNAMED
#if USE_SHARE_MEMORY
#include
#endif // USE_SHARE_MEMORY
#if USE_MSG_QUEUE
#if !USE_SEMAPHORE
#include
#endif
#include
#endif // USE_MSG_QUEUE
#include
#include
#include
#if USE_FILE_CTL
#include
#endif // USE_FILE_CTL
#if USE_TIME
#include
#endif // USE_TIME
#if USE_THREAD
#include
#endif // USE_THREAD
#if USE_SOCKET
#include
#include
#include
#endif // USE_SEMAPHORE_NAME
#ifndef bool
typedef unsigned int bool;
#endif
enum
{
true = 1,
false = !true
};
typedef unsigned int uint;
typedef unsigned char uchar;
typedef unsigned short ushort;
#define DEBUG_INFO(...) printf("Info: "); printf(__VA_ARGS__)
#define DEBUG_ERROR(...) printf("Error: "); printf(__VA_ARGS__)
#define DEBUG_WARNING(...) printf("Warning: "); printf(__VA_ARGS__)
#define DEBUG_PRINTF(...) printf(__VA_ARGS__)
#if USE_SEMAPHORE
typedef struct sem_use SEM_USE;
struct sem_use
{
int semid;
key_t key;
struct sembuf sops;
};
#endif // USE_SEMAPHORE
#if USE_SHARE_MEMORY
typedef struct shmem_use SHMEM_USE;
struct shmem_use
{
int shmid;
key_t key;
};
#define BUF_SIZE 1024*1 //共享内存大小
typedef struct shmem_area SHMEM_AREA;
struct shmem_area
{
bool isnull;
char data[BUF_SIZE];
};
#endif // USE_SHARE_MEMORY
#if USE_MSG_QUEUE
typedef struct msg_queue_use MSG_QUEUE_USE;
struct msg_queue_use{
key_t key;
int msgid;
};
#endif // USE_MSG_QUEUE
#if USE_SOCKET
typedef struct use_tcp_client{
int fd;
struct sockaddr_in server_addr;
socklen_t addr_length;
}USE_TCP_CLIENT;
typedef struct use_tcp_service{
int fd;
int newfd;
struct sockaddr_in server_addr;
struct sockaddr_in client_addr;
socklen_t addr_length;
}USE_TCP_SERVICE;
#endif // USE_SOCKET
#endif // _TYPE_H_
ends