From 27a554ee0f1df1585db87957183b0ef362df5c4d Mon Sep 17 00:00:00 2001
From: rswindell <>
Date: Sat, 7 May 2005 01:59:16 +0000
Subject: [PATCH] Bugfix (buffer overflow) in sbbs_t::temp_xfer(). strcpy() of
 uninitialized temp_uler string over-writes f.dir and other stuff. Man I can't
 wait to nuke this code! Blechy! Pew!

---
 src/sbbs3/filedat.c    | 46 +++++++++++++++++++++---------------------
 src/sbbs3/tmp_xfer.cpp | 32 ++++++++++++++---------------
 2 files changed, 39 insertions(+), 39 deletions(-)

diff --git a/src/sbbs3/filedat.c b/src/sbbs3/filedat.c
index c3980bc161..ae1ca273a6 100644
--- a/src/sbbs3/filedat.c
+++ b/src/sbbs3/filedat.c
@@ -8,7 +8,7 @@
  * @format.tab-size 4		(Plain Text/Source Code File Header)			*
  * @format.use-tabs true	(see http://www.synchro.net/ptsc_hdr.html)		*
  *																			*
- * Copyright 2003 Rob Swindell - http://www.synchro.net/copyright.html		*
+ * Copyright 2005 Rob Swindell - http://www.synchro.net/copyright.html		*
  *																			*
  * This program is free software; you can redistribute it and/or			*
  * modify it under the terms of the GNU General Public License				*
@@ -48,7 +48,7 @@ BOOL DLLCALL getfiledat(scfg_t* cfg, file_t* f)
 	int file;
 	long length;
 
-	sprintf(str,"%s%s.dat",cfg->dir[f->dir]->data_dir,cfg->dir[f->dir]->code);
+	SAFEPRINTF2(str,"%s%s.dat",cfg->dir[f->dir]->data_dir,cfg->dir[f->dir]->code);
 	if((file=sopen(str,O_RDONLY|O_BINARY,SH_DENYWR))==-1) {
 		return(FALSE); 
 	}
@@ -125,7 +125,7 @@ BOOL DLLCALL putfiledat(scfg_t* cfg, file_t* f)
 	buf[F_MISC]=f->misc+' ';
 	putrec(buf,F_ALTPATH,2,hexplus(f->altpath,tmp));
 	putrec(buf,F_ALTPATH+2,2,crlf);
-	sprintf(str,"%s%s.dat",cfg->dir[f->dir]->data_dir,cfg->dir[f->dir]->code);
+	SAFEPRINTF2(str,"%s%s.dat",cfg->dir[f->dir]->data_dir,cfg->dir[f->dir]->code);
 	if((file=sopen(str,O_WRONLY|O_BINARY,SH_DENYRW))==-1) {
 		return(FALSE); 
 	}
@@ -169,7 +169,7 @@ BOOL DLLCALL addfiledat(scfg_t* cfg, file_t* f)
 	/************************/
 	/* Add data to DAT File */
 	/************************/
-	sprintf(str,"%s%s.dat",cfg->dir[f->dir]->data_dir,cfg->dir[f->dir]->code);
+	SAFEPRINTF2(str,"%s%s.dat",cfg->dir[f->dir]->data_dir,cfg->dir[f->dir]->code);
 	if((file=sopen(str,O_RDWR|O_BINARY|O_CREAT,SH_DENYRW,S_IREAD|S_IWRITE))==-1) {
 		return(FALSE); 
 	}
@@ -221,7 +221,7 @@ BOOL DLLCALL addfiledat(scfg_t* cfg, file_t* f)
 	/*******************************************/
 	/* Update last upload date/time stamp file */
 	/*******************************************/
-	sprintf(str,"%s%s.dab",cfg->dir[f->dir]->data_dir,cfg->dir[f->dir]->code);
+	SAFEPRINTF2(str,"%s%s.dab",cfg->dir[f->dir]->data_dir,cfg->dir[f->dir]->code);
 	if((file=sopen(str,O_WRONLY|O_CREAT|O_BINARY,SH_DENYRW,S_IREAD|S_IWRITE))!=-1) {
 		now=time(NULL);
 		write(file,&now,4);
@@ -231,10 +231,10 @@ BOOL DLLCALL addfiledat(scfg_t* cfg, file_t* f)
 	/************************/
 	/* Add data to IXB File */
 	/************************/
-	strcpy(fname,f->name);
+	SAFECOPY(fname,f->name);
 	for(i=8;i<12;i++)   /* Turn FILENAME.EXT into FILENAMEEXT */
 		fname[i]=fname[i+1];
-	sprintf(str,"%s%s.ixb",cfg->dir[f->dir]->data_dir,cfg->dir[f->dir]->code);
+	SAFEPRINTF2(str,"%s%s.ixb",cfg->dir[f->dir]->data_dir,cfg->dir[f->dir]->code);
 	if((file=sopen(str,O_RDWR|O_CREAT|O_BINARY,SH_DENYRW,S_IREAD|S_IWRITE))==-1) {
 		return(FALSE); 
 	}
@@ -330,7 +330,7 @@ BOOL DLLCALL getfileixb(scfg_t* cfg, file_t* f)
 	int				file;
 	long			l,length;
 
-	sprintf(str,"%s%s.ixb",cfg->dir[f->dir]->data_dir,cfg->dir[f->dir]->code);
+	SAFEPRINTF2(str,"%s%s.ixb",cfg->dir[f->dir]->data_dir,cfg->dir[f->dir]->code);
 	if((file=sopen(str,O_RDONLY|O_BINARY,SH_DENYWR))==-1) {
 		return(FALSE); 
 	}
@@ -349,11 +349,11 @@ BOOL DLLCALL getfileixb(scfg_t* cfg, file_t* f)
 		return(FALSE); 
 	}
 	close(file);
-	strcpy(fname,f->name);
+	SAFECOPY(fname,f->name);
 	for(l=8;l<12;l++)	/* Turn FILENAME.EXT into FILENAMEEXT */
 		fname[l]=fname[l+1];
 	for(l=0;l<length;l+=F_IXBSIZE) {
-		sprintf(str,"%11.11s",ixbbuf+l);
+		SAFEPRINTF(str,"%11.11s",ixbbuf+l);
 		if(!stricmp(str,fname))
 			break; 
 	}
@@ -380,10 +380,10 @@ BOOL DLLCALL removefiledat(scfg_t* cfg, file_t* f)
     int		i,file;
 	long	l,length;
 
-	strcpy(fname,f->name);
+	SAFECOPY(fname,f->name);
 	for(i=8;i<12;i++)   /* Turn FILENAME.EXT into FILENAMEEXT */
 		fname[i]=fname[i+1];
-	sprintf(str,"%s%s.ixb",cfg->dir[f->dir]->data_dir,cfg->dir[f->dir]->code);
+	SAFEPRINTF2(str,"%s%s.ixb",cfg->dir[f->dir]->data_dir,cfg->dir[f->dir]->code);
 	if((file=sopen(str,O_RDONLY|O_BINARY,SH_DENYWR))==-1) {
 		return(FALSE); 
 	}
@@ -418,7 +418,7 @@ BOOL DLLCALL removefiledat(scfg_t* cfg, file_t* f)
 	}
 	FREE((char *)ixbbuf);
 	close(file);
-	sprintf(str,"%s%s.dat",cfg->dir[f->dir]->data_dir,cfg->dir[f->dir]->code);
+	SAFEPRINTF2(str,"%s%s.dat",cfg->dir[f->dir]->data_dir,cfg->dir[f->dir]->code);
 	if((file=sopen(str,O_WRONLY|O_BINARY,SH_DENYRW))==-1) {
 		return(FALSE); 
 	}
@@ -445,11 +445,11 @@ BOOL DLLCALL findfile(scfg_t* cfg, uint dirnum, char *filename)
     int i,file;
     long length,l;
 
-	sprintf(fname,"%.12s",filename);
+	SAFECOPY(fname,filename);
 	strupr(fname);
 	for(i=8;i<12;i++)   /* Turn FILENAME.EXT into FILENAMEEXT */
 		fname[i]=fname[i+1];
-	sprintf(str,"%s%s.ixb",cfg->dir[dirnum]->data_dir,cfg->dir[dirnum]->code);
+	SAFEPRINTF2(str,"%s%s.ixb",cfg->dir[dirnum]->data_dir,cfg->dir[dirnum]->code);
 	if((file=sopen(str,O_RDONLY|O_BINARY,SH_DENYWR))==-1) return(FALSE);
 	length=filelength(file);
 	if(!length) {
@@ -523,7 +523,7 @@ BOOL DLLCALL rmuserxfers(scfg_t* cfg, int fromuser, int destuser, char *fname)
     int file;
     long l,length;
 
-	sprintf(str,"%sxfer.ixt", cfg->data_dir);
+	SAFEPRINTF(str,"%sxfer.ixt", cfg->data_dir);
 	if(!fexist(str))
 		return(FALSE);
 	if(!flength(str)) {
@@ -581,7 +581,7 @@ void DLLCALL getextdesc(scfg_t* cfg, uint dirnum, ulong datoffset, char *ext)
 	int file;
 
 	memset(ext,0,F_EXBSIZE+1);
-	sprintf(str,"%s%s.exb",cfg->dir[dirnum]->data_dir,cfg->dir[dirnum]->code);
+	SAFEPRINTF2(str,"%s%s.exb",cfg->dir[dirnum]->data_dir,cfg->dir[dirnum]->code);
 	if((file=nopen(str,O_RDONLY))==-1)
 		return;
 	lseek(file,(datoffset/F_LEN)*F_EXBSIZE,SEEK_SET);
@@ -596,7 +596,7 @@ void DLLCALL putextdesc(scfg_t* cfg, uint dirnum, ulong datoffset, char *ext)
 
 	strip_invalid_attr(ext);	/* eliminate bogus ctrl-a codes */
 	memset(nulbuf,0,sizeof(nulbuf));
-	sprintf(str,"%s%s.exb",cfg->dir[dirnum]->data_dir,cfg->dir[dirnum]->code);
+	SAFEPRINTF2(str,"%s%s.exb",cfg->dir[dirnum]->data_dir,cfg->dir[dirnum]->code);
 	if((file=nopen(str,O_WRONLY|O_CREAT))==-1)
 		return;
 	lseek(file,0L,SEEK_END);
@@ -619,7 +619,7 @@ int DLLCALL update_uldate(scfg_t* cfg, file_t* f)
 	/*******************/
 	/* Update IXB File */
 	/*******************/
-	sprintf(str,"%s%s.ixb",cfg->dir[f->dir]->data_dir,cfg->dir[f->dir]->code);
+	SAFEPRINTF2(str,"%s%s.ixb",cfg->dir[f->dir]->data_dir,cfg->dir[f->dir]->code);
 	if((file=nopen(str,O_RDWR))==-1)
 		return(errno); 
 	length=filelength(file);
@@ -627,7 +627,7 @@ int DLLCALL update_uldate(scfg_t* cfg, file_t* f)
 		close(file);
 		return(-1); 
 	}
-	strcpy(fname,f->name);
+	SAFECOPY(fname,f->name);
 	for(i=8;i<12;i++)   /* Turn FILENAME.EXT into FILENAMEEXT */
 		fname[i]=fname[i+1];
 	for(l=0;l<length;l+=F_IXBSIZE) {
@@ -645,7 +645,7 @@ int DLLCALL update_uldate(scfg_t* cfg, file_t* f)
 	/*******************************************/
 	/* Update last upload date/time stamp file */
 	/*******************************************/
-	sprintf(str,"%s%s.dab",cfg->dir[f->dir]->data_dir,cfg->dir[f->dir]->code);
+	SAFEPRINTF2(str,"%s%s.dab",cfg->dir[f->dir]->data_dir,cfg->dir[f->dir]->code);
 	if((file=nopen(str,O_WRONLY|O_CREAT))==-1)
 		return(errno);
 
@@ -663,9 +663,9 @@ char* DLLCALL getfilepath(scfg_t* cfg, file_t* f, char* path)
 
 	unpadfname(f->name,fname);
 	if(f->dir>=cfg->total_dirs)
-		sprintf(path,"%s%s",cfg->temp_dir,fname);
+		SAFEPRINTF2(path,"%s%s",cfg->temp_dir,fname);
 	else
-		sprintf(path,"%s%s",f->altpath>0 && f->altpath<=cfg->altpaths 
+		SAFEPRINTF2(path,"%s%s",f->altpath>0 && f->altpath<=cfg->altpaths 
 			? cfg->altpath[f->altpath-1] : cfg->dir[f->dir]->path
 			,fname);
 
diff --git a/src/sbbs3/tmp_xfer.cpp b/src/sbbs3/tmp_xfer.cpp
index db44d9b065..07d17b688b 100644
--- a/src/sbbs3/tmp_xfer.cpp
+++ b/src/sbbs3/tmp_xfer.cpp
@@ -8,7 +8,7 @@
  * @format.tab-size 4		(Plain Text/Source Code File Header)			*
  * @format.use-tabs true	(see http://www.synchro.net/ptsc_hdr.html)		*
  *																			*
- * Copyright 2004 Rob Swindell - http://www.synchro.net/copyright.html		*
+ * Copyright 2005 Rob Swindell - http://www.synchro.net/copyright.html		*
  *																			*
  * This program is free software; you can redistribute it and/or			*
  * modify it under the terms of the GNU General Public License				*
@@ -66,11 +66,11 @@ void sbbs_t::temp_xfer()
 		errormsg(WHERE,ERR_ALLOC,"temp_dir",sizeof(dir_t));
 		return; }
 	memset(cfg.dir[dirnum],0,sizeof(dir_t));
-	strcpy(cfg.dir[dirnum]->lname,"Temporary");
-	strcpy(cfg.dir[dirnum]->sname,"Temp");
-	strcpy(cfg.dir[dirnum]->code,"TEMP");
-	strcpy(cfg.dir[dirnum]->path,cfg.temp_dir);
-	strcpy(cfg.dir[dirnum]->data_dir,cfg.dir[0]->data_dir);
+	SAFECOPY(cfg.dir[dirnum]->lname,"Temporary");
+	SAFECOPY(cfg.dir[dirnum]->sname,"Temp");
+	SAFECOPY(cfg.dir[dirnum]->code,"TEMP");
+	SAFECOPY(cfg.dir[dirnum]->path,cfg.temp_dir);
+	SAFECOPY(cfg.dir[dirnum]->data_dir,cfg.dir[0]->data_dir);
 	cfg.dir[dirnum]->maxfiles=MAX_FILES;
 	cfg.dir[dirnum]->op_ar=(uchar *)nulstr;
 	temp_dirnum=curdirnum=usrdir[curlib][curdir[curlib]];
@@ -80,8 +80,8 @@ void sbbs_t::temp_xfer()
 	/* Fill filedat information */
 	/****************************/
 	memset(&f,0,sizeof(f));
-	sprintf(f.name,"temp_%3.3d.%s",cfg.node_num,useron.tmpext);
-	strcpy(f.desc,"Temp File");
+	SAFEPRINTF2(f.name,"temp_%3.3d.%s",cfg.node_num,useron.tmpext);
+	SAFECOPY(f.desc,"Temp File");
 	f.dir=dirnum;
 
 	if(useron.misc&(RIP|WIP|HTML) && !(useron.misc&EXPERT))
@@ -98,7 +98,7 @@ void sbbs_t::temp_xfer()
 			menu("tempxfer"); }
 		ASYNC;
 		bputs(text[TempDirPrompt]);
-		strcpy(f.uler,temp_uler);
+		SAFECOPY(f.uler,temp_uler);
 		ch=(char)getkeys("ADEFNILQRVX?\r",0);
 		if(ch>' ')
 			logch(ch,0);
@@ -153,7 +153,7 @@ void sbbs_t::temp_xfer()
 				xfer_prot_menu(XFER_DOWNLOAD);
 				SYNC;
 				mnemonics(text[ProtocolOrQuit]);
-				strcpy(tmp2,"Q");
+				SAFECOPY(tmp2,"Q");
 				for(i=0;i<cfg.total_prots;i++)
 					if(cfg.prot[i]->dlcmd[0] && chk_ar(cfg.prot[i]->ar,&useron)) {
 						sprintf(tmp,"%c",cfg.prot[i]->mnemonic);
@@ -314,11 +314,11 @@ void sbbs_t::extract(uint dirnum)
 		|| strchr(fname,'?'))
 		return;
 	padfname(fname,f.name);
-	strcpy(str,f.name);
+	SAFECOPY(str,f.name);
 	truncsp(str);
 	for(i=0;i<cfg.total_fextrs;i++)
 		if(!stricmp(str+9,cfg.fextr[i]->ext) && chk_ar(cfg.fextr[i]->ar,&useron)) {
-			strcpy(excmd,cfg.fextr[i]->cmd);
+			SAFECOPY(excmd,cfg.fextr[i]->cmd);
 			break; }
 	if(i==cfg.total_fextrs) {
 		bputs(text[UnextractableFile]);
@@ -363,8 +363,8 @@ void sbbs_t::extract(uint dirnum)
 			temp_cdt=0L;
 		else
 			temp_cdt=f.cdt;
-		strcpy(temp_uler,f.uler);
-		strcpy(temp_file,f.name); }     /* padded filename */
+		SAFECOPY(temp_uler,f.uler);
+		SAFECOPY(temp_file,f.name); }     /* padded filename */
 	if(!fexistcase(path)) {
 		bputs(text[FileNotThere]);  /* not on disk */
 		return; }
@@ -438,8 +438,8 @@ ulong sbbs_t::create_filelist(char *name, long mode)
 		bputs(text[NoFiles]);
 		sprintf(str,"%s%s",cfg.temp_dir,name);
 		remove(str); }
-	strcpy(temp_file,name);
-	strcpy(temp_uler,"File List");
+	SAFECOPY(temp_file,name);
+	SAFECOPY(temp_uler,"File List");
 	return(k);
 }
 
-- 
GitLab