訊號驅動IO的UDP回射伺服器

2021-08-04 23:56:51 字數 2835 閱讀 6189

1)、建立sigio的訊號處理函式。

2)、設定套接字的屬主, 通常使用fcntl的f_setown命令設定。

3)、開啟套接字的訊號驅動io, 通常使用fcntl的f_setfl命令開啟o_async標誌完成。

1)、資料報到達套接字。

2)、套接字上發生了非同步錯誤(udp已經連線)。

1)、監聽套接上的某個請求已經完成。

2)、某個斷開請求發起。

3)、某個斷開請求完成。

4)、資料到達套接字。

5)、資料已經衝套接字發走(即輸出緩衝區有空閒)

6)、發生某個非同步錯誤

結合上圖可視,當資料報到達資料緩衝區的時候, 觸發sigio訊號, 那麼系統進入訊號處理函式, 把資料報從緩衝區讀入到應用層緩衝區當中, 再由伺服器應用程式處理。

偽**如下:

void do_echo(int sockfd_arg, struct sockaddr *cliaddr, socklen_t clilen) 

}void sig_io(int signo)

}

伺服器核心程式源**如下:

dg_echo.c

#include "unp.h"

static int sockfd;

#define qsize 8 /*size of input queue*/

#define maxdg 4096 /*max datagram size*/

typedef struct

}dg;

static dg dg[qsize]; //queue of datagram to process.

static long cntread[qsize + 1]; // diagnostic counter

static int iget; // next one for main loop to process

static int iput; // next one for signal handler to read into

static nqueue; //on queue for main loop to process

static socklen_t clilen; //maxlen length of sockaddr{}

static void sig_io(int);

static void sig_hup(int);

void dg_echo(int sockfd_arg, struct sockaddr* pcliaddr, socklen_t clilen_arg)

for(i = 0; i<= qsize; ++i)

cntread[i] = 0;

iget = iput = nqueue = 0;

signal(sighup, sig_hup);

signal(sigio, sig_io);

fcntl(sockfd, f_setown, getpid());// 設定套接字屬主

ioctl(sockfd, fioasync, &on); //套接字設定成訊號驅動io

ioctl(sockfd, fionbio, &on);

sigemptyset(&zeromask); // init three signal sets

sigemptyset(&newmask);

sigemptyset(&oldmask);

sigaddset(&newmask, sigio); //signal we want to block

sigprocmask(sig_block, &newmask, &oldmask);//堵塞訊號

for(;;)

}static void sig_io(int signo)

ptr = &dg[iput];

ptr->dg_salen = clilen;

len = recvfrom(sockfd, ptr->dg_data, maxdg, 0, ptr->dg_sa, &(ptr->dg_salen));

if(len < 0)

}ptr->dg_len = len;

nread++;

nqueue++;

if(++iput >= qsize)

iput = 0;

}cntread[nread]++;

}static void sig_hup(int signo)

printf("sum = %d\n", sum);

exit(0);

}

注意事項:

1、sigsuspend函式, 將訊號遮蔽字掩碼設定為引數的掩碼, 若為空, 表示不堵塞任何訊號, 睡眠並且等待系統遞交訊號, 在進入訊號處理函式的時候, 該訊號遮蔽字恢復函式呼叫之前, 訊號處理函式執行完畢後, 該函式才返回。

2、nqueue表示應用程式緩衝區, 已經存入的資料報數量

客服端程式, 想伺服器傳送20000個大小為1400b的資料報, 因為可能考慮到伺服器的執行速度那麼客戶端每次傳送乙個資料報後休息1us,

1、熟記udp的訊號驅動模型

2、了解sigio訊號產生的原因

3、了解sigsuspend函式原理

4、判斷其中的競爭條件。

5、了解f_setown  o_async   fioasync的應用

6、sigprocmask函式了解,熟記sig_block   sig_setmask   sig_unblock(

慎用)

TCP 回射伺服器

tcp reflect server client tcp回射伺服器。學習了 unp 的第五章前面的知識,自己把 敲出來了,加深了理解吧。簡單地說就是,client傳送給server一條訊息 一行文字 server再將同樣地訊息傳送回client。就像這樣 用到的函式和api包括 1 socket ...

Linux C 回射伺服器

回射伺服器就是服務端將客戶端的資料傳送回去。我實現的回射伺服器返回增加了時間。服務端 可以很容易看懂 cpp view plain copy include include include include include include include include include define ...

TCP 回射伺服器

本例為多程序的 tcp 回射程式 服務端 include intmain int argc,char ar close connfd 父程序斷開連線 void str echo int sockfd 套接字 sockaddr in cliaddr,servaddr 網際套接字位址結構,包含協議族 i...