|
发表于 2021-3-11 15:47:16
|
显示全部楼层
同样碰到这个问题,在官方找到了另外一个方法,放过来供大家参考
https://www.keil.com/support/man ... _tn_tcp_mulconn.htm
The framework of the user application shall contain the following basic functions:
The user_init() function to initialize all user application sessions at startup.
void user_init () {
USER_INFO *user_s;
int i;
for (i = 0; i < user_num_sess; i++) {
user_s = &user_session;
user_s->Count = 0;
user_s->Flags = 0;
user_s->BCnt = 0;
user_s->Tout = 0;
user_s->File = NULL;
user_s->Script= NULL;
/* Allocate a TCP socket for the session. */
user_s->Socket = tcp_get_socket (TCP_TYPE_SERVER, TCP_TOS_NORMAL,
120, user_listener);
user_s->State = USER_STATE_ERROR;
if (user_s->Socket != 0) {
if (tcp_listen (user_s->Socket, USER_SERVER_PORT) == __TRUE) {
user_s->State = USER_STATE_IDLE;
}
}
}
}
All user sessions are now initialized and each session has allocated it's own TCP socket. A socket is listening on selected USER_SERVER_PORT port.
The user_listener() callback function for TCP socket. This callback function is common for all TCP sockets allocated in this user application.
static U16 user_listener (U8 socket, U8 event, U8 *ptr, U16 par) {
USER_INFO *user_s;
U8 session;
int i;
session = user_map_session (socket);
if (session == 0)) {
return (__FALSE);
}
user_s = &user_session[session-1];
switch (event) {
case TCP_EVT_CONREQ:
if (user_s->State == USER_STATE_IDLE) {
user_s->State = USER_STATE_RESERVED;
}
return (__TRUE);
case TCP_EVT_ABORT:
user_kill_session (user_s);
return (__TRUE);
case TCP_EVT_CONNECT:
user_s->State = USER_STATE_ACTIVE;
return (__TRUE);
case TCP_EVT_CLOSE:
user_kill_session (user_s);
return (__TRUE);
case TCP_EVT_ACK:
user_s->Count += user_s->BCnt;
user_s->BCnt = 0;
return (__TRUE);
case TCP_EVT_DATA:
..
return (__TRUE);
}
return (__FALSE);
}
The user_map_session() function to map the socket, which has generated a callback event, to it's owner session.
static U8 user_map_session (U8 socket) {
int i;
for (i = 1; i <= user_num_sess; i++) {
if (user_session[i-1].Socket == socket) {
return (i);
}
}
return (0);
}
The user_kill_session() function to initialize the session to a default state, close any eventually opened files and release any eventually allocated buffers.
static void user_kill_session (USER_INFO *user_s) {
user_s->State = USER_STATE_IDLE;
if (user_s->Flags & USER_FLAG_FOPENED) {
user_fclose (user_s->File);
user_s->File = NULL;
}
if (user_s->Script != NULL) {
free_mem (user_s->Script);
user_s->Script = NULL;
}
user_s->Flags = 0;
user_s->Count = 0;
user_s->BCnt = 0;
user_s->Tout = 0;
}
The user_run_server() function to maintain the application jobs, timeouts, etc. This function shall be frequently called from the main loop.
void user_run_server () {
USER_INFO *user_s;
int i;
for (i = 0; i < user_num_sess; i++) {
user_s = &user_session;
switch (user_s->State) {
case USER_STATE_IDLE:
case USER_STATE_RESERVED:
/* Keep TCP sockets listening. */
if (tcp_get_state (user_s->Socket) < TCP_STATE_LISTEN) {
tcp_listen (user_s->Socket, USER_SERVER_PORT);
}
break;
case USER_STATE_WAITING:
if (sec_tick == __TRUE) {
if (--user_s->Tout == 0) {
/* A timeout expired. */
user_kill_session (user_s);
}
}
break;
case USER_STATE_ACTIVE:
..
break;
}
}
} |
|