Subj : New Defects reported by Coverity Scan for Synchronet To : cov-scan@synchro.net From : scan-admin@coverity.com Date : Wed Mar 31 2021 13:34:34 Hi, Please find the latest report on new defect(s) introduced to Synchronet found with Coverity Scan. 16 new defect(s) introduced to Synchronet found with Coverity Scan. 1 defect(s), reported by Coverity Scan earlier, were marked fixed in the recent build analyzed by Coverity Scan. New defect(s) Reported-by: Coverity Scan Showing 16 of 16 defect(s) ** CID 330056: Error handling issues (CHECKED_RETURN) /xtrn.cpp: 1716 in sbbs_t::external(const char *, long, const char *)() ________________________________________________________________________________________________________ *** CID 330056: Error handling issues (CHECKED_RETURN) /xtrn.cpp: 1716 in sbbs_t::external(const char *, long, const char *)() 1710 write(in_pipe[1],buf,wr); 1711 } 1712 1713 bp=buf; 1714 i=0; 1715 if(mode&EX_NOLOG) >>> CID 330056: Error handling issues (CHECKED_RETURN) >>> Calling "poll(fds, ((mode & 0x40000000L) ? 1 : 2), 1)" without checking return value. This library function may fail and return an error code. [Note: The source code implementation of the function has been overridden by a builtin model.] 1716 poll(fds, (mode & EX_NOLOG) ? 1 : 2, 1); 1717 else { 1718 while (poll(fds, (mode & EX_NOLOG) ? 1 : 2, 1) > 0 && (fds[1].revents & POLLIN) 1719 && (i < (int)sizeof(buf) - 1)) { 1720 if((rd=read(err_pipe[0],bp,1))>0) { 1721 i+=rd; ** CID 330055: Resource leaks (RESOURCE_LEAK) /services.c: 2131 in services_thread() ________________________________________________________________________________________________________ *** CID 330055: Resource leaks (RESOURCE_LEAK) /services.c: 2131 in services_thread() 2125 client_addr_len = sizeof(client_addr); 2126 2127 udp_len=0; 2128 2129 if(service[i].options&SERVICE_OPT_UDP) { 2130 /* UDP */ >>> CID 330055: Resource leaks (RESOURCE_LEAK) >>> Overwriting "udp_buf" in "udp_buf = (uint8_t *)calloc(1UL, 8192UL)" leaks the storage that "udp_buf" points to. 2131 if((udp_buf = (BYTE*)calloc(1, MAX_UDP_BUF_LEN)) == NULL) { 2132 lprintf(LOG_CRIT,"%04d %s !ERROR %d allocating UDP buffer" 2133 ,service[i].set->socks[j].sock, service[i].protocol, errno); 2134 continue; 2135 } 2136 ** CID 330054: Program hangs (LOCK) /sbbs_status.c: 735 in status_thread() ________________________________________________________________________________________________________ *** CID 330054: Program hangs (LOCK) /sbbs_status.c: 735 in status_thread() 729 listUnlock(&status_sock); 730 protected_uint32_destroy(thread_count); 731 protected_uint32_destroy(active_clients); 732 733 startup->thread_up(startup->cbdata, FALSE, FALSE); 734 startup->terminated(startup->cbdata, rc); >>> CID 330054: Program hangs (LOCK) >>> Returning without unlocking "status_thread_mutex". 735 } 736 737 #define makestubs(lower, UPPER) \ 738 void status_##lower##_lputs(void *cbdata, int level, const char *str) { status_lputs(SERVICE_##UPPER, level, str); } \ 739 void status_##lower##_errormsg(void *cbdata, int level, const char *str) { status_errormsg(SERVICE_##UPPER, level, str); } \ 740 void status_##lower##_status(void *cbdata, const char *str) { status_status(SERVICE_##UPPER, str); } \ ** CID 330053: Program hangs (SLEEP) ________________________________________________________________________________________________________ *** CID 330053: Program hangs (SLEEP) /sbbs_status.c: 561 in status_thread() 555 if (socket_readable(*csock, 5000)) { 556 len = recv(*csock, auth, sizeof(auth), 0); 557 if (len <= 0) { 558 closesocket(*csock); 559 free(csock); 560 pthread_mutex_lock(&status_thread_mutex); >>> CID 330053: Program hangs (SLEEP) >>> Call to "lprintf" might sleep while holding lock "status_thread_mutex". 561 lprintf(LOG_CRIT, "Error recv returned %d (%d)!", len, errno); 562 continue; 563 } 564 // TODO: Check auth... "User\0Pass\0SysPass" 565 client.user = auth; 566 user.number = matchuser(&scfg, auth, TRUE); ** CID 330052: Insecure data handling (TAINTED_SCALAR) ________________________________________________________________________________________________________ *** CID 330052: Insecure data handling (TAINTED_SCALAR) /main.cpp: 2214 in passthru_thread(void *)() 2208 if(wr != rd) { 2209 lprintf(LOG_ERR,"Short-write (%ld of %ld bytes) from passthru socket to outbuf" 2210 ,(long)wr, (long)rd); 2211 break; 2212 } 2213 } else { >>> CID 330052: Insecure data handling (TAINTED_SCALAR) >>> Passing tainted expression "inbuf" to "rputs", which uses it as an offset. 2214 sbbs->rputs(inbuf, rd); 2215 } 2216 } 2217 if(sbbs->passthru_socket!=INVALID_SOCKET) { 2218 close_socket(sbbs->passthru_socket); 2219 sbbs->passthru_socket=INVALID_SOCKET; ** CID 330051: Resource leaks (RESOURCE_LEAK) /websrvr.c: 3809 in fastcgi_connect() ________________________________________________________________________________________________________ *** CID 330051: Resource leaks (RESOURCE_LEAK) /websrvr.c: 3809 in fastcgi_connect() 3803 if(result != 0) { 3804 lprintf(LOG_ERR, "%04d ERROR resolving FastCGI address %s port %s", client_sock, path, port); 3805 free(path); 3806 return INVALID_SOCKET; 3807 } 3808 for(cur=res,result=1; result && cur; cur=cur->ai_next) { >>> CID 330051: Resource leaks (RESOURCE_LEAK) >>> Overwriting handle "sock" in "sock = socket(cur->ai_family, cur->ai_socktype, cur->ai_protocol)" leaks the handle. 3809 sock = socket(cur->ai_family, cur->ai_socktype, cur->ai_protocol); 3810 if (sock == INVALID_SOCKET) 3811 continue; 3812 val=1; 3813 ioctlsocket(sock,FIONBIO,&val); 3814 result=connect(sock, cur->ai_addr, cur->ai_addrlen); ** CID 330050: Error handling issues (CHECKED_RETURN) /ftpsrvr.c: 1108 in receive_thread() ________________________________________________________________________________________________________ *** CID 330050: Error handling issues (CHECKED_RETURN) /ftpsrvr.c: 1108 in receive_thread() 1102 system(cmd); 1103 fexistcase(tmp); /* fixes filename case */ 1104 } 1105 if((file=nopen(tmp,O_RDONLY))!=-1) { 1106 lprintf(LOG_DEBUG,"%04d <%s> DATA Parsing DIZ: %s",xfer.ctrl_sock, xfer.user->alias,tmp); 1107 memset(ext,0,sizeof(ext)); >>> CID 330050: Error handling issues (CHECKED_RETURN) >>> "read(int, void *, size_t)" returns the number of bytes read, but it is ignored. 1108 read(file,ext,sizeof(ext)-1); 1109 for(i=sizeof(ext)-1;i;i--) /* trim trailing spaces */ 1110 if(ext[i-1]>' ') 1111 break; 1112 ext[i]=0; 1113 if(!f.desc[0]) { /* use for normal description */ ** CID 330049: Insecure data handling (TAINTED_SCALAR) ________________________________________________________________________________________________________ *** CID 330049: Insecure data handling (TAINTED_SCALAR) /ftpsrvr.c: 1146 in receive_thread() 1140 if(!addfiledat(&scfg,&f)) 1141 lprintf(LOG_ERR,"%04d <%s> !DATA ERROR adding file (%s) to database" 1142 ,xfer.ctrl_sock, xfer.user->alias,f.name); 1143 } 1144 1145 if(f.misc&FM_EXTDESC) >>> CID 330049: Insecure data handling (TAINTED_SCALAR) >>> Passing tainted expression "ext" to "putextdesc", which uses it as a loop boundary. 1146 putextdesc(&scfg,f.dir,f.datoffset,ext); 1147 1148 if(scfg.dir[f.dir]->upload_sem[0]) 1149 ftouch(scfg.dir[f.dir]->upload_sem); 1150 /**************************/ 1151 /* Update Uploader's Info */ ** CID 330048: Uninitialized variables (UNINIT) /xtrn.cpp: 1692 in sbbs_t::external(const char *, long, const char *)() ________________________________________________________________________________________________________ *** CID 330048: Uninitialized variables (UNINIT) /xtrn.cpp: 1692 in sbbs_t::external(const char *, long, const char *)() 1686 1687 if(mode&EX_STDOUT) { 1688 if(!(mode&EX_STDIN)) 1689 close(out_pipe[1]); /* close write-end of pipe */ 1690 fds[0].fd = out_pipe[0]; 1691 fds[0].events = POLLIN; >>> CID 330048: Uninitialized variables (UNINIT) >>> Using uninitialized value "err_pipe[0]". 1692 fds[1].fd = err_pipe[0]; 1693 fds[1].events = POLLIN; 1694 fds[1].revents = 0; 1695 while(!terminated) { 1696 if(waitpid(pid, &i, WNOHANG)!=0) /* child exited */ 1697 break; ** CID 330047: (SLEEP) /main.cpp: 1967 in input_thread(void *)() ________________________________________________________________________________________________________ *** CID 330047: (SLEEP) /main.cpp: 1983 in input_thread(void *)() 1977 rd=sizeof(inbuf); 1978 1979 #ifdef USE_CRYPTLIB 1980 if(sbbs->ssh_mode && sock==sbbs->client_socket) { 1981 int err; 1982 pthread_mutex_lock(&sbbs->ssh_mutex); >>> CID 330047: (SLEEP) >>> Call to "crypt_pop_channel_data" might sleep while holding lock "sbbs->input_thread_mutex". 1983 if(cryptStatusError((err=crypt_pop_channel_data(sbbs, (char*)inbuf, rd, &i)))) { 1984 pthread_mutex_unlock(&sbbs->ssh_mutex); 1985 if(pthread_mutex_unlock(&sbbs->input_thread_mutex)!=0) 1986 sbbs->errormsg(WHERE,ERR_UNLOCK,"input_thread_mutex",0); 1987 if(err==CRYPT_ERROR_TIMEOUT) 1988 continue; /main.cpp: 1967 in input_thread(void *)() 1961 1962 if(rd==0) { // input buffer full 1963 lprintf(LOG_WARNING,"Node %d !WARNING input buffer full", sbbs->cfg.node_num); 1964 // wait up to 5 seconds to empty (1 byte min) 1965 time_t start=time(NULL); 1966 while((rd=RingBufFree(&sbbs->inbuf))==0 && time(NULL)-start<5) { >>> CID 330047: (SLEEP) >>> Call to "nanosleep" might sleep while holding lock "sbbs->input_thread_mutex". 1967 YIELD(); 1968 } 1969 if(rd==0) { /* input buffer still full */ 1970 if(pthread_mutex_unlock(&sbbs->input_thread_mutex)!=0) 1971 sbbs->errormsg(WHERE,ERR_UNLOCK,"input_thread_mutex",0); 1972 continue; /main.cpp: 1983 in input_thread(void *)() 1977 rd=sizeof(inbuf); 1978 1979 #ifdef USE_CRYPTLIB 1980 if(sbbs->ssh_mode && sock==sbbs->client_socket) { 1981 int err; 1982 pthread_mutex_lock(&sbbs->ssh_mutex); >>> CID 330047: (SLEEP) >>> Call to "crypt_pop_channel_data" might sleep while holding lock "sbbs->ssh_mutex". 1983 if(cryptStatusError((err=crypt_pop_channel_data(sbbs, (char*)inbuf, rd, &i)))) { 1984 pthread_mutex_unlock(&sbbs->ssh_mutex); 1985 if(pthread_mutex_unlock(&sbbs->input_thread_mutex)!=0) 1986 sbbs->errormsg(WHERE,ERR_UNLOCK,"input_thread_mutex",0); 1987 if(err==CRYPT_ERROR_TIMEOUT) 1988 continue; ** CID 330046: Resource leaks (RESOURCE_LEAK) /services.c: 2009 in services_thread() ________________________________________________________________________________________________________ *** CID 330046: Resource leaks (RESOURCE_LEAK) /services.c: 2009 in services_thread() 2003 2004 #ifndef _WIN32 2005 nfds = setup_poll(&fds); 2006 if (nfds == 0) { 2007 lprintf(LOG_CRIT, "!ERROR setting up poll() data"); 2008 cleanup(1); >>> CID 330046: Resource leaks (RESOURCE_LEAK) >>> Variable "fds" going out of scope leaks the storage it points to. 2009 return; 2010 } 2011 #endif 2012 /* Main Server Loop */ 2013 while(!terminated) { 2014 YIELD(); ** CID 330045: Memory - illegal accesses (STRING_NULL) ________________________________________________________________________________________________________ *** CID 330045: Memory - illegal accesses (STRING_NULL) /sbbs_status.c: 566 in status_thread() 560 pthread_mutex_lock(&status_thread_mutex); 561 lprintf(LOG_CRIT, "Error recv returned %d (%d)!", len, errno); 562 continue; 563 } 564 // TODO: Check auth... "User\0Pass\0SysPass" 565 client.user = auth; >>> CID 330045: Memory - illegal accesses (STRING_NULL) >>> Passing unterminated string "auth" to "matchuser", which expects a null-terminated string. 566 user.number = matchuser(&scfg, auth, TRUE); 567 if (user.number == 0) { 568 closesocket(*csock); 569 free(csock); 570 lprintf(LOG_WARNING, "Invalid username \"%s\"", auth); 571 pthread_mutex_lock(&status_thread_mutex); ** CID 330044: (CONSTANT_EXPRESSION_RESULT) /main.cpp: 1942 in input_thread(void *)() /main.cpp: 1940 in input_thread(void *)() ________________________________________________________________________________________________________ *** CID 330044: (CONSTANT_EXPRESSION_RESULT) /main.cpp: 1942 in input_thread(void *)() 1936 1937 #ifdef _WIN32 1938 sock=sbbs->client_socket; 1939 #else 1940 if (fds[0].revents | POLLIN) 1941 sock = sbbs->client_socket; >>> CID 330044: (CONSTANT_EXPRESSION_RESULT) >>> "fds[1].revents | 1" is always 1/true regardless of the values of its operand. This occurs as the logical second operand of "&&". 1942 else if(uspy_socket[sbbs->cfg.node_num - 1] != INVALID_SOCKET && fds[1].revents | POLLIN) { 1943 if(socket_recvdone(uspy_socket[sbbs->cfg.node_num-1], 0)) { 1944 close_socket(uspy_socket[sbbs->cfg.node_num-1]); 1945 lprintf(LOG_NOTICE,"Closing local spy socket: %d",uspy_socket[sbbs->cfg.node_num-1]); 1946 uspy_socket[sbbs->cfg.node_num-1]=INVALID_SOCKET; 1947 if(pthread_mutex_unlock(&sbbs->input_thread_mutex)!=0) /main.cpp: 1940 in input_thread(void *)() 1934 * ------------ 1935 */ 1936 1937 #ifdef _WIN32 1938 sock=sbbs->client_socket; 1939 #else >>> CID 330044: (CONSTANT_EXPRESSION_RESULT) >>> "fds[0].revents | 1" is always 1/true regardless of the values of its operand. This occurs as the logical operand of "if". 1940 if (fds[0].revents | POLLIN) 1941 sock = sbbs->client_socket; 1942 else if(uspy_socket[sbbs->cfg.node_num - 1] != INVALID_SOCKET && fds[1].revents | POLLIN) { 1943 if(socket_recvdone(uspy_socket[sbbs->cfg.node_num-1], 0)) { 1944 close_socket(uspy_socket[sbbs->cfg.node_num-1]); 1945 lprintf(LOG_NOTICE,"Closing local spy socket: %d",uspy_socket[sbbs->cfg.node_num-1]); ** CID 330043: Error handling issues (CHECKED_RETURN) /websrvr.c: 3066 in get_request_headers() ________________________________________________________________________________________________________ *** CID 330043: Error handling issues (CHECKED_RETURN) /websrvr.c: 3066 in get_request_headers() 3060 i=strlen(head_line); 3061 if(i>sizeof(head_line)-1) { 3062 lprintf(LOG_ERR,"%04d !ERROR long multi-line header. The web server is broken!", session->socket); 3063 i=sizeof(head_line)/2; 3064 break; 3065 } >>> CID 330043: Error handling issues (CHECKED_RETURN) >>> Calling "sockreadline" without checking return value (as is done elsewhere 4 out of 5 times). 3066 sockreadline(session,head_line+i,sizeof(head_line)-i-1); 3067 } 3068 strListPush(&session->req.headers,head_line); 3069 3070 if((strtok_r(head_line,":",&last))!=NULL && (value=strtok_r(NULL,"",&last))!=NULL) { 3071 i=get_header_type(head_line); ** CID 330042: Program hangs (SLEEP) ________________________________________________________________________________________________________ *** CID 330042: Program hangs (SLEEP) /websrvr.c: 6311 in http_output_thread() 6305 *(bufdata++)='\r'; 6306 *(bufdata++)='\n'; 6307 len+=2; 6308 } 6309 6310 if(!failed) >>> CID 330042: Program hangs (SLEEP) >>> Call to "sess_sendbuf" might sleep while holding lock "session->outbuf_write". 6311 sess_sendbuf(session, buf, len, &failed); 6312 pthread_mutex_unlock(&session->outbuf_write); 6313 } 6314 thread_down(); 6315 /* Ensure outbuf isn't currently being drained */ 6316 pthread_mutex_lock(&session->outbuf_write); ** CID 33663: (TAINTED_SCALAR) ________________________________________________________________________________________________________ *** CID 33663: (TAINTED_SCALAR) /mxlookup.c: 332 in dns_getmx() 326 327 len=ntohs(rr->length); 328 if(ntohs(rr->type)==DNS_MX) { 329 pref=ntohs(*(WORD*)p); 330 p+=2; 331 namelen=0; >>> CID 33663: (TAINTED_SCALAR) >>> Passing tainted expression "*p" to "dns_name", which uses it as an offset. 332 p+=dns_name(hostname, &namelen, sizeof(hostname)-1, msg+offset, p); 333 if(pref<=highpref) { 334 highpref=pref; 335 if(mx[0]) 336 strcpy(mx2,mx); 337 strcpy(mx,hostname); /mxlookup.c: 332 in dns_getmx() 326 327 len=ntohs(rr->length); 328 if(ntohs(rr->type)==DNS_MX) { 329 pref=ntohs(*(WORD*)p); 330 p+=2; 331 namelen=0; >>> CID 33663: (TAINTED_SCALAR) >>> Passing tainted expression "*p" to "dns_name", which uses it as an offset. 332 p+=dns_name(hostname, &namelen, sizeof(hostname)-1, msg+offset, p); 333 if(pref<=highpref) { 334 highpref=pref; 335 if(mx[0]) 336 strcpy(mx2,mx); 337 strcpy(mx,hostname); /mxlookup.c: 314 in dns_getmx() 308 309 answers=ntohs(msghdr.ancount); 310 p=(char*)msg+len; /* Skip the header and question portion */ 311 312 for(i=0;i>> CID 33663: (TAINTED_SCALAR) >>> Passing tainted expression "*p" to "dns_name", which uses it as an offset. 314 p+=dns_name(hostname, &namelen, sizeof(hostname)-1, msg+offset, p); 315 316 rr=(dns_rr_t*)p; 317 p+=sizeof(dns_rr_t); 318 #if defined(MX_LOOKUP_TEST) 319 printf("answer #%d\n",i+1); /mxlookup.c: 332 in dns_getmx() 326 327 len=ntohs(rr->length); 328 if(ntohs(rr->type)==DNS_MX) { 329 pref=ntohs(*(WORD*)p); 330 p+=2; 331 namelen=0; >>> CID 33663: (TAINTED_SCALAR) >>> Passing tainted expression "*p" to "dns_name", which uses it as an offset. 332 p+=dns_name(hostname, &namelen, sizeof(hostname)-1, msg+offset, p); 333 if(pref<=highpref) { 334 highpref=pref; 335 if(mx[0]) 336 strcpy(mx2,mx); 337 strcpy(mx,hostname); /mxlookup.c: 314 in dns_getmx() 308 309 answers=ntohs(msghdr.ancount); 310 p=(char*)msg+len; /* Skip the header and question portion */ 311 312 for(i=0;i>> CID 33663: (TAINTED_SCALAR) >>> Passing tainted expression "*p" to "dns_name", which uses it as an offset. 314 p+=dns_name(hostname, &namelen, sizeof(hostname)-1, msg+offset, p); 315 316 rr=(dns_rr_t*)p; 317 p+=sizeof(dns_rr_t); 318 #if defined(MX_LOOKUP_TEST) 319 printf("answer #%d\n",i+1); /mxlookup.c: 314 in dns_getmx() 308 309 answers=ntohs(msghdr.ancount); 310 p=(char*)msg+len; /* Skip the header and question portion */ 311 312 for(i=0;i>> CID 33663: (TAINTED_SCALAR) >>> Passing tainted expression "*p" to "dns_name", which uses it as an offset. 314 p+=dns_name(hostname, &namelen, sizeof(hostname)-1, msg+offset, p); 315 316 rr=(dns_rr_t*)p; 317 p+=sizeof(dns_rr_t); 318 #if defined(MX_LOOKUP_TEST) 319 printf("answer #%d\n",i+1); ________________________________________________________________________________________________________ To view the defects in Coverity Scan visit, https://u15810271.ct.sendgrid.net/ls/click?upn=HRESupC-2F2Czv4BOaCWWCy7my0P0qcxCbhZ31OYv50yp-2FP9gGRhvFklLaQKuBylUrkMFB3WMR2p7qIYKYTZrh4BbWTBf-2B-2Fi5ZUVF-2Fo-2B6flxo-3DgxWT_g4j7BHlu96plUOfCQsO0yRjoWZCZl8YGnZ-2FUtT39hrCz-2FHLWEbfbfwfRJk6HAYb2nXmllk8VP2LmdOfioY9e5f9FKIRH487b3hVluhi0nXvHGlL4qxUitEqsOZ39O0N7vYloRKZTi0gGiI6hAtra7Lo6c8-2FFYmFqn2mUzrS2kSHW2v5oeGlNpRP-2F23ptNZWHW3gidk4CH8lp58gqzopvy-2Bhl83rsDQDCol5qXKVutHI-3D --- SBBSecho 3.14-Linux * Origin: Vertrauen - [vert/cvs/bbs].synchro.net (1:103/705) .