From d5bd4e9c37e903e2e5f1174185522968ddfede0b Mon Sep 17 00:00:00 2001 From: John Safranek Date: Tue, 9 Apr 2024 10:15:34 -0700 Subject: [PATCH] Refactoring Channels 1. Allow some of the shell code in the echoserver for handling echo. 2. Add check for echo to the shell start cb to skip forking a child process to handle the shell. 3. Always all the echo test in the testsuite. 4. Check a return value on execv of the shell in the echoserver. 5. Whitespace. --- examples/echoserver/echoserver.c | 63 +++++++++++++++++--------------- tests/testsuite.c | 5 --- 2 files changed, 33 insertions(+), 35 deletions(-) diff --git a/examples/echoserver/echoserver.c b/examples/echoserver/echoserver.c index bcb51d3c3..6dbfe9ef9 100644 --- a/examples/echoserver/echoserver.c +++ b/examples/echoserver/echoserver.c @@ -176,13 +176,11 @@ typedef struct WS_FwdCbActionCtx { #endif -#ifdef WOLFSSH_SHELL typedef struct WS_ShellCtx { int isConnected; WS_SOCKET_T childFd; word32 channelId; } WS_ShellCtx; -#endif typedef struct { @@ -202,10 +200,8 @@ typedef struct { WS_FwdCbActionCtx fwdCbCtx; byte fwdBuffer[EXAMPLE_BUFFER_SZ]; #endif -#ifdef WOLFSSH_SHELL WS_ShellCtx shellCtx; byte shellBuffer[EXAMPLE_BUFFER_SZ]; -#endif #ifdef WOLFSSH_SFTP int doSftp; #endif @@ -217,8 +213,6 @@ typedef struct { } thread_ctx_t; -#ifdef WOLFSSH_SHELL - static byte find_char(const byte* str, const byte* buf, word32 bufSz) { const byte* cur; @@ -281,8 +275,6 @@ static int process_bytes(thread_ctx_t* threadCtx, return stop; } -#endif /* WOLFSSH_SHELL */ - #if defined(WOLFSSL_PTHREADS) && defined(WOLFSSL_TEST_GLOBAL_REQ) @@ -640,23 +632,33 @@ static int termios_show(int fd) } return 0; } -#endif +#endif /* SHELL_DEBUG */ +#endif /* WOLFSSH_SHELL */ static int wsShellStartCb(WOLFSSH_CHANNEL* channel, void* ctx) { if (ctx != NULL) { thread_ctx_t* threadCtx; +#ifdef WOLFSSH_SHELL WOLFSSH* ssh; const char *userName; struct passwd *p_passwd; struct termios tios; pid_t childPid; int rc; +#endif /* WOLFSSH_SHELL */ threadCtx = (thread_ctx_t*)ctx; - ssh = threadCtx->ssh; threadCtx->shellCtx.isConnected = 1; + if (threadCtx->echo) { + /* Running as the echoserver. Don't check the user with + * the system. One of the canned users is OK here. */ + return 0; + } + +#ifdef WOLFSSH_SHELL + ssh = threadCtx->ssh; wolfSSH_ChannelGetId(channel, &threadCtx->shellCtx.channelId, WS_CHANNEL_ID_PEER); userName = wolfSSH_GetUsername(ssh); @@ -695,6 +697,10 @@ static int wsShellStartCb(WOLFSSH_CHANNEL* channel, void* ctx) } rc = execv("/bin/sh", (char **)args); + if (rc < 0) { + printf("execv failed: rc =%d,errno=%x\n", rc, errno); + return WS_FATAL_ERROR; + } } #ifdef SHELL_DEBUG printf("In childPid > 0; getpid=%d\n", (int)getpid()); @@ -732,11 +738,13 @@ static int wsShellStartCb(WOLFSSH_CHANNEL* channel, void* ctx) #endif /* HAVE_SYS_IOCTL_H */ wolfSSH_SetTerminalResizeCtx(ssh, (void*)&threadCtx->shellCtx.childFd); +#else /* WOLFSSH_SHELL */ + (void)channel; +#endif /* WOLFSSH_SHELL */ } return 0; } -#endif /* WOLFSSH_SHELL */ #ifdef WOLFSSH_SCP @@ -952,23 +960,18 @@ static int ssh_worker(thread_ctx_t* threadCtx) while (ChildRunning) { fd_set readFds, exFds; WS_SOCKET_T maxFd; - int cnt_r; -#if defined(WOLFSSH_SHELL) || defined(WOLFSSH_AGENT) || defined(WOLFSSH_FWD) - int cnt_w; -#endif + int cnt_r, cnt_w = 0; FD_ZERO(&readFds); FD_ZERO(&exFds); FD_SET(sshFd, &readFds); maxFd = sshFd; - #ifdef WOLFSSH_SHELL if (threadCtx->shellCtx.isConnected) { FD_SET(threadCtx->shellCtx.childFd, &readFds); if (threadCtx->shellCtx.childFd > maxFd) maxFd = threadCtx->shellCtx.childFd; } - #endif /* WOLFSSH_SHELL */ #ifdef WOLFSSH_AGENT if (threadCtx->agentCbCtx.state == AGENT_STATE_LISTEN) { FD_SET(agentListenFd, &readFds); @@ -1028,7 +1031,6 @@ static int ssh_worker(thread_ctx_t* threadCtx) if (cnt_r < 0) { rc = wolfSSH_get_error(ssh); if (rc == WS_CHAN_RXD) { - #ifdef WOLFSSH_SHELL if (threadCtx->shellCtx.isConnected && lastChannel == threadCtx->shellCtx.channelId) { cnt_r = wolfSSH_ChannelIdRead(ssh, @@ -1040,11 +1042,7 @@ static int ssh_worker(thread_ctx_t* threadCtx) #ifdef SHELL_DEBUG buf_dump(threadCtx->channelBuffer, cnt_r); #endif - if (!threadCtx->echo) { - cnt_w = (int)write(threadCtx->shellCtx.childFd, - threadCtx->channelBuffer, cnt_r); - } - else { + if (threadCtx->echo) { cnt_w = wolfSSH_ChannelIdSend(ssh, threadCtx->shellCtx.channelId, threadCtx->channelBuffer, cnt_r); @@ -1055,10 +1053,15 @@ static int ssh_worker(thread_ctx_t* threadCtx) ChildRunning = !doStop; } } + #ifdef WOLFSSH_SHELL + else { + cnt_w = (int)write(threadCtx->shellCtx.childFd, + threadCtx->channelBuffer, cnt_r); + } + #endif /* WOLFSSH_SHELL */ if (cnt_w <= 0) break; } - #endif /* WOLFSSH_SHELL */ #ifdef WOLFSSH_AGENT if (lastChannel == agentChannelId) { cnt_r = wolfSSH_ChannelIdRead(ssh, agentChannelId, @@ -1144,7 +1147,7 @@ static int ssh_worker(thread_ctx_t* threadCtx) } } #ifdef WOLFSSH_SHELL - if (threadCtx->shellCtx.isConnected) { + if (threadCtx->shellCtx.isConnected && !threadCtx->echo) { if (FD_ISSET(threadCtx->shellCtx.childFd, &readFds)) { cnt_r = (int)read(threadCtx->shellCtx.childFd, threadCtx->shellBuffer, @@ -2493,6 +2496,10 @@ THREAD_RETURN WOLFSSH_THREAD echoserver_test(void* args) char** argv = serverArgs->argv; serverArgs->return_code = EXIT_SUCCESS; +#ifndef WOLFSSH_SHELL + echo = 1; +#endif + if (argc > 0) { const char* optlist = "?1a:d:efEp:R:Ni:j:I:J:K:P:k:b:"; myoptind = 0; @@ -2525,9 +2532,7 @@ THREAD_RETURN WOLFSSH_THREAD echoserver_test(void* args) break; case 'f': - #ifdef WOLFSSH_SHELL - echo = 1; - #endif + echo = 1; break; case 'p': @@ -2647,9 +2652,7 @@ THREAD_RETURN WOLFSSH_THREAD echoserver_test(void* args) wolfSSH_SetUserAuth(ctx, ((func_args*)args)->user_auth); wolfSSH_SetUserAuthResult(ctx, wsUserAuthResult); wolfSSH_CTX_SetBanner(ctx, echoserverBanner); -#ifdef WOLFSSH_SHELL wolfSSH_CTX_SetChannelReqShellCb(ctx, wsShellStartCb); -#endif #ifdef WOLFSSH_AGENT wolfSSH_CTX_set_agent_cb(ctx, wolfSSH_AGENT_DefaultActions, NULL); #endif diff --git a/tests/testsuite.c b/tests/testsuite.c index 845f67dfe..2af53c1e7 100644 --- a/tests/testsuite.c +++ b/tests/testsuite.c @@ -69,8 +69,6 @@ char* myoptarg = NULL; #if !defined(NO_WOLFSSH_SERVER) && !defined(NO_WOLFSSH_CLIENT) && \ !defined(SINGLE_THREADED) && !defined(WOLFSSH_TEST_BLOCK) -#ifdef WOLFSSH_SHELL - static int tsClientUserAuth(byte authType, WS_UserAuthData* authData, void* ctx) { static char password[] = "upthehill"; @@ -150,7 +148,6 @@ static void wolfSSH_EchoTest(void) FreeTcpReady(&ready); } -#endif /* WOLFSSH_SHELL */ int wolfSSH_TestsuiteTest(int argc, char** argv) @@ -179,9 +176,7 @@ int wolfSSH_TestsuiteTest(int argc, char** argv) ChangeToWolfSshRoot(); #endif -#ifdef WOLFSSH_SHELL wolfSSH_EchoTest(); -#endif wolfSSH_Cleanup();