|
本帖最后由 sunsili 于 2021-12-17 15:00 编辑 : `( V$ Z. r/ w
% r' }" Z# o0 j
Linux TCPIP server报Socket accept: Invalid argument再次运行报端口占用
& h+ E" N- C7 B0 {8 q
( X$ }" z3 M# p5 \问题现象: server(服务端)运行在accept函数处等待client的连接,当有client来连接时,accept函数返回值为-1(错误). 报错 Socket accept: Invalid argument 问题偶尔出现 Ctrl+c 退出后,再运行报端口占用 请教大神问题何在?感谢万分。11
7 N2 ?. D4 h8 e
代码如下:
5 y! \/ y2 T, \- //多进程的方式
( z) i/ H' E8 L6 Z - //服务器端 server.c2 ?8 H( ^: T A( T3 c. D4 @# K
- #include <stdio.h>
4 v. s, [$ O0 | X2 V+ G) U - #include <unistd.h>
) K. Q! E/ t. p8 Z9 D/ ^' _ - #include <string.h>& |* B' J$ d, W/ X/ k
- #include <sys/types.h>
" @' g0 F3 L8 q' r% G' }7 S - #include <sys/socket.h>
* u( f5 r4 S K4 F- ^ - #include <arpa/inet.h>* g2 M' P- G6 X6 d- l" v2 H
- #include <netinet/in.h>
# q8 j7 w0 E6 |3 s - #include <stdlib.h>
+ j; L) |6 Z' |8 a7 S4 p3 o
' M! @' y6 E. H- #define SERVER_PORT 1234 //1024以前是系统内部占用
! B# J/ m- T& y7 v4 D" K- l - #define SERVER_IPADDR "192.168.31.76" //注意:IP地址需要和自己Ubuntu系统里面的IP地址,设置为同网段的。
/ O' f+ U4 Z( N! t1 p - #define LISTEN_Q_MAX 10 //服务器能够连接的客户端总个数。
4 C7 a0 m% e9 A/ w - //typedef 类型别名 int a char b;
! o% e# F4 q( r# u( r J - typedef struct sockaddr_in SIN;
3 ~% V& j; N3 ?9 `# b - int Socket(int domain,int type,int protocol);- a8 A7 @" J& e2 G6 n2 ?
- int Bind(int sockfd,SA* my_addr,int addrlen);) q; S% Q/ |5 _+ N
- int Listen(int s,int backlog); d1 x7 ]9 R% l3 }+ H! `3 H* w
- int Accept(int s,SA* addr,int *addrlen);
8 j8 s; P/ T% g# ?& M- C" Q# Y - //声明全局变量( M! \8 a5 D8 D9 ?! T+ {" G
- char t_buf[64];6 R4 N0 I9 N# i/ i& f/ J; M
- char r_buf[64];" Q) G% c0 b* E, j, @8 q7 }) r/ x
- char clientname[64];. \. ^( r& i) F7 @, b
- int r_len;, h* |2 B& i6 x( c1 }* Z5 Q5 M
2 m9 t' v. G4 u& x- L+ P' I+ O- int main(int argc,char* argv[])4 T' r5 v) r/ D
- {
3 A1 d& a& L8 ] - pid_t pid;) q) p8 B: `3 q" _/ y4 n, L( R
- int serfd,clifd;
0 h H& T- d1 [2 n: p4 i1 G - int addrlen;; x/ Q I& ?: ^* a' A0 L& ~
- int reuse=1; e1 \, N0 x) |
- SIN seraddr,cliaddr;
& c7 ^! Q0 ?/ E4 @& B& |, L; L7 A$ A, {3 s - u- i) F1 b- ~# Q* R3 K" y
- //1、创建一个用于TCP通信的端口
% d. \; x! [$ J; r# b* @6 U6 a! D; Z - serfd = Socket(AF_INET,SOCK_STREAM,0);
6 E- S( @7 ]0 Q- ^ -
) h0 u5 D4 K. c3 J- e - //2、编写服务器的地址信息
% _0 K9 v& y1 a$ i# G - bzero(&seraddr,sizeof(SIN)); //功能之前用的memset()
: O! Q5 A; Y+ G) s - seraddr.sin_family = AF_INET;+ e, b4 i( z6 C# x9 }8 h
- seraddr.sin_port = htons(SERVER_PORT); //配置端口号/ z5 W, _9 f$ O
- seraddr.sin_addr.s_addr=inet_addr(SERVER_IPADDR); //对IP地址传进来
. B6 C B* O2 T -
* B7 m/ c. Q8 v - setsockopt(serfd,SOL_SOCKET,SO_REUSEADDR,&reuse,sizeof(reuse)); //不是必须的
+ S2 D; U4 p: V& r2 C Y; b' w/ J -
. W$ a* U$ M2 ^$ c: ^5 L8 E - //3、端口和服务器进行绑定
0 n. P* x* Z' l( F5 T( N* I9 E - Bind(serfd,(SA*)&seraddr,sizeof(SA));0 W- m$ m* U: h3 [- Q
-
0 o4 }8 F' j! _6 \ - //4、创建监听队列" j, u" y' s0 }; o; c( J( _ n
- Listen(serfd,LISTEN_Q_MAX);
. } A& o2 _" P6 x& m( P) I- G - 6 B9 P5 V: A) C! C, H# o
- //5、等待客户端连接,获取客户端信息7 @4 x! B9 {& T8 T2 R% e* D
- while(1), Q+ @) g4 c: K" s
- {+ H) t) Z2 S1 Q
- clifd = Accept(serfd,(SA*)&cliaddr,&addrlen);6 \- k0 m' L3 {7 _
- //等待被连接
' [" l# C0 v% e - //clifd=accept(serfd,(SA*)&cliaddr,&addrlen);4 q9 @& H* s+ L& ~& V5 } C/ G
- if(clifd == -1)
$ l: n) b: X* H- F7 @ - {( A; S' D. `8 ~; D( ?& D
- perror("accept failed\r\n");
4 B/ F; ~ o" P- \0 I - exit(0);) x1 a% r2 h. @8 {# C8 B
- }1 r; U: `$ x# s" F, z
- . |( r% V; o. }7 t K
-
3 A2 X9 O) }! b3 k$ M' B+ n - % ^0 n$ Y/ j( }1 G# K) L* b
- printf("Connect already.client%d\r\n",clifd);
\( V4 ]# |$ Y, H4 z -
; h; E+ ~" {& N0 L% E1 h1 @0 _ - pid = fork();5 P6 n3 Y7 ^. n, v- r- o
- if(pid == 0)( m6 X9 x/ P! s+ G: H9 J) N( x0 J; H
- {
+ j' E/ c( N7 U" }! j4 J, O$ F, j& { - //子进程. x1 A x' X4 Y+ b
- read(clifd,clientname,sizeof(clientname));
% s' F$ D5 `7 x2 J+ ~* m! @ - while(1)3 N+ f5 p+ N9 H& o3 h, m
- {
# S- O0 W# B/ G( s0 r' m0 M; X - //子进程 --处理当前客户端的事务
1 O. H" b( a; n; Q* Q$ Z - r_len = read(clifd,r_buf,sizeof(r_buf));! Y& L6 `. K; J1 Q1 P/ V
- if(r_len == 0)% r1 O% z6 a2 ^/ W0 o: f
- {
) {3 W% q3 q5 z4 L. |/ ` - close(clifd);
5 w" Y. Z" x* l4 v" I - printf("client %s offline\r\n",clientname);
. f9 W; Y3 q5 w5 T2 S - exit(0);( C/ O. J8 x0 Q% R s
- }
' `3 v# V3 H; c# s4 M - printf("recv from client %s:%sr\n",clientname,r_buf);
3 Y1 C9 E# w$ p3 i8 S6 J - ! N; R) V0 a$ I& [9 r
- }
0 ^2 Q) g# {2 Q. m# ~ - }
$ z. v6 ?9 V7 Z' F' x( p7 j" o3 o - close(clifd);4 ?/ v- P0 R3 v6 x5 q! \
- close(serfd);
! ?% y' _' R( A- b3 n; } - }
4 a' m) `# q4 w5 ^! E/ @
s" l$ P) G, H( X8 @6 K& ?, U$ V6 B- int Socket(int domain,int type,int protocol)
6 q+ s7 W2 w. N' A. o3 n - {
( r. ~, c6 q, k' r8 w7 _ - int serfd; //局部变量. Y1 h2 u8 W' P1 {4 j
- serfd = socket(domain,type,protocol); //核心
9 Z9 ~+ V0 A, ^% _+ T* M2 s2 g8 U$ e& M - if(serfd == -1)* o" N% Q: B: B# y" c
- {
; V* \2 c/ A8 n3 _; {! {1 G! N - perror("socket failed\r\n");
: u2 Q* `, {3 o2 r/ h+ t/ \: { - exit(-1);
3 O9 u) b4 m2 e X' W; ?, f* O - }* z. ~. k2 d* J0 M5 S
- 1 S9 X# |$ y" |
- return serfd;; q2 A: r8 f- ?: T! L/ ^
- }
1 w2 r0 h9 i% |; i# z
- L8 H0 t) L2 U' S i9 }1 {# x- 1 n1 Z+ X9 g$ a h6 I6 W! }
- int Bind(int sockfd,SA* my_addr,int addrlen)& S5 ]3 @" g4 i' N
- {0 o) X! Q3 L R# e8 ^; F0 r
- int ret;2 ^# |4 H5 L6 q; s4 b) Q
- ret = bind(sockfd,my_addr,addrlen);
6 g& E4 u" _% x - if(ret == -1)
$ U6 C$ y$ r$ T. s2 V - {
$ _; x+ A$ p$ }) L - perror("bind failed\r\n");: [5 V i& i5 u; G2 z" O
- exit(-1);+ R. O1 ]8 \, j4 ?$ c5 H
- }
0 @- Q" n" S2 X# S - return 0;. E# b- ^0 y4 S# ^# P3 I" m) p
- }7 Y! |& U: i6 b! U' U
- - Y3 R W$ Q. W7 A* d
- //监听函数0 E. J$ C9 i8 o4 L! X+ x) L2 o
- int Listen(int s,int backlog)# N, K9 P' r: O
- {
: }8 s9 f9 I- o$ J8 N - int ret;
. ~7 k- V7 _+ R) N U6 T% [7 q# O - ret = listen(s,backlog);& Y7 b- f. \3 G1 ^9 z4 V- k
- if(ret == -1)1 v* A( E; Z( Z3 N M1 j
- {
* w0 q( b& o3 H. B2 v* Y! b8 z* E1 V - perror("listen failed\r\n");
, ?" x. L2 w2 ]" A - exit(-1);( `8 M# I: j8 N! X; z& [+ E
- }
. m5 h& u3 X7 K- H& y! C1 ?+ F - return 0;
; |1 X8 R# D9 |) E7 d - }. }( J' M3 f9 {. D s$ o
- . i0 V4 ^0 p3 ]6 q T8 {
- //等待接收客户端函数, K! j$ N; d2 h% {- [
- int Accept(int s,SA* addr,int *addrlen)
+ m' A* T/ ^1 v' v/ @# b - {& L6 R; Z1 e$ A4 |
- int ret;5 I; F6 p2 \5 w
- ret = accept(s,addr,addrlen);
' P( P! Y! N* f( Z& J- i# T - if(ret == -1)
" }1 n& S- ~4 ^7 o, v T - {9 |4 \3 ~3 X U/ Y, e# p# v0 ^
- perror("accept failed\r\n");, `/ ?( u4 W8 |
- exit(-1);+ K1 l) ^9 j& {6 |6 T. u6 Z# @' f
- }( E h# D* A0 }( s# b! J/ i- j, E
- return ret;* g6 {: U8 y; H+ W0 j/ D
- }</p>
复制代码 ! s5 W7 c& F+ ]% ]( p, [
3 V& {8 |8 f, `
& m3 p4 R- x& W: Z
: b- Z1 A) }2 K) C. |" E7 O |
|