|
|
1.1 root 1: /* SBBSECHO.C */
2:
1.1.1.2 ! root 3: /* Developed 1990-2000 by Rob Swindell; PO Box 501, Yorba Linda, CA 92885 */
1.1 root 4:
5: /* Portions written by Allen Christiansen 1994-1996 */
6:
7: /* Synchronet FidoNet EchoMail Scanning/Tossing and NetMail Tossing Utility */
8:
9: #include <dos.h>
10: #include <mem.h>
11: #include <time.h>
12: #include <errno.h>
13: #include <stdio.h>
14: #include <conio.h>
15: #include <ctype.h>
16: #include <fcntl.h>
17: #include <share.h>
18: #include <malloc.h>
19: #include <stdarg.h>
20: #include <stdlib.h>
21: #include <string.h>
22: #include <process.h>
23: #include <sys\stat.h>
24:
25: #include "sbbsdefs.h"
26: #include "smblib.h"
27: #include "scfglib.h"
28: #define GLOBAL extern /* turn vars.c and scfgvars.c files into headers */
29: #include "scfgvars.c"
30: #include "post.h"
31: #include "lzh.h"
32: #include "sbbsecho.h"
33:
34: extern long crc32tbl[];
35: ulong crc32(char *str);
36:
37: #ifndef __FLAT__
38: #include "..\..\spawno\spawno.h"
39: #endif
40:
41: #ifdef __TURBOC__
42: unsigned _stklen=20000;
43: #endif
44:
45: #ifdef __WATCOMC__
46: #define O_DENYNONE SH_DENYNO
47: #endif
48:
49: char *wday[]={"Sun","Mon","Tue","Wed","Thu","Fri","Sat"};
50: char *mon[]={"Jan","Feb","Mar","Apr","May","Jun"
51: ,"Jul","Aug","Sep","Oct","Nov","Dec"};
52:
53: smb_t *smb,*email;
54: long misc=(IMPORT_PACKETS|IMPORT_NETMAIL|IMPORT_ECHOMAIL|EXPORT_ECHOMAIL
55: |DELETE_NETMAIL|DELETE_PACKETS);
56: ulong netmail=0;
57: char tmp[256],pkt_type=0;
58: faddr_t sys_faddr;
59: config_t cfg;
60: int nodefile,secure,cur_smb=0;
61: FILE *fidologfile=NULL;
62: two_two_t two_two;
63: two_plus_t two_plus;
64:
65: #ifdef __WATCOMC__
66: /******************************************************************************
67: A DOS to Unix function - because WATCOM doesn't have one
68: ******************************************************************************/
69: time_t dostounix(struct date *d,struct time *t)
70: {
71: struct tm tm;
72:
73: tm.tm_sec=t->ti_sec;
74: tm.tm_min=t->ti_min;
75: tm.tm_hour=t->ti_hour;
76: tm.tm_mday=d->da_day;
77: tm.tm_mon=(d->da_mon-1);
78: tm.tm_year=d->da_year-1900;
79: tm.tm_isdst=0;
80:
81: return(mktime(&tm));
82: }
83: #endif
84:
85: #ifndef __NT__
86: #define delfile(x) remove(x)
87: #else
88: int delfile(char *filename)
89: {
90: int i=0;
91:
92: while(remove(filename) && i++<120) /* Wait up to 60 seconds to delete file */
93: delay(500); /* for Win95 bug fix */
94: return(i);
95: }
96: #endif
97:
98: /******************************************************************************
99: This turns the DOS file date garbage into a long
100: ******************************************************************************/
101: long ddtol(ushort ftim, ushort fdat)
102: {
103: struct date date;
104: struct time time;
105:
106: date.da_year=((fdat&0xfe00)>>9)+1980;
107: date.da_mon=((fdat&0x01e0)>>5);
108: date.da_day=(fdat&0x001f);
109: time.ti_hour=((ftim&0xf800)>>11);
110: time.ti_min=((ftim&0x07e0)>>5);
111: time.ti_sec=((ftim&0x001f)<<1);
112: time.ti_hund=0;
113: return(dostounix(&date,&time));
114: }
115: void checkmem(void)
116: {
117: #ifdef __WATCOMC__
118: char *p=NULL;
119: long size=640L*1024L,over;
120:
121: while(size>0) {
122: p=(char *)LMALLOC(size);
123: if(p)
124: break;
125: size-=1024L; }
126:
127: printf("\nAvailable Memory = %ld bytes",size);
128: if(p)
129: LFREE(p);
130: #elif !defined(__OS2__)
131: printf("\nAvailable Memory = %ld bytes",farcoreleft());
132: #endif
133: }
134:
135: /**********************/
136: /* Log print function */
137: /**********************/
138: void logprintf(char *str, ...)
139: {
140: va_list argptr;
141: char buf[256];
142: time_t now;
143: struct tm *gm;
144:
145: if(!(misc&LOGFILE) || fidologfile==NULL)
146: return;
147: va_start(argptr,str);
148: vsprintf(buf,str,argptr);
149: va_end(argptr);
150: now=time(NULL);
151: gm=localtime(&now);
152: fseek(fidologfile,0L,SEEK_END);
153: fprintf(fidologfile,"%02u/%02u/%02u %02u:%02u:%02u %s\r\n"
1.1.1.2 ! root 154: ,gm->tm_mon+1,gm->tm_mday,TM_YEAR(gm->tm_year),gm->tm_hour,gm->tm_min,gm->tm_sec
1.1 root 155: ,buf);
156: fflush(fidologfile);
157: }
158:
159: /****************************************************************************/
160: /* Puts a backslash on path strings */
161: /****************************************************************************/
162: void backslash(char *str)
163: {
164: int i;
165:
166: i=strlen(str);
167: if(i && str[i-1]!='\\') {
168: str[i]='\\'; str[i+1]=0; }
169: }
170:
171: /*****************************************************************************/
172: /* Returns command line generated from instr with %c replacments */
173: /*****************************************************************************/
174: char *cmdstr(char *instr, char *fpath, char *fspec)
175: {
176: static char cmd[128];
177: char str[256],str2[128];
178: int i,j,len;
179:
180: len=strlen(instr);
181: for(i=j=0;i<len && j<128;i++) {
182: if(instr[i]=='%') {
183: i++;
184: cmd[j]=0;
185: switch(toupper(instr[i])) {
186: case 'F': /* File path */
187: strcat(cmd,fpath);
188: break;
189: case 'G': /* Temp directory */
190: if(temp_dir[0]!='\\' && temp_dir[1]!=':') {
191: strcpy(str,node_dir);
192: strcat(str,temp_dir);
193: if(_fullpath(str2,str,40))
194: strcpy(str,str2);
195: backslash(str);
196: strcat(cmd,str);}
197: else
198: strcat(cmd,temp_dir);
199: break;
200: case 'J':
201: if(data_dir[0]!='\\' && data_dir[1]!=':') {
202: strcpy(str,node_dir);
203: strcat(str,data_dir);
204: if(_fullpath(str2,str,40))
205: strcpy(str,str2);
206: backslash(str);
207: strcat(cmd,str); }
208: else
209: strcat(cmd,data_dir);
210: break;
211: case 'K':
212: if(ctrl_dir[0]!='\\' && ctrl_dir[1]!=':') {
213: strcpy(str,node_dir);
214: strcat(str,ctrl_dir);
215: if(_fullpath(str2,str,40))
216: strcpy(str,str2);
217: backslash(str);
218: strcat(cmd,str); }
219: else
220: strcat(cmd,ctrl_dir);
221: break;
222: case 'N': /* Node Directory (same as SBBSNODE environment var) */
223: strcat(cmd,node_dir);
224: break;
225: case 'O': /* SysOp */
226: strcat(cmd,sys_op);
227: break;
228: case 'Q': /* QWK ID */
229: strcat(cmd,sys_id);
230: break;
231: case 'S': /* File Spec */
232: strcat(cmd,fspec);
233: break;
234: case '!': /* EXEC Directory */
235: if(exec_dir[0]!='\\' && exec_dir[1]!=':') {
236: strcpy(str,node_dir);
237: strcat(str,exec_dir);
238: if(_fullpath(str2,str,40))
239: strcpy(str,str2);
240: backslash(str);
241: strcat(cmd,str); }
242: else
243: strcat(cmd,exec_dir);
244: break;
245: case '#': /* Node number (same as SBBSNNUM environment var) */
246: sprintf(str,"%d",node_num);
247: strcat(cmd,str);
248: break;
249: case '*':
250: sprintf(str,"%03d",node_num);
251: strcat(cmd,str);
252: break;
253: case '%': /* %% for percent sign */
254: strcat(cmd,"%");
255: break;
256: default: /* unknown specification */
257: printf("ERROR Checking Command Line '%s'\n",instr);
258: logprintf("ERROR line %d Checking Command Line '%s'",__LINE__
259: ,instr);
260: exit(1);
261: break; }
262: j=strlen(cmd); }
263: else
264: cmd[j++]=instr[i]; }
265: cmd[j]=0;
266:
267: return(cmd);
268: }
269:
270: /****************************************************************************/
271: /* Runs an external program directly using spawnvp */
272: /****************************************************************************/
273: int execute(char *cmdline)
274: {
275: char c,d,e,cmdlen,*arg[30],str[256];
276: int i;
277:
278: strcpy(str,cmdline);
279: arg[0]=str; /* point to the beginning of the string */
280: cmdlen=strlen(str);
281: for(c=0,d=1,e=0;c<cmdlen;c++,e++) /* Break up command line */
282: if(str[c]==SP) {
283: str[c]=0; /* insert nulls */
284: arg[d++]=str+c+1; /* point to the beginning of the next arg */
285: e=0; }
286: arg[d]=0;
287: #ifndef __FLAT__
288: if(node_swap) {
289: printf("Swapping...\n");
290: i=spawnvpo(".\\",(const char *)arg[0],(const char **)arg); }
291: else
292: #endif
293: i=spawnvp(P_WAIT,arg[0],arg);
294: return(i);
295: }
296: /******************************************************************************
297: Returns the system address with the same zone as the address passed
298: ******************************************************************************/
299: faddr_t getsysfaddr(short zone)
300: {
301: int i;
302: faddr_t sysfaddr;
303:
304: sysfaddr.zone=sysfaddr.net=sysfaddr.node=1;
305: sysfaddr.point=0;
306: if(!total_faddrs)
307: return(sys_faddr);
308: sysfaddr=faddr[0];
309: if(total_faddrs==1)
310: return(sysfaddr);
311: for(i=0;i<total_faddrs;i++)
312: if(faddr[i].zone==zone)
313: return(faddr[i]);
314: return(sysfaddr);
315: }
316: /******************************************************************************
317: This function creates or appends on existing Binkley compatible .?LO file
318: attach file.
319: Returns 0 on success.
320: ******************************************************************************/
321: int write_flofile(char *attachment, faddr_t dest)
322: {
323: char fname[256],outbound[128],str[128],ch;
324: ushort attr=0;
325: int i,file;
326: FILE *stream;
327:
328: i=matchnode(dest,0);
329: if(i<cfg.nodecfgs)
330: attr=cfg.nodecfg[i].attr;
331:
332: if(attr&ATTR_CRASH) ch='C';
333: else if(attr&ATTR_HOLD) ch='H';
334: else if(attr&ATTR_DIRECT) ch='D';
335: else ch='F';
336: if(dest.zone==faddr[0].zone) /* Default zone, use default outbound */
337: strcpy(outbound,cfg.outbound);
338: else /* Inter-zone outbound is OUTBOUND.XXX */
339: sprintf(outbound,"%.*s.%03X\\"
340: ,strlen(cfg.outbound)-1,cfg.outbound,dest.zone);
341: if(dest.point) { /* Point destination is OUTBOUND\*.PNT */
342: sprintf(str,"%04X%04X.PNT"
343: ,dest.net,dest.node);
344: strcat(outbound,str); }
345: if(outbound[strlen(outbound)-1]=='\\')
346: outbound[strlen(outbound)-1]=0;
347: mkdir(outbound);
348: strcat(outbound,"\\");
349: if(dest.point)
350: sprintf(fname,"%s%08X.%cLO",outbound,dest.point,ch);
351: else
352: sprintf(fname,"%s%04X%04X.%cLO",outbound,dest.net,dest.node,ch);
353: if((stream=fnopen(&file,fname,O_WRONLY|O_CREAT))==NULL) {
354: printf("\7ERROR opening %s %s\n",fname,sys_errlist[errno]);
355: logprintf("ERROR line %d opening %s %s",__LINE__,fname,sys_errlist[errno]);
356: return(-1); }
357:
358: fseek(stream,0L,SEEK_END);
359: fprintf(stream,"^%s\r\n",attachment);
360: fclose(stream);
361: return(0);
362: }
363:
364: /******************************************************************************
365: This function will create a netmail message (.MSG format).
366: If file is non-zero, will set file attachment bit (for bundles).
367: Returns 0 on success.
368: ******************************************************************************/
369: int create_netmail(char *to,char *subject,char *body,faddr_t dest,int file)
370: {
371: FILE *fstream;
372: char str[256],fname[256];
373: ushort attr=0;
374: int fmsg;
375: uint i;
376: static uint startmsg;
377: time_t t;
1.1.1.2 ! root 378: faddr_t faddr;
1.1 root 379: fmsghdr_t hdr;
380: struct tm *tm;
381:
382: if(!startmsg) startmsg=1;
383: i=matchnode(dest,0);
384: if(i<cfg.nodecfgs) {
385: attr=cfg.nodecfg[i].attr;
386: if(!attr) {
387: i=matchnode(dest,2);
388: if(i<cfg.nodecfgs)
389: attr=cfg.nodecfg[i].attr; } }
390:
391: do {
392: for(i=startmsg;i;i++) {
393: sprintf(fname,"%s%u.MSG",netmail_dir,i);
394: if(!fexist(fname))
395: break; }
396: if(!i) {
397: printf("\7%s directory full!\n",netmail_dir);
398: logprintf("Directory full: %s",netmail_dir);
399: return(-1); }
400: startmsg=i+1;
401: strupr(fname);
402: if((fstream=fnopen(&fmsg,fname,O_RDWR|O_CREAT))==NULL) {
403: printf("\7ERROR opening %s %s\n",fname,sys_errlist[errno]);
404: logprintf("ERROR line %d opening %s %s",__LINE__,fname,sys_errlist[errno]);
405: return(-1); }
406:
1.1.1.2 ! root 407: faddr=getsysfaddr(dest.zone);
1.1 root 408: memset(&hdr,0,sizeof(fmsghdr_t));
1.1.1.2 ! root 409: hdr.origzone=faddr.zone;
! 410: hdr.orignet=faddr.net;
! 411: hdr.orignode=faddr.node;
! 412: hdr.origpoint=faddr.point;
1.1 root 413: hdr.destzone=dest.zone;
414: hdr.destnet=dest.net;
415: hdr.destnode=dest.node;
416: hdr.destpoint=dest.point;
417:
418: hdr.attr=(FIDO_PRIVATE|FIDO_KILLSENT|FIDO_LOCAL);
419: if(file)
420: hdr.attr|=FIDO_FILE;
421:
422: if(attr&ATTR_HOLD)
423: hdr.attr|=FIDO_HOLD;
424: if(attr&ATTR_CRASH)
425: hdr.attr|=FIDO_CRASH;
426:
427: sprintf(hdr.from,"SBBSecho");
428:
429: t=time(NULL);
430: tm=gmtime(&t);
431: sprintf(hdr.time,"%02u %3.3s %02u %02u:%02u:%02u"
1.1.1.2 ! root 432: ,tm->tm_mday,mon[tm->tm_mon],TM_YEAR(tm->tm_year)
1.1 root 433: ,tm->tm_hour,tm->tm_min,tm->tm_sec);
434:
435: if(to)
436: sprintf(hdr.to,"%s",to);
437: else
438: sprintf(hdr.to,"SYSOP");
439:
440: sprintf(hdr.subj,"%.71s",subject);
441:
442: fwrite(&hdr,sizeof(fmsghdr_t),1,fstream);
443: sprintf(str,"\1INTL %u:%u/%u %u:%u/%u\r"
444: ,hdr.destzone,hdr.destnet,hdr.destnode
445: ,hdr.origzone,hdr.orignet,hdr.orignode);
446: fwrite(str,strlen(str),1,fstream);
447: if(attr&ATTR_DIRECT) {
448: fwrite("\1FLAGS DIR",10,1,fstream);
449: if(file)
450: fwrite(" KFS\r",5,1,fstream);
451: else
452: fwrite("\r",1,1,fstream); }
453: if(hdr.destpoint) {
454: sprintf(str,"\1TOPT %u\r",hdr.destpoint);
455: fwrite(str,strlen(str),1,fstream); }
456: if(hdr.origpoint) {
457: sprintf(str,"\1FMPT %u\r",hdr.origpoint);
458: fwrite(str,strlen(str),1,fstream); }
459: if(!file || (!(attr&ATTR_DIRECT) && file))
460: fwrite(body,strlen(body)+1,1,fstream); /* Write additional NULL */
461: else
462: fwrite("\0",1,1,fstream); /* Write NULL */
463: fclose(fstream);
464: } while(!fexist(fname));
465: return(0);
466: }
467:
468: /******************************************************************************
469: This function takes the contents of 'infile' and puts it into a netmail
470: message bound for addr.
471: ******************************************************************************/
472: void file_to_netmail(FILE *infile,char *title,faddr_t addr,char *to)
473: {
474: char *buf,*p;
475: long l,m,len;
476:
477: l=len=ftell(infile);
478: if(len>8192L)
479: len=8192L;
480: rewind(infile);
481: if((buf=(char *)MALLOC(len+1))==NULL) {
482: printf("ERROR allocating %lu bytes for file to netmail buffer.\n",len);
483: logprintf("ERROR line %d allocating %lu for file to netmail buf",__LINE__
484: ,len);
485: return; }
486: while((m=fread(buf,1,(len>8064L) ? 8064L:len,infile))>0) {
487: buf[m]=0;
488: if(l>8064L && (p=strrchr(buf,'\n'))!=NULL) {
489: p++;
490: if(*p) {
491: *p=0;
492: p++;
493: fseek(infile,-1L,SEEK_CUR);
494: while(*p) { /* Seek back to end of last line */
495: p++;
496: fseek(infile,-1L,SEEK_CUR); } } }
497: if(ftell(infile)<l)
498: strcat(buf,"\r\nContinued in next message...\r\n");
499: create_netmail(to,title,buf,addr,0); }
500: FREE(buf);
501: }
502: /******************************************************************************
503: This function sends a notify list to applicable nodes, this list includes the
504: settings configured for the node, as well as a list of areas the node is
505: connected to.
506: ******************************************************************************/
507: void notify_list(void)
508: {
509: FILE *tmpf;
510: char str[256];
511: int i,j,k;
512:
513: for(k=0;k<cfg.nodecfgs;k++) {
514:
515: if(!(cfg.nodecfg[k].attr&SEND_NOTIFY))
516: continue;
517:
518: if((tmpf=tmpfile())==NULL) {
519: printf("\7ERROR couldn't open tmpfile.\n");
520: logprintf("ERROR line %d couldn't open tmpfile",__LINE__);
521: return; }
522:
523: fprintf(tmpf,"Following are the options set for your system and a list "
524: "of areas\r\nyou are connected to. Please make sure everything "
525: "is correct.\r\n\r\n");
526: fprintf(tmpf,"Packet Type %s\r\n"
527: ,cfg.nodecfg[k].pkt_type==PKT_TWO ? "2"
528: :cfg.nodecfg[k].pkt_type==PKT_TWO_TWO ? "2.2":"2+");
529: fprintf(tmpf,"Archive Type %s\r\n"
530: ,(cfg.nodecfg[k].arctype>cfg.arcdefs) ?
531: "None":cfg.arcdef[cfg.nodecfg[k].arctype].name);
532: fprintf(tmpf,"Mail Status %s\r\n"
533: ,cfg.nodecfg[k].attr&ATTR_CRASH ? "Crash"
534: :cfg.nodecfg[k].attr&ATTR_HOLD ? "Hold" : "None");
535: fprintf(tmpf,"Direct %s\r\n"
536: ,cfg.nodecfg[k].attr&ATTR_DIRECT ? "Yes":"No");
537: fprintf(tmpf,"Passive %s\r\n"
538: ,cfg.nodecfg[k].attr&ATTR_PASSIVE ? "Yes":"No");
539: fprintf(tmpf,"Remote AreaMgr %s\r\n\r\n"
540: ,cfg.nodecfg[k].password[0] ? "Yes" : "No");
541:
542: fprintf(tmpf,"Connected Areas\r\n---------------\r\n");
543: for(i=0;i<cfg.areas;i++) {
544: sprintf(str,"%s\r\n",cfg.area[i].name);
545: if(str[0]=='*')
546: continue;
547: for(j=0;j<cfg.area[i].uplinks;j++)
548: if(!memcmp(&cfg.nodecfg[k].faddr,&cfg.area[i].uplink[j]
549: ,sizeof(faddr_t)))
550: break;
551: if(j<cfg.area[i].uplinks)
552: fprintf(tmpf,"%s",str); }
553:
554: if(ftell(tmpf))
555: file_to_netmail(tmpf,"SBBSecho Notify List",cfg.nodecfg[k].faddr,0);
556: fclose(tmpf); }
557: }
558: /******************************************************************************
559: This function creates a netmail to addr showing a list of available areas (0),
560: a list of connected areas (1), or a list of removed areas (2).
561: ******************************************************************************/
562: void netmail_arealist(char type,faddr_t addr)
563: {
564: FILE *stream,*tmpf;
565: char str[256],temp[256],title[81],match,*p;
566: int file,i,j,k,x,y;
567:
568: if(!type)
569: strcpy(title,"List of Available Areas");
570: else if(type==1)
571: strcpy(title,"List of Connected Areas");
572: else
573: strcpy(title,"List of Unlinked Areas");
574:
575: if((tmpf=tmpfile())==NULL) {
576: printf("\7ERROR couldn't open tmpfile.\n");
577: logprintf("ERROR line %d couldn't open tmpfile",__LINE__);
578: return; }
579:
580: if(type==1 || (type!=1 && !(misc&ELIST_ONLY))) {
581: for(i=0;i<cfg.areas;i++) {
582: sprintf(str,"%s\r\n",cfg.area[i].name);
583: if(type) {
584: for(j=0;j<cfg.area[i].uplinks;j++)
585: if(!memcmp(&addr,&cfg.area[i].uplink[j],sizeof(faddr_t)))
586: break;
587: if((type==1 && j<cfg.area[i].uplinks) ||
588: (type==2 && j==cfg.area[i].uplinks))
589: fprintf(tmpf,"%s",str); }
590: else
591: fprintf(tmpf,"%s",str); } }
592:
593: if(!type) {
594: i=matchnode(addr,0);
595: if(i<cfg.nodecfgs) {
596: for(j=0;j<cfg.listcfgs;j++) {
597: match=0;
598: for(k=0;k<cfg.listcfg[j].numflags;k++) {
599: if(match) break;
600: for(x=0;x<cfg.nodecfg[i].numflags;x++)
601: if(!stricmp(cfg.listcfg[j].flag[k].flag
602: ,cfg.nodecfg[i].flag[x].flag)) {
603: if((stream=fnopen(&file
604: ,cfg.listcfg[j].listpath,O_RDONLY))==NULL) {
605: printf("\7ERROR couldn't open %s.\n"
606: ,cfg.listcfg[j].listpath);
607: logprintf("ERROR line %d couldn't open %s %s"
608: ,__LINE__,cfg.listcfg[j].listpath
609: ,sys_errlist[errno]);
610: match=1;
611: break; }
612: while(!feof(stream)) {
613: if(!fgets(str,255,stream))
614: break;
615: truncsp(str);
616: strcat(str,"\r\n");
617: p=str;
618: while(*p && *p<=SP) p++;
619: if(*p==';') /* Ignore Comment Lines */
620: continue;
621: strcpy(temp,p);
622: p=temp;
623: while(*p && *p>SP) p++;
624: *p=0;
625: if(!(misc&ELIST_ONLY)) {
626: for(y=0;y<cfg.areas;y++)
627: if(!stricmp(cfg.area[y].name,temp))
628: break;
629: if(y==cfg.areas)
630: fprintf(tmpf,"%s",str); }
631: else
632: fprintf(tmpf,"%s",str); }
633: fclose(stream);
634: match=1;
635: break; } } } } }
636:
637: if(!ftell(tmpf))
638: create_netmail(0,title,"None.",addr,0);
639: else
640: file_to_netmail(tmpf,title,addr,0);
641: fclose(tmpf);
642: }
643: /******************************************************************************
644: Imitation of Borland's tempnam function because Watcom doesn't have it
645: ******************************************************************************/
646: //#ifdef __WATCOMC__
647: char *tempname(char *dir, char *prefix)
648: {
649: char str[256],*p;
650: int i;
651:
652: for(i=0;i<1000;i++) {
653: sprintf(str,"%s%s%03u.$$$",dir,prefix,i);
654: if(!fexist(str))
655: break; }
656: if(i>=1000) {
657: logprintf("tempnam: too many files");
658: return(NULL); }
659: p=malloc(strlen(str)+1);
660: if(!p) {
661: logprintf("tempnam: couldn't malloc %u",strlen(str)+1);
662: return(NULL); }
663: strcpy(p,str);
664: return(p);
665: }
666: //#endif
667:
668: char check_elists(char *areatag,faddr_t addr)
669: {
670: FILE *stream;
671: char str[1025],quit=0,match=0,*p;
672: int i,j,k,x,file;
673:
674: i=matchnode(addr,0);
675: if(i<cfg.nodecfgs) {
676: for(j=0;j<cfg.listcfgs;j++) {
677: quit=0;
678: for(k=0;k<cfg.listcfg[j].numflags;k++) {
679: if(quit) break;
680: for(x=0;x<cfg.nodecfg[i].numflags;x++)
681: if(!stricmp(cfg.listcfg[j].flag[k].flag
682: ,cfg.nodecfg[i].flag[x].flag)) {
683: if((stream=fnopen(&file
684: ,cfg.listcfg[j].listpath,O_RDONLY))==NULL) {
685: printf("\7ERROR couldn't open %s.\n"
686: ,cfg.listcfg[j].listpath);
687: logprintf("ERROR line %d opening %s"
688: ,__LINE__,cfg.listcfg[j].listpath);
689: quit=1;
690: break; }
691: while(!feof(stream)) {
692: if(!fgets(str,255,stream))
693: break;
694: truncsp(str);
695: strcat(str,"\r\n");
696: p=str;
697: while(*p && *p<=SP) p++;
698: if(*p==';') /* Ignore Comment Lines */
699: continue;
700: strcpy(str,p);
701: p=str;
702: while(*p && *p>SP) p++;
703: *p=0;
704: if(!stricmp(areatag,str)) {
705: match=1;
706: break; } }
707: fclose(stream);
708: quit=1;
709: if(match)
710: return(match);
711: break; } } } }
712: return(match);
713: }
714: /******************************************************************************
715: Used by AREAFIX to add/remove/change areas in the areas file
716: ******************************************************************************/
717: void alter_areas(area_t add_area,area_t del_area,faddr_t addr)
718: {
719: FILE *nmfile,*afilein,*afileout,*reqfile,*fwdfile;
720: char str[1025],fields[1025],field1[81],field2[81],field3[81]
721: ,drive[3],dir[66],name[9],ext[5],outpath[128]
722: ,*outname,*p,*tp,nomatch=0,match=0;
723: int i,j,k,x,y,file;
724: ulong tagcrc;
725:
726: _splitpath(cfg.areafile,drive,dir,name,ext);
727: sprintf(outpath,"%s%s",drive,dir);
728: if((outname=tempname(outpath,"AREAS"))==NULL) {
729: printf("\7ERROR creating temp file name for %s.\n",outpath);
730: logprintf("ERROR tempnam(%s,AREAS)",outpath);
731: return; }
732: if((nmfile=tmpfile())==NULL) {
733: printf("\7ERROR couldn't open NetMail temp file.\n");
734: logprintf("ERROR in tmpfile()");
735: free(outname);
736: return; }
737: if((afileout=fopen(outname,"w+b"))==NULL) {
738: printf("\7ERROR couldn't open %s.\n",outname);
739: logprintf("ERROR line %d opening %s %s",__LINE__,outname
740: ,sys_errlist[errno]);
741: fclose(nmfile);
742: free(outname);
743: return; }
744: if((afilein=fnopen(&file,cfg.areafile,O_RDONLY))==NULL) {
745: printf("\7ERROR couldn't open %s.\n",cfg.areafile);
746: logprintf("ERROR line %d opening %s %s",__LINE__,cfg.areafile
747: ,sys_errlist[errno]);
748: fclose(afileout);
749: fclose(nmfile);
750: free(outname);
751: return; }
752: while(!feof(afilein)) {
753: if(!fgets(fields,1024,afilein))
754: break;
755: truncsp(fields);
756: strcat(fields,"\r\n");
757: p=fields;
758: while(*p && *p<=SP) p++;
759: if(*p==';') { /* Skip Comment Lines */
760: fprintf(afileout,"%s",fields);
761: continue; }
762: sprintf(field1,"%-.81s",p); /* Internal Code Field */
763: tp=field1;
764: while(*tp && *tp>SP) tp++;
765: *tp=0;
766: while(*p && *p>SP) p++;
767: while(*p && *p<=SP) p++;
768: sprintf(field2,"%-.81s",p); /* Areatag Field */
769: tp=field2;
770: while(*tp && *tp>SP) tp++;
771: *tp=0;
772: while(*p && *p>SP) p++;
773: while(*p && *p<=SP) p++;
774: if((tp=strchr(p,';'))!=NULL) {
775: sprintf(field3,"%-.81s",p); /* Comment Field (if any) */
776: while(*tp && *tp>SP) tp++;
777: *tp=0; }
778: else
779: field3[0]=0;
780: if(del_area.tags) { /* Check for areas to remove */
781: for(i=0;i<del_area.tags;i++) {
782: if(!stricmp(del_area.tag[i],field2) ||
783: !stricmp(del_area.tag[0],"-ALL")) /* Match Found */
784: break; }
785: if(i<del_area.tags) {
786: for(i=0;i<cfg.areas;i++) {
787: if(!stricmp(field2,cfg.area[i].name)) {
788: for(j=0;j<cfg.area[i].uplinks;j++)
789: if(!memcmp(&cfg.area[i].uplink[j],&addr
790: ,sizeof(faddr_t)))
791: break;
792: if(j==cfg.area[i].uplinks &&
793: stricmp(del_area.tag[0],"-ALL")) {
794: fprintf(afileout,"%s",fields);
795: fprintf(nmfile,"%s not connected.\r\n",field2);
796: break; }
797:
798: /* Added 12/4/95 to remove uplink from connected uplinks */
799:
800: for(k=j;k<cfg.area[i].uplinks-1;k++)
801: memcpy(&cfg.area[i].uplink[k],&cfg.area[i].uplink[k+1]
802: ,sizeof(faddr_t));
803: --cfg.area[i].uplinks;
804: if((cfg.area[i].uplink=(faddr_t *)
805: REALLOC(cfg.area[i].uplink,sizeof(faddr_t)
806: *(cfg.area[i].uplinks)))==NULL) {
807: printf("ERROR allocating memory for area #%u "
808: "uplinks.\n",i+1);
809: logprintf("ERROR line %d allocating memory for area "
810: "#%u uplinks.\n",__LINE__,i+1);
811: exit(1); }
812:
813: fprintf(afileout,"%-16s%-23s ",field1,field2);
814: for(j=0;j<cfg.area[i].uplinks;j++) {
815: if(!memcmp(&cfg.area[i].uplink[j],&addr
816: ,sizeof(faddr_t)))
817: continue;
818: fprintf(afileout,"%s "
819: ,faddrtoa(cfg.area[i].uplink[j])); }
820: if(field3[0])
821: fprintf(afileout,"%s",field3);
822: fprintf(afileout,"\r\n");
823: fprintf(nmfile,"%s removed.\r\n",field2);
824: break; } }
825: if(i==cfg.areas) /* Something screwy going on */
826: fprintf(afileout,"%s",fields);
827: continue; } } /* Area match so continue on */
828: if(add_area.tags) { /* Check for areas to add */
829: for(i=0;i<add_area.tags;i++)
830: if(!stricmp(add_area.tag[i],field2) ||
831: !stricmp(add_area.tag[0],"+ALL")) /* Match Found */
832: break;
833: if(i<add_area.tags) {
834: if(stricmp(add_area.tag[i],"+ALL"))
835: add_area.tag[i][0]=0; /* So we can check other lists */
836: for(i=0;i<cfg.areas;i++) {
837: if(!stricmp(field2,cfg.area[i].name)) {
838: for(j=0;j<cfg.area[i].uplinks;j++)
839: if(!memcmp(&cfg.area[i].uplink[j],&addr
840: ,sizeof(faddr_t)))
841: break;
842: if(j<cfg.area[i].uplinks) {
843: fprintf(afileout,"%s",fields);
844: fprintf(nmfile,"%s already connected.\r\n",field2);
845: break; }
846: if(misc&ELIST_ONLY && !check_elists(field2,addr)) {
847: fprintf(afileout,"%s",fields);
848: break; }
849:
850: /* Added 12/4/95 to add uplink to connected uplinks */
851:
852: ++cfg.area[i].uplinks;
853: if((cfg.area[i].uplink=(faddr_t *)
854: REALLOC(cfg.area[i].uplink,sizeof(faddr_t)
855: *(cfg.area[i].uplinks)))==NULL) {
856: printf("ERROR allocating memory for area #%u "
857: "uplinks.\n",i+1);
858: logprintf("ERROR line %d allocating memory for area "
859: "#%u uplinks.\n",__LINE__,i+1);
860: exit(1); }
861: memcpy(&cfg.area[i].uplink[j],&addr,sizeof(faddr_t));
862:
863: fprintf(afileout,"%-16s%-23s ",field1,field2);
864: for(j=0;j<cfg.area[i].uplinks;j++)
865: fprintf(afileout,"%s "
866: ,faddrtoa(cfg.area[i].uplink[j]));
867: #if 0 // Removed (02/26/96) rrs
868: fprintf(afileout,"%s ",faddrtoa(addr));
869: #endif
870: if(field3[0])
871: fprintf(afileout,"%s",field3);
872: fprintf(afileout,"\r\n");
873: fprintf(nmfile,"%s added.\r\n",field2);
874: break; } }
875: if(i==cfg.areas) /* Something screwy going on */
876: fprintf(afileout,"%s",fields);
877: continue; } /* Area match so continue on */
878: nomatch=1; } /* This area wasn't in there */
879: fprintf(afileout,"%s",fields); } /* No match so write back line */
880: fclose(afilein);
881: if(nomatch || (add_area.tags && !stricmp(add_area.tag[0],"+ALL"))) {
882: i=matchnode(addr,0);
883: if(i<cfg.nodecfgs) {
884: for(j=0;j<cfg.listcfgs;j++) {
885: match=0;
886: for(k=0;k<cfg.listcfg[j].numflags;k++) {
887: if(match) break;
888: for(x=0;x<cfg.nodecfg[i].numflags;x++)
889: if(!stricmp(cfg.listcfg[j].flag[k].flag
890: ,cfg.nodecfg[i].flag[x].flag)) {
891: if((fwdfile=tmpfile())==NULL) {
892: printf("\7ERROR couldn't open forwarding temp "
893: "file.\n");
894: logprintf("ERROR line %d opening forward temp "
895: "file",__LINE__);
896: match=1;
897: break; }
898: if((afilein=fnopen(&file
899: ,cfg.listcfg[j].listpath,O_RDONLY))==NULL) {
900: printf("\7ERROR couldn't open %s.\n"
901: ,cfg.listcfg[j].listpath);
902: logprintf("ERROR line %d opening %s"
903: ,__LINE__,cfg.listcfg[j].listpath);
904: fclose(fwdfile);
905: match=1;
906: break; }
907: while(!feof(afilein)) {
908: if(!fgets(str,255,afilein))
909: break;
910: truncsp(str);
911: strcat(str,"\r\n");
912: p=str;
913: while(*p && *p<=SP) p++;
914: if(*p==';') /* Ignore Comment Lines */
915: continue;
916: strcpy(str,p);
917: p=str;
918: while(*p && *p>SP) p++;
919: *p=0;
920: if(!stricmp(add_area.tag[0],"+ALL")) {
921: sprintf(fields,"%.1024s",str);
922: tagcrc=crc32(strupr(fields));
923: for(y=0;y<cfg.areas;y++)
924: if(tagcrc==cfg.area[y].tag)
925: break;
926: if(y<cfg.areas)
927: continue; }
928: for(y=0;y<add_area.tags;y++)
929: if((!stricmp(add_area.tag[y],str) &&
930: add_area.tag[y][0]) ||
931: !stricmp(add_area.tag[0],"+ALL"))
932: break;
933: if(y<add_area.tags) {
934: fprintf(afileout,"%-16s%-23s","P",str);
935: if(cfg.listcfg[j].forward.zone)
936: fprintf(afileout," %s"
937: ,faddrtoa(cfg.listcfg[j].forward));
938: fprintf(afileout," %s\r\n",faddrtoa(addr));
939: fprintf(nmfile,"%s added.\r\n",str);
940: if(stricmp(add_area.tag[0],"+ALL"))
941: add_area.tag[y][0]=0;
942: if(!(cfg.listcfg[j].misc&NOFWD)
943: && cfg.listcfg[j].forward.zone)
944: fprintf(fwdfile,"%s\r\n",str); } }
945: fclose(afilein);
946: if(!(cfg.listcfg[j].misc&NOFWD) && ftell(fwdfile)>0)
947: file_to_netmail(fwdfile,cfg.listcfg[j].password
948: ,cfg.listcfg[j].forward,"Areafix");
949: fclose(fwdfile);
950: match=1;
951: break; } } } } }
952: if(add_area.tags && stricmp(add_area.tag[0],"+ALL")) {
953: for(i=0;i<add_area.tags;i++)
954: if(add_area.tag[i][0])
955: fprintf(nmfile,"%s not found.\r\n",add_area.tag[i]); }
956: if(!ftell(nmfile))
957: create_netmail(0,"Area Change Request","No changes made.",addr,0);
958: else
959: file_to_netmail(nmfile,"Area Change Request",addr,0);
960: fclose(nmfile);
961: fclose(afileout);
962: if(delfile(cfg.areafile)) /* Delete AREAS.BBS */
963: logprintf("ERROR line %d removing %s %s",__LINE__,cfg.areafile
964: ,sys_errlist[errno]);
965: if(rename(outname,cfg.areafile)) /* Rename new AREAS.BBS file */
966: logprintf("ERROR line %d renaming %s to %s",__LINE__,outname,cfg.areafile);
967: free(outname);
968: }
969: /******************************************************************************
970: Used by AREAFIX to add/remove/change uplink info in the configuration file
971: old = the old setting for this option, new = what the setting is changing to
972: option = 0 for compression type change
973: 1 for areafix password change
974: 2 to set this node to passive
975: 3 to set this node to active (remove passive)
976: ******************************************************************************/
977: void alter_config(faddr_t addr,char *old,char *new,char option)
978: {
979: FILE *outfile,*cfgfile;
980: char str[257],outpath[128],tmp[257],tmp2[257],*outname,*p,*tp
981: ,drive[3],dir[66],name[9],ext[5],match=0;
982: int i,j,k,file;
983: faddr_t taddr;
984:
985: i=matchnode(addr,0); /* i = config number from here on */
986: _splitpath(cfg.cfgfile,drive,dir,name,ext);
987: sprintf(outpath,"%s%s",drive,dir);
988: if((outname=tempname(outpath,"CFG"))==NULL) {
989: printf("\7ERROR creating temporary file name for %s.\n",outpath);
990: logprintf("ERROR tempnam(%s,CFG)",outpath);
991: return; }
992: if((outfile=fopen(outname,"w+b"))==NULL) {
993: printf("\7ERROR couldn't open %s.\n",outname);
994: logprintf("ERROR line %d opening %s %s",__LINE__,outname
995: ,sys_errlist[errno]);
996: free(outname);
997: return; }
998: if((cfgfile=fnopen(&file,cfg.cfgfile,O_RDONLY))==NULL) {
999: printf("\7ERROR couldn't open %s.\n",cfg.cfgfile);
1000: logprintf("ERROR line %d opening %s",__LINE__,cfg.cfgfile
1001: ,sys_errlist[errno]);
1002: fclose(outfile);
1003: free(outname);
1004: return; }
1005:
1006: while(!feof(cfgfile)) {
1007: if(!fgets(str,256,cfgfile))
1008: break;
1009: truncsp(str);
1010: p=str;
1011: while(*p && *p<=SP) p++;
1012: if(*p==';') {
1013: fprintf(outfile,"%s\r\n",str);
1014: continue; }
1015: sprintf(tmp,"%-.25s",p);
1016: tp=strchr(tmp,SP);
1017: if(tp)
1018: *tp=0; /* Chop off at space */
1019: strupr(tmp); /* Convert code to uppercase */
1020: while(*p>SP) p++; /* Skip code */
1021: while(*p && *p<=SP) p++; /* Skip white space */
1022:
1023: if(option==0 && !strcmp(tmp,"USEPACKER")) { /* Change Compression */
1024: if(!*p)
1025: continue;
1026: strcpy(tmp2,p);
1027: p=tmp2;
1028: while(*p && *p>SP) p++;
1029: *p=0;
1030: p++;
1031: if(!stricmp(new,tmp2)) { /* Add to new definition */
1032: fprintf(outfile,"%-10s %s %s %s\r\n",tmp,tmp2
1033: ,faddrtoa(cfg.nodecfg[i].faddr)
1034: ,(*p) ? p : "");
1035: match=1;
1036: continue; }
1037: else if(!stricmp(old,tmp2)) { /* Remove from old def */
1038: for(j=k=0;j<cfg.nodecfgs;j++) {
1039: if(j==i)
1040: continue;
1041: if(!stricmp(cfg.arcdef[cfg.nodecfg[j].arctype].name,tmp2)) {
1042: if(!k) {
1043: fprintf(outfile,"%-10s %s",tmp,tmp2);
1044: k++; }
1045: fprintf(outfile," %s"
1046: ,faddrtoa(cfg.nodecfg[j].faddr)); } }
1047: fprintf(outfile,"\r\n");
1048: continue; } }
1049:
1050: if(option==1 && !strcmp(tmp,"AREAFIX")) { /* Change Password */
1051: if(!*p)
1052: continue;
1053: taddr=atofaddr(p);
1054: if(!memcmp(&cfg.nodecfg[i].faddr,&taddr,sizeof(faddr_t))) {
1055: while(*p && *p>SP) p++; /* Skip over address */
1056: while(*p && *p<=SP) p++; /* Skip over whitespace */
1057: while(*p && *p>SP) p++; /* Skip over password */
1058: while(*p && *p<=SP) p++; /* Skip over whitespace */
1059: fprintf(outfile,"%-10s %s %s %s\r\n",tmp
1060: ,faddrtoa(cfg.nodecfg[i].faddr),new,p);
1061: continue; } }
1062:
1063: if(option>1 && !strcmp(tmp,"PASSIVE")) { /* Toggle Passive Areas */
1064: match=1;
1065: for(j=k=0;j<cfg.nodecfgs;j++) {
1066: if(option==2 && j==i) {
1067: if(!k) fprintf(outfile,"%-10s",tmp);
1068: fprintf(outfile," %s",faddrtoa(cfg.nodecfg[j].faddr));
1069: k++;
1070: continue; }
1071: if(option==3 && j==i)
1072: continue;
1073: if(cfg.nodecfg[j].attr&ATTR_PASSIVE) {
1074: if(!k) fprintf(outfile,"%-10s",tmp);
1075: fprintf(outfile," %s",faddrtoa(cfg.nodecfg[j].faddr));
1076: k++; } }
1077: if(k) fprintf(outfile,"\r\n");
1078: continue; }
1079: fprintf(outfile,"%s\r\n",str); }
1080:
1081: if(!match) {
1082: if(option==0)
1083: fprintf(outfile,"%-10s %s %s\r\n","USEPACKER",new
1084: ,faddrtoa(cfg.nodecfg[i].faddr));
1085: if(option==2)
1086: fprintf(outfile,"%-10s %s\r\n","PASSIVE"
1087: ,faddrtoa(cfg.nodecfg[i].faddr)); }
1088:
1089: fclose(cfgfile);
1090: fclose(outfile);
1091: if(delfile(cfg.cfgfile))
1092: logprintf("ERROR line %d removing %s %s",__LINE__,cfg.cfgfile
1093: ,sys_errlist[errno]);
1094: if(rename(outname,cfg.cfgfile))
1095: logprintf("ERROR line %d renaming %s to %s",__LINE__,outname,cfg.cfgfile);
1096: free(outname);
1097: }
1098: /******************************************************************************
1099: Used by AREAFIX to process any '%' commands that come in via netmail
1100: ******************************************************************************/
1101: void command(char *instr,faddr_t addr)
1102: {
1103: FILE *stream,*tmpf;
1104: char str[256],temp[256],match,*buf,*p;
1105: int file,i,j,node;
1106: long l;
1107: area_t add_area,del_area;
1108:
1109: node=matchnode(addr,0);
1110: if(node==cfg.nodecfgs)
1111: return;
1112: memset(&add_area,0,sizeof(area_t));
1113: memset(&del_area,0,sizeof(area_t));
1114: strupr(instr);
1115: if((p=strstr(instr,"HELP"))!=NULL) {
1116: sprintf(str,"%s%sAREAMGR.HLP",(exec_dir[0]=='.') ? node_dir:"",exec_dir);
1117: if(!fexist(str))
1118: return;
1119: if((stream=fnopen(&file,str,O_RDONLY))==NULL) {
1120: printf("\7ERROR couldn't open %s.\n",str);
1121: logprintf("ERROR line %d opening %s %s",__LINE__,str
1122: ,sys_errlist[errno]);
1123: return; }
1124: l=filelength(file);
1125: if((buf=(char *)LMALLOC(l+1L))==NULL) {
1126: printf("ERROR line %d allocating %lu bytes for %s\n",__LINE__,l,str);
1127: return; }
1128: fread(buf,l,1,stream);
1129: fclose(stream);
1130: buf[l]=0;
1131: create_netmail(0,"Area Manager Help",buf,addr,0);
1132: LFREE(buf);
1133: return; }
1134:
1135: if((p=strstr(instr,"LIST"))!=NULL) {
1136: netmail_arealist(0,addr);
1137: return; }
1138:
1139: if((p=strstr(instr,"QUERY"))!=NULL) {
1140: netmail_arealist(1,addr);
1141: return; }
1142:
1143: if((p=strstr(instr,"UNLINKED"))!=NULL) {
1144: netmail_arealist(2,addr);
1145: return; }
1146:
1147: if((p=strstr(instr,"COMPRESSION"))!=NULL) {
1148: while(*p && *p>SP) p++;
1149: while(*p && *p<=SP) p++;
1150: for(i=0;i<cfg.arcdefs;i++)
1151: if(!stricmp(p,cfg.arcdef[i].name))
1152: break;
1153: if(!stricmp(p,"NONE"))
1154: i=0xffff;
1155: if(i==cfg.arcdefs) {
1156: if((tmpf=tmpfile())==NULL) {
1157: printf("\7ERROR couldn't open tmpfile.\n");
1158: logprintf("ERROR line %d opening tmpfile()",__LINE__);
1159: return; }
1160: fprintf(tmpf,"Compression type unavailable.\r\n\r\n"
1161: "Available types are:\r\n");
1162: for(i=0;i<cfg.arcdefs;i++)
1163: fprintf(tmpf," %s\r\n",cfg.arcdef[i].name);
1164: file_to_netmail(tmpf,"Compression Type Change",addr,0);
1165: fclose(tmpf);
1166: LFREE(buf);
1167: return; }
1168: alter_config(addr,cfg.arcdef[cfg.nodecfg[node].arctype].name
1169: ,cfg.arcdef[i].name,0);
1170: cfg.nodecfg[node].arctype=i;
1171: sprintf(str,"Compression type changed to %s.",cfg.arcdef[i].name);
1172: create_netmail(0,"Compression Type Change",str,addr,0);
1173: return; }
1174:
1175: if((p=strstr(instr,"PASSWORD"))!=NULL) {
1176: while(*p && *p>SP) p++;
1177: while(*p && *p<=SP) p++;
1178: sprintf(temp,"%-.25s",p);
1179: p=temp;
1180: while(*p && *p>SP) p++;
1181: *p=0;
1182: if(node==cfg.nodecfgs) /* Should never happen */
1183: return;
1184: if(!stricmp(temp,cfg.nodecfg[node].password)) {
1185: sprintf(str,"Your password was already set to %s."
1186: ,cfg.nodecfg[node].password);
1187: create_netmail(0,"Password Change Request",str,addr,0);
1188: return; }
1189: alter_config(addr,cfg.nodecfg[node].password,temp,1);
1190: sprintf(str,"Your password has been changed from %s to %.25s."
1191: ,cfg.nodecfg[node].password,temp);
1192: sprintf(cfg.nodecfg[node].password,"%.25s",temp);
1193: create_netmail(0,"Password Change Request",str,addr,0);
1194: return; }
1195:
1196: if((p=strstr(instr,"RESCAN"))!=NULL) {
1197: export_echomail("",addr);
1198: create_netmail(0,"Rescan Areas"
1199: ,"All connected areas carried by your hub have been rescanned."
1200: ,addr,0);
1201: return; }
1202:
1203: if((p=strstr(instr,"ACTIVE"))!=NULL) {
1204: if(!(cfg.nodecfg[node].attr&ATTR_PASSIVE)) {
1205: create_netmail(0,"Reconnect Disconnected Areas"
1206: ,"Your areas are already connected.",addr,0);
1207: return; }
1208: alter_config(addr,0,0,3);
1209: create_netmail(0,"Reconnect Disconnected Areas"
1210: ,"Temporarily disconnected areas have been reconnected.",addr,0);
1211: return; }
1212:
1213: if((p=strstr(instr,"PASSIVE"))!=NULL) {
1214: if(cfg.nodecfg[node].attr&ATTR_PASSIVE) {
1215: create_netmail(0,"Temporarily Disconnect Areas"
1216: ,"Your areas are already temporarily disconnected.",addr,0);
1217: return; }
1218: alter_config(addr,0,0,2);
1219: create_netmail(0,"Temporarily Disconnect Areas"
1220: ,"Your areas have been temporarily disconnected.",addr,0);
1221: return; }
1222:
1223: if((p=strstr(instr,"FROM"))!=NULL);
1224:
1225: if((p=strstr(instr,"+ALL"))!=NULL) {
1226: if((add_area.tag=(char **)REALLOC(add_area.tag
1227: ,sizeof(char *)*add_area.tags+1))==NULL) {
1228: printf("ERROR allocating memory for add area tag #%u.\n"
1229: ,add_area.tags+1);
1230: logprintf("ERROR line %d allocating memory for add area tag #%u"
1231: ,__LINE__,add_area.tags+1);
1232: exit(1); }
1233: if((add_area.tag[add_area.tags]=(char *)LMALLOC(strlen(instr)+1))==NULL) {
1234: printf("ERROR allocating memory for add area tag #%u.\n"
1235: ,add_area.tags+1);
1236: logprintf("ERROR line %d allocating memory for add area tag #%u"
1237: ,__LINE__,add_area.tags+1);
1238: exit(1); }
1239: strcpy(add_area.tag[add_area.tags],instr);
1240: add_area.tags++;
1241: alter_areas(add_area,del_area,addr);
1242: for(i=0;i<add_area.tags;i++)
1243: LFREE(add_area.tag[i]);
1244: FREE(add_area.tag);
1245: return; }
1246:
1247: if((p=strstr(instr,"-ALL"))!=NULL) {
1248: if((del_area.tag=(char **)REALLOC(del_area.tag
1249: ,sizeof(char *)*del_area.tags+1))==NULL) {
1250: printf("ERROR allocating memory for del area tag #%u.\n"
1251: ,del_area.tags+1);
1252: logprintf("ERROR line %d allocating memory for del area tag #%u"
1253: ,__LINE__,del_area.tags+1);
1254: exit(1); }
1255: if((del_area.tag[del_area.tags]=(char *)LMALLOC(strlen(instr)+1))==NULL) {
1256: printf("ERROR allocating memory for del area tag #%u.\n"
1257: ,del_area.tags+1);
1258: logprintf("ERROR line %d allocating memory for del area tag #%u"
1259: ,__LINE__,del_area.tags+1);
1260: exit(1); }
1261: strcpy(del_area.tag[del_area.tags],instr);
1262: del_area.tags++;
1263: alter_areas(add_area,del_area,addr);
1264: for(i=0;i<del_area.tags;i++)
1265: LFREE(del_area.tag[i]);
1266: FREE(del_area.tag);
1267: return; }
1268: }
1269: /******************************************************************************
1270: This is where we're gonna process any netmail that comes in for areafix.
1271: Returns text for message body for the local sysop if necessary.
1272: ******************************************************************************/
1273: char *process_areafix(faddr_t addr,char HUGE16 *inbuf,char *password)
1274: {
1275: static char body[512],str[81];
1276: char *p,*tp,action,percent=0;
1277: int i;
1278: ulong l,m;
1279: area_t add_area,del_area;
1280:
1281: p=(char *)inbuf;
1282:
1283: while(*p==1) { /* Skip kludge lines 11/05/95 */
1284: while(*p && *p!=CR)
1285: p++; /* Skip meat */
1286: if(*p)
1287: p++; } /* Skip CR */
1288:
1289: #if 0 // Removed 11/05/95
1290: while(*p && (tp=strchr(p,'\1'))!=NULL) { /* Remove ^A kludge lines */
1291: p=tp;
1292: while(*p && *p!=CR) p++; }
1293: if(*p==CR)
1294: p++;
1295: #endif
1296:
1297: if(((tp=strstr(p,"---\r"))!=NULL || (tp=strstr(p,"--- "))!=NULL) &&
1298: (*(tp-1)==10 || *(tp-1)==13))
1299: *tp=0;
1300:
1301: if(!strnicmp(p,"%FROM",5)) { /* Remote Remote Maintenance (must be first) */
1302: sprintf(str,"%.80s",p+6);
1303: if((tp=strchr(str,CR))!=NULL)
1304: *tp=0;
1305: logprintf("Remote maintenance for %s requested via %s",str,faddrtoa(addr));
1306: addr=atofaddr(str); }
1307:
1308: i=matchnode(addr,0);
1309: if(i==cfg.nodecfgs) {
1310: sprintf(body,"Your node is not configured for Areafix, please "
1311: "contact your hub.\r\n");
1312: create_netmail(0,"Areafix Request",body,addr,0);
1313: sprintf(body,"An areafix request was made by node %s.\r\nThis node "
1314: "is not currently configured for areafix.\r\n",faddrtoa(addr));
1315: return(body); }
1316:
1317: if(stricmp(cfg.nodecfg[i].password,password)) {
1318: create_netmail(0,"Areafix Request","Invalid Password.",addr,0);
1319: sprintf(body,"Node %s attempted an areafix request using an invalid "
1320: "password.\r\nThe password attempted was %s.\r\nThe correct password "
1321: "for this node is %s.\r\n",faddrtoa(addr),password
1322: ,(cfg.nodecfg[i].password[0]) ? cfg.nodecfg[i].password
1323: : "[None Defined]");
1324: return(body); }
1325:
1326: m=strlen(p);
1327: add_area.tags=0;
1328: add_area.tag=NULL;
1329: del_area.tags=0;
1330: del_area.tag=NULL;
1331: for(l=0;l<m;l++) {
1332: while(*(p+l) && *(p+l)<=SP) l++;
1333: if(!(*(p+l))) break;
1334: if(*(p+l)=='+' || *(p+l)=='-' || *(p+l)=='%') {
1335: action=*(p+l);
1336: l++; }
1337: else
1338: action='+';
1339: sprintf(str,"%.80s",p+l);
1340: if((tp=strchr(str,CR))!=NULL)
1341: *tp=0;
1342: switch(action) {
1343: case '+': /* Add Area */
1344: if((add_area.tag=(char **)REALLOC(add_area.tag
1345: ,sizeof(char *)*add_area.tags+1))==NULL) {
1346: printf("ERROR allocating memory for add area tag #%u.\n"
1347: ,add_area.tags+1);
1348: logprintf("ERROR line %d allocating memory for add area "
1349: "tag #%u",__LINE__,add_area.tags+1);
1350: exit(1); }
1351: if((add_area.tag[add_area.tags]=(char *)LMALLOC(strlen(str)+1))
1352: ==NULL) {
1353: printf("ERROR allocating memory for add area tag #%u.\n"
1354: ,add_area.tags+1);
1355: logprintf("ERROR line %d allocating memory for add area "
1356: "tag #%u",__LINE__,add_area.tags+1);
1357: exit(1); }
1358: strcpy(add_area.tag[add_area.tags],str);
1359: add_area.tags++;
1360: break;
1361: case '-': /* Remove Area */
1362: if((del_area.tag=(char **)REALLOC(del_area.tag
1363: ,sizeof(char *)*del_area.tags+1))==NULL) {
1364: printf("ERROR allocating memory for del area tag #%u.\n"
1365: ,del_area.tags+1);
1366: logprintf("ERROR line %d allocating memory for del area "
1367: "tag #%u",__LINE__,del_area.tags+1);
1368: exit(1); }
1369: if((del_area.tag[del_area.tags]=(char *)LMALLOC(strlen(str)+1))
1370: ==NULL) {
1371: printf("ERROR allocating memory for del area tag #%u.\n"
1372: ,del_area.tags+1);
1373: logprintf("ERROR line %d allocating memory for del area "
1374: "tag #%u",__LINE__,del_area.tags+1);
1375: exit(1); }
1376: strcpy(del_area.tag[del_area.tags],str);
1377: del_area.tags++;
1378: break;
1379: case '%': /* Process Command */
1380: command(str,addr);
1381: percent++;
1382: break; }
1383:
1384: while(*(p+l) && *(p+l)!=CR) l++; }
1385:
1386: if(!percent && !add_area.tags && !del_area.tags) {
1387: create_netmail(0,"Areafix Request","No commands to process.",addr,0);
1388: sprintf(body,"Node %s attempted an areafix request with an empty message "
1389: "body or with no valid commands.\r\n",faddrtoa(addr));
1390: return(body); }
1391: if(add_area.tags || del_area.tags)
1392: alter_areas(add_area,del_area,addr);
1393: if(add_area.tags) {
1394: for(i=0;i<add_area.tags;i++)
1395: LFREE(add_area.tag[i]);
1396: FREE(add_area.tag); }
1397: if(del_area.tags) {
1398: for(i=0;i<del_area.tags;i++)
1399: LFREE(del_area.tag[i]);
1400: FREE(del_area.tag); }
1401: return(0);
1402: }
1403: /******************************************************************************
1404: This function will compare the archive signatures defined in the CFG file and
1405: extract 'infile' using the appropriate de-archiver.
1406: ******************************************************************************/
1407: int unpack(char *infile)
1408: {
1409: FILE *stream;
1410: char str[256],tmp[3];
1411: int i,j,k,ch,file;
1412:
1413: if((stream=fnopen(&file,infile,O_RDONLY))==NULL) {
1414: printf("\7ERROR couldn't open %s.\n",infile);
1415: logprintf("ERROR line %d opening %s %s",__LINE__,infile
1416: ,sys_errlist[errno]);
1417: exit(1); }
1418: for(i=0;i<cfg.arcdefs;i++) {
1419: str[0]=0;
1420: fseek(stream,cfg.arcdef[i].byteloc,SEEK_SET);
1421: for(j=0;j<strlen(cfg.arcdef[i].hexid)/2;j++) {
1422: ch=fgetc(stream);
1423: if(ch==EOF) {
1424: i=cfg.arcdefs;
1425: break; }
1426: sprintf(tmp,"%02X",ch);
1427: strcat(str,tmp); }
1428: if(!stricmp(str,cfg.arcdef[i].hexid))
1429: break; }
1430: fclose(stream);
1431:
1432: if(i==cfg.arcdefs) {
1433: printf("\7ERROR couldn't determine filetype of %s.\n",infile);
1434: logprintf("ERROR line %d determining filetype of %s",__LINE__,infile);
1435: return(1); }
1436:
1437: j=execute(cmdstr(cfg.arcdef[i].unpack,infile
1438: ,secure ? cfg.secure : cfg.inbound));
1439: if(j) {
1440: printf("\7ERROR %d (%d) executing %s\n"
1441: ,j,errno,cmdstr(cfg.arcdef[i].unpack,infile
1442: ,secure ? cfg.secure : cfg.inbound));
1443: logprintf("ERROR %d (%d) line %d executing %s"
1444: ,j,errno,__LINE__,cmdstr(cfg.arcdef[i].unpack,infile
1445: ,secure ? cfg.secure : cfg.inbound));
1446: return(j); }
1447: return(0);
1448: }
1449: /******************************************************************************
1450: This function will check the 'dest' for the type of archiver to use (as
1451: defined in the CFG file) and compress 'srcfile' into 'destfile' using the
1452: appropriate archive program.
1453: ******************************************************************************/
1454: void pack(char *srcfile,char *destfile,faddr_t dest)
1455: {
1456: int i,j;
1457: uint use=0;
1458:
1459: i=matchnode(dest,0);
1460: if(i<cfg.nodecfgs)
1461: use=cfg.nodecfg[i].arctype;
1462:
1463: j=execute(cmdstr(cfg.arcdef[use].pack,destfile,srcfile));
1464: if(j) {
1465: printf("\7ERROR %d (%d) executing %s\n"
1466: ,j,errno,cmdstr(cfg.arcdef[use].pack,destfile,srcfile));
1467: logprintf("ERROR %d (%d) line %d executing %s"
1468: ,j,errno,__LINE__,cmdstr(cfg.arcdef[use].pack,destfile,srcfile)); }
1469: }
1470:
1471: char attachment(char *bundlename,faddr_t dest,char cleanup)
1472: {
1473: FILE *fidomsg,*stream;
1474: char str[1025],path[512],fname[129],*p;
1475: int last,fmsg,file,error=0L;
1476: long fncrc,*mfncrc=0L,num_mfncrc=0L;
1477: struct find_t ff;
1478: attach_t attach;
1479: fmsghdr_t hdr;
1480:
1481: sprintf(fname,"%sBUNDLES.SBE",cfg.outbound);
1482: if((stream=fnopen(&file,fname,O_RDWR|O_CREAT))==NULL) {
1483: printf("\7ERROR opening %s %s\n",fname,sys_errlist[errno]);
1484: logprintf("ERROR line %d opening %s %s",__LINE__,fname,sys_errlist[errno]);
1485: return(1); }
1486:
1487: if(cleanup==2) { /* Check for existance in BUNDLES.SBE */
1488: while(!feof(stream)) {
1489: if(!fread(&attach,1,sizeof(attach_t),stream))
1490: break;
1491: if(!stricmp(attach.fname,bundlename)) {
1492: fclose(stream);
1493: return(1); } }
1494: fclose(stream);
1495: return(0); }
1496:
1497: if(cleanup==1) { /* Create netmail attaches */
1498:
1499: if(!filelength(file)) {
1500: fclose(stream);
1501: return(0); }
1502: /* Get attach names from existing MSGs */
1503: sprintf(str,"%s*.MSG",netmail_dir);
1504: for(last=_dos_findfirst(str,0,&ff);!last;last=_dos_findnext(&ff)) {
1505: sprintf(path,"%s%s",netmail_dir,ff.name);
1506: strupr(path);
1507: if((fidomsg=fnopen(&fmsg,path,O_RDWR))==NULL) {
1508: printf("\7ERROR opening %s\n",path);
1509: logprintf("ERROR line %d opening %s %s",__LINE__,path
1510: ,sys_errlist[errno]);
1511: continue; }
1512: if(filelength(fmsg)<sizeof(fmsghdr_t)) {
1513: printf("\7ERROR %s has invalid length of %u bytes\n",path
1514: ,filelength(fmsg));
1515: logprintf("ERROR line %d %s has invalid length of %u bytes"
1516: ,__LINE__,path,filelength(fmsg));
1517: fclose(fidomsg);
1518: continue; }
1519: if(fread(&hdr,sizeof(fmsghdr_t),1,fidomsg)!=1) {
1520: fclose(fidomsg);
1521: printf("\7ERROR reading %u bytes from %s"
1522: ,sizeof(fmsghdr_t),path);
1523: logprintf("ERROR line %d reading %u bytes from %s"
1524: ,__LINE__,sizeof(fmsghdr_t),path);
1525: continue; }
1526: fclose(fidomsg);
1527: if(!(hdr.attr&FIDO_FILE)) /* Not a file attach */
1528: continue;
1529: num_mfncrc++;
1530: if((p=strrchr(hdr.subj,'\\'))!=NULL)
1531: p++;
1532: else
1533: p=hdr.subj;
1534: if((mfncrc=(long *)REALLOC(mfncrc,num_mfncrc*sizeof(long)))==NULL) {
1535: printf("ERROR allocating %lu bytes for bundle name crc.\n"
1536: ,num_mfncrc*sizeof(long));
1537: logprintf("ERROR line %d allocating %lu for bundle name crc"
1538: ,__LINE__,num_mfncrc*sizeof(long));
1539: continue; }
1540: mfncrc[num_mfncrc-1]=crc32(strupr(p)); }
1541:
1542: while(!feof(stream)) {
1543: if(!fread(&attach,1,sizeof(attach_t),stream))
1544: break;
1545: sprintf(str,"%s%s",cfg.outbound,attach.fname);
1546: if(!fexist(str))
1547: continue;
1548: fncrc=crc32(strupr(attach.fname));
1549: for(last=0;last<num_mfncrc;last++)
1550: if(mfncrc[last]==fncrc)
1551: break;
1552: if(last==num_mfncrc)
1553: if(create_netmail(0,str,"\1FLAGS KFS\r",attach.dest,1))
1554: error=1; }
1555: if(!error) /* don't truncate if an error occured */
1556: chsize(file,0L);
1557: fclose(stream);
1558: if(num_mfncrc)
1559: FREE(mfncrc);
1560: #ifdef __WATCOMC__
1561: _dos_findclose(&ff);
1562: #endif
1563: return(0); }
1564:
1565: while(!feof(stream)) {
1566: if(!fread(&attach,1,sizeof(attach_t),stream))
1567: break;
1568: if(!stricmp(attach.fname,bundlename)) {
1569: fclose(stream);
1570: return(0); } }
1571:
1572: memcpy(&attach.dest,&dest,sizeof(faddr_t));
1573: strcpy(attach.fname,bundlename);
1574: fwrite(&attach,sizeof(attach_t),1,stream);
1575: fclose(stream);
1576: return(0);
1577: }
1578:
1579: /******************************************************************************
1580: This function is called when a message packet has reached it's maximum size.
1581: It places packets into a bundle until that bundle is full, at which time the
1582: last character of the extension increments (1 thru 0 and then A thru Z). If
1583: all bundles have reached their maximum size remaining packets are placed into
1584: the Z bundle.
1585: ******************************************************************************/
1586: void pack_bundle(char *infile,faddr_t dest)
1587: {
1588: char str[256],fname[256],outbound[128],day[3],ch,*p;
1589: int i,j,file,node;
1590: time_t now;
1591:
1592: node=matchnode(dest,0);
1593: strcpy(str,infile);
1594: str[strlen(str)-1]='T';
1595: if(rename(infile,str)) /* Change .PK_ file to .PKT file */
1596: logprintf("ERROR line %d renaming %s to %s",__LINE__,infile,str);
1597: infile[strlen(infile)-1]='T';
1598: time(&now);
1599: sprintf(day,"%-.2s",ctime(&now));
1600: strupr(day);
1601: if(misc&FLO_MAILER) {
1602: if(node<cfg.nodecfgs && cfg.nodecfg[node].route.zone)
1603: dest=cfg.nodecfg[node].route;
1604: if(dest.zone==faddr[0].zone) /* Default zone, use default outbound */
1605: strcpy(outbound,cfg.outbound);
1606: else /* Inter-zone outbound is OUTBOUND.XXX */
1607: sprintf(outbound,"%.*s.%03X\\"
1608: ,strlen(cfg.outbound)-1,cfg.outbound,dest.zone);
1609: if(dest.point) { /* Point destination is OUTBOUND\*.PNT */
1610: sprintf(str,"%04X%04X.PNT"
1611: ,dest.net,dest.node);
1612: strcat(outbound,str); }
1613: }
1614: else
1615: strcpy(outbound,cfg.outbound);
1616: if(outbound[strlen(outbound)-1]=='\\')
1617: outbound[strlen(outbound)-1]=0;
1618: mkdir(outbound);
1619: strcat(outbound,"\\");
1620:
1621: if(node<cfg.nodecfgs)
1622: if(cfg.nodecfg[node].arctype==0xffff) { /* Uncompressed! */
1623: if(misc&FLO_MAILER)
1624: i=write_flofile(infile,dest);
1625: else
1626: i=create_netmail(0,infile,"\1FLAGS KFS\r",dest,1);
1627: if(i) exit(1);
1628: return; }
1629:
1630: sprintf(fname,"%s%04hX%04hX.%s",outbound,(short)(faddr[0].net-dest.net)
1631: ,(short)(faddr[0].node-dest.node),day);
1632: if(dest.point && !(misc&FLO_MAILER))
1633: sprintf(fname,"%s%04hXP%03hX.%s",outbound,0,(short)dest.point,day);
1634: for(i='0';i<='Z';i++) {
1635: if(i==':')
1636: i='A';
1637: sprintf(str,"%s%c",fname,i);
1638: if(flength(str)==0)
1639: if(delfile(str))
1640: logprintf("ERROR line %d removing %s %s",__LINE__,str
1641: ,sys_errlist[errno]);
1642: if(fexist(str)) {
1643: if((p=strrchr(str,'\\'))!=NULL)
1644: p++;
1645: else
1646: p=str;
1647: if(flength(str)>=cfg.maxbdlsize)
1648: continue;
1649: file=sopen(str,O_WRONLY,SH_DENYRW);
1650: if(file==-1) /* Can't open?!? Probably being sent */
1651: continue;
1652: close(file);
1653: if(!attachment(p,dest,2))
1654: attachment(p,dest,0);
1655: pack(infile,str,dest);
1656: if(delfile(infile))
1657: logprintf("ERROR line %d removing %s %s",__LINE__,infile
1658: ,sys_errlist[errno]);
1659: return; }
1660: else {
1661: if(misc&FLO_MAILER)
1662: j=write_flofile(str,dest);
1663: else {
1664: if((p=strrchr(str,'\\'))!=NULL)
1665: p++;
1666: else
1667: p=str;
1668: j=attachment(p,dest,0); }
1669: if(j)
1670: exit(1);
1671: pack(infile,str,dest);
1672: if(delfile(infile))
1673: logprintf("ERROR line %d removing %s %s",__LINE__,infile
1674: ,sys_errlist[errno]);
1675: return; } }
1676:
1677: pack(infile,str,dest); /* Won't get here unless all bundles are full */
1678: }
1679:
1680: /******************************************************************************
1681: This function checks the inbound directory for the first bundle it finds, it
1682: will then unpack and delete the bundle. If no bundles exist this function
1683: returns a 0, otherwise a 1 is returned.
1684: ******************************************************************************/
1685: int unpack_bundle(void)
1686: {
1687: char str[256];
1688: static char fname[256];
1689: int i,j;
1690: static struct find_t ff;
1691:
1692: for(i=0;i<7;i++) {
1693: sprintf(str,"%s*.%s?",secure ? cfg.secure : cfg.inbound
1694: ,(i==0) ? "SU" : (i==1) ? "MO" : (i==2) ? "TU" : (i==3) ? "WE" : (i==4)
1695: ? "TH" : (i==5) ? "FR" : "SA");
1696: if(!ff.name[0])
1697: j=_dos_findfirst(str,0,&ff);
1698: else {
1699: j=_dos_findnext(&ff);
1700: if(j) {
1701: #ifdef __WATCOMC__
1702: _dos_findclose(&ff);
1703: #endif
1704: j=_dos_findfirst(str,0,&ff); } }
1705: if(!j) {
1706: sprintf(fname,"%s%s",secure ? cfg.secure : cfg.inbound,ff.name);
1707: if(unpack(fname)) {
1708: if((ddtol(ff.wr_time,ff.wr_date)+(48L*60L*60L))>time(NULL)) {
1709: strcpy(str,fname);
1710: str[strlen(str)-2]='_';
1711: if(fexist(str))
1712: str[strlen(str)-2]='-';
1713: if(fexist(str))
1714: delfile(str);
1715: if(rename(fname,str))
1716: logprintf("ERROR line %d renaming %s to %s"
1717: ,__LINE__,fname,str); } }
1718: else if(delfile(fname))
1719: logprintf("ERROR line %d removing %s %s",__LINE__,fname
1720: ,sys_errlist[errno]);
1721: return(1); } }
1722:
1723: #ifdef __WATCOMC__
1724: _dos_findclose(&ff);
1725: #endif
1726: return(0);
1727: }
1728:
1729:
1730: /******************************************************************************
1731: Displays characters locally
1732: ******************************************************************************/
1733: long lputs(char *str)
1734: {
1735: char tmp[256];
1736: int i,j,k;
1737:
1738:
1739: j=strlen(str);
1740: for(i=k=0;i<j;i++) /* remove CRs */
1741: if(str[i]==CR && str[i+1]==LF)
1742: continue;
1743: else
1744: tmp[k++]=str[i];
1745: tmp[k]=0;
1746: return(fputs(tmp,stdout));
1747: }
1748:
1749: /******************************************/
1750: /* CRC-16 routines required for SMB index */
1751: /******************************************/
1752:
1753: /***********************************************)**********************)*****/
1754: /* Updates 16-bit "rcrc" with character 'ch' */
1755: /****************************************************************************/
1756: void ucrc16(uchar ch, ushort *rcrc) {
1757: ushort i, cy;
1758: uchar nch=ch;
1759:
1760: for (i=0; i<8; i++) {
1761: cy=*rcrc & 0x8000;
1762: *rcrc<<=1;
1763: if (nch & 0x80) *rcrc |= 1;
1764: nch<<=1;
1765: if (cy) *rcrc ^= 0x1021; }
1766: }
1767:
1768: /****************************************************************************/
1769: /* Returns 16-crc of string (not counting terminating NULL) */
1770: /****************************************************************************/
1771: ushort crc16(char *str)
1772: {
1773: int i=0;
1774: ushort crc=0;
1775:
1776: ucrc16(0,&crc);
1777: while(str[i])
1778: ucrc16(str[i++],&crc);
1779: ucrc16(0,&crc);
1780: ucrc16(0,&crc);
1781: return(crc);
1782: }
1783:
1784: /****************************************************************************/
1785: /* Performs printf() through local assembly routines */
1786: /* Called from everywhere */
1787: /****************************************************************************/
1788: int lprintf(char *fmat, ...)
1789: {
1790: va_list argptr;
1791: char sbuf[256];
1792: int chcount;
1793:
1794: va_start(argptr,fmat);
1795: chcount=vsprintf(sbuf,fmat,argptr);
1796: va_end(argptr);
1797: lputs(sbuf);
1798: return(chcount);
1799: }
1800:
1801: /****************************************************************************/
1802: /* Reads the data for node number 'number' into the structure 'node' */
1803: /* from NODE.DAB */
1804: /* if lockit is non-zero, locks this node's record. putnodedat() unlocks it */
1805: /****************************************************************************/
1806: void getnodedat(uint number, node_t *node, char lockit)
1807: {
1808: char str[256];
1809: int count=0;
1810:
1811: number--; /* make zero based */
1812: while(count<LOOP_NODEDAB) {
1813: lseek(nodefile,(long)number*sizeof(node_t),SEEK_SET);
1814: if(lockit
1815: && lock(nodefile,(long)number*sizeof(node_t),sizeof(node_t))==-1) {
1816: count++;
1817: continue; }
1818: if(read(nodefile,node,sizeof(node_t))==sizeof(node_t))
1819: break;
1820: count++; }
1821: if(count==LOOP_NODEDAB) {
1822: printf("\7ERROR unlocking and reading NODE.DAB\n");
1823: logprintf("ERROR line %d unlocking and reading NODE.DAB",__LINE__); }
1824: }
1825:
1826: /****************************************************************************/
1827: /* Write the data from the structure 'node' into NODE.DAB */
1828: /* getnodedat(num,&node,1); must have been called before calling this func */
1829: /* NOTE: ------^ the indicates the node record has been locked */
1830: /****************************************************************************/
1831: void putnodedat(uint number, node_t node)
1832: {
1833: char str[256];
1834: int count;
1835:
1836: number--; /* make zero based */
1837: lseek(nodefile,(long)number*sizeof(node_t),SEEK_SET);
1838: if(write(nodefile,&node,sizeof(node_t))!=sizeof(node_t)) {
1839: unlock(nodefile,(long)number*sizeof(node_t),sizeof(node_t));
1840: printf("\7ERROR writing NODE.DAB for node %u\n",number+1);
1841: logprintf("ERROR line %d writing NODE.DAB for node %u",__LINE__,number+1);
1842: return; }
1843: unlock(nodefile,(long)number*sizeof(node_t),sizeof(node_t));
1844: }
1845:
1846: /****************************************************************************/
1847: /* Creates a short message for 'usernumber' than contains 'strin' */
1848: /****************************************************************************/
1849: void putsmsg(int usernumber, char *strin)
1850: {
1851: char str[256];
1852: int file,i;
1853: node_t node;
1854:
1855: sprintf(str,"%sMSGS\\%4.4u.MSG",data_dir,usernumber);
1856: if((file=nopen(str,O_WRONLY|O_CREAT|O_APPEND))==-1) {
1857: printf("\7ERROR opening/creating %s for create/append access\n",str);
1858: logprintf("ERROR line %d opening/creating %s",__LINE__,str);
1859: return; }
1860: i=strlen(strin);
1861: if(write(file,strin,i)!=i) {
1862: close(file);
1863: printf("\7ERROR writing %u bytes to %s\n",i,str);
1864: logprintf("ERROR line %d writing to %s",__LINE__,str);
1865: return; }
1866: close(file);
1867: for(i=1;i<=sys_nodes;i++) { /* flag node if user on that msg waiting */
1868: getnodedat(i,&node,0);
1869: if(node.useron==usernumber
1870: && (node.status==NODE_INUSE || node.status==NODE_QUIET)
1871: && !(node.misc&NODE_MSGW)) {
1872: getnodedat(i,&node,1);
1873: node.misc|=NODE_MSGW;
1874: putnodedat(i,node); } }
1875: }
1876:
1877: /****************************************************************************/
1878: /* Converts an ASCII Hex string into an ulong */
1879: /****************************************************************************/
1880: ulong ahtoul(char *str)
1881: {
1882: ulong l,val=0;
1883:
1884: while((l=(*str++)|0x20)!=0x20)
1885: val=(l&0xf)+(l>>6&1)*9+val*16;
1886: return(val);
1887: }
1888:
1889: /****************************************************************************/
1890: /* Truncates white-space chars off end of 'str' and terminates at first tab */
1891: /****************************************************************************/
1892: void truncsp(char *str)
1893: {
1894: int c;
1895:
1896: c=strlen(str);
1897: while(c && (uchar)str[c-1]<=SP) c--;
1898: str[c]=0;
1899: }
1900:
1901:
1902: void remove_re(char *str)
1903: {
1904: while(!strnicmp(str,"RE:",3)) {
1905: strcpy(str,str+3);
1906: while(str[0]==SP)
1907: strcpy(str,str+1); }
1908: }
1909:
1910: /****************************************************************************/
1911: /* Moves or copies a file from one dir to another */
1912: /* both 'src' and 'dest' must contain full path and filename */
1913: /* returns 0 if successful, -1 if error */
1914: /****************************************************************************/
1915: int mv(char *src, char *dest, char copy)
1916: {
1917: char buf[4096],str[256];
1918: int ind,outd;
1919: long length,chunk=4096,l;
1920: #ifdef __WATCOMC__
1921: unsigned short ftime,fdate;
1922: #else
1923: unsigned ftime,fdate;
1924: #endif
1925: FILE *inp,*outp;
1926:
1927: if(!strcmp(src,dest)) /* source and destination are the same! */
1928: return(0);
1929: if(!fexist(src)) {
1930: logprintf("MV ERROR: Source doesn't exist '%s",src);
1931: return(-1); }
1932: if(!copy && fexist(dest)) {
1933: logprintf("MV ERROR: Destination already exists '%s'",dest);
1934: return(-1); }
1935: if(!copy && ((src[1]!=':' && dest[1]!=':')
1936: || (src[1]==':' && dest[1]==':' && toupper(src[0])==toupper(dest[0])))) {
1937: if(rename(src,dest)) { /* same drive, so move */
1938: logprintf("MV ERROR: Error renaming %s to %s",src,dest);
1939: return(-1); }
1940: return(0); }
1941: if((ind=nopen(src,O_RDONLY))==-1) {
1942: logprintf("MV ERROR: ERR_OPEN %s",src);
1943: return(-1); }
1944: if((inp=fdopen(ind,"rb"))==NULL) {
1945: close(ind);
1946: logprintf("MV ERROR: ERR_FDOPEN %s",str);
1947: return(-1); }
1948: setvbuf(inp,NULL,_IOFBF,8*1024);
1949: if((outd=nopen(dest,O_WRONLY|O_CREAT|O_TRUNC))==-1) {
1950: fclose(inp);
1951: logprintf("MV ERROR: ERR_OPEN %s",dest);
1952: return(-1); }
1953: if((outp=fdopen(outd,"wb"))==NULL) {
1954: close(outd);
1955: fclose(inp);
1956: logprintf("MV ERROR: ERR_FDOPEN %s",str);
1957: return(-1); }
1958: setvbuf(outp,NULL,_IOFBF,8*1024);
1959: length=filelength(ind);
1960: l=0L;
1961: while(l<length) {
1962: if(l+chunk>length)
1963: chunk=length-l;
1964: fread(buf,chunk,1,inp);
1965: fwrite(buf,chunk,1,outp);
1966: l+=chunk; }
1967: _dos_getftime(ind,&fdate,&ftime);
1968: _dos_setftime(outd,fdate,ftime);
1969: fclose(inp);
1970: fclose(outp);
1971: if(!copy && delfile(src)) {
1972: logprintf("ERROR line %d removing %s %s",__LINE__,src,sys_errlist[errno]);
1973: return(-1); }
1974: return(0);
1975: }
1976:
1977: /****************************************************************************/
1978: /* Returns the total number of msgs in the sub-board and sets 'ptr' to the */
1979: /* date of the last message in the sub (0) if no messages. */
1980: /****************************************************************************/
1981: ulong getlastmsg(uint subnum, ulong *ptr, time_t *t)
1982: {
1983: char str[256];
1984: int i;
1985: smb_t smbfile;
1986:
1987: if(subnum>=total_subs) {
1988: printf("\nERROR getlastmsg, subnum=%d\n",subnum);
1989: logprintf("ERROR line %d getlastmsg %d",__LINE__,subnum);
1990: exit(1); }
1991: sprintf(smbfile.file,"%s%s",sub[subnum]->data_dir,sub[subnum]->code);
1992: smbfile.retry_time=smb_retry_time;
1993: if((i=smb_open(&smbfile))!=0) {
1994: printf("ERROR %d opening %s\n",i,smbfile.file);
1995: logprintf("ERROR %d line %d opening %s",i,__LINE__,smbfile.file);
1996: return(0); }
1997:
1998: if(!filelength(fileno(smbfile.shd_fp))) { /* Empty base */
1999: if(ptr) (*ptr)=0;
2000: smb_close(&smbfile);
2001: return(0); }
2002: #if 0 // Not necessary with SMBLIB v2.0
2003: if((i=smb_locksmbhdr(&smbfile))!=0) {
2004: smb_close(&smbfile);
2005: printf("ERROR %d locking %s\n",i,smbfile.file);
2006: logprintf("ERROR %d line %d locking %s smbhdr",i,__LINE__
2007: ,smbfile.file);
2008: return(0); }
2009: if((i=smb_getstatus(&smbfile))!=0) {
2010: smb_unlocksmbhdr(&smbfile);
2011: smb_close(&smbfile);
2012: printf("ERROR %d reading %s\n",i,smbfile.file);
2013: logprintf("ERROR %d line %d reading %s",i,__LINE__,smbfile.file);
2014: return(0); }
2015: smb_unlocksmbhdr(&smbfile);
2016: #endif
2017: smb_close(&smbfile);
2018: if(ptr) (*ptr)=smbfile.status.last_msg;
2019: return(smbfile.status.total_msgs);
2020: }
2021:
2022:
2023: ulong loadmsgs(post_t HUGE16 **post, ulong ptr)
2024: {
2025: int i;
2026: long l=0,total;
2027: idxrec_t idx;
2028:
2029:
2030: if((i=smb_locksmbhdr(&smb[cur_smb]))!=0) {
2031: printf("ERROR %d locking %s\n",i,smb[cur_smb].file);
2032: logprintf("ERROR %d line %d locking %s",i,__LINE__,smb[cur_smb].file);
2033: return(0L); }
2034:
2035: /* total msgs in sub */
2036: total=filelength(fileno(smb[cur_smb].sid_fp))/sizeof(idxrec_t);
2037:
2038: if(!total) { /* empty */
2039: smb_unlocksmbhdr(&smb[cur_smb]);
2040: return(0); }
2041:
2042: if(((*post)=(post_t HUGE16 *)LMALLOC(sizeof(post_t)*total)) /* alloc for max */
2043: ==NULL) {
2044: smb_unlocksmbhdr(&smb[cur_smb]);
2045: printf("ERROR allocating %lu bytes for %s\n",sizeof(post_t *)*total
2046: ,smb[cur_smb].file);
2047: logprintf("ERROR line %d allocating %lu bytes for %s",__LINE__
2048: ,sizeof(post_t *)*total,smb[cur_smb].file);
2049: return(0); }
2050:
2051: fseek(smb[cur_smb].sid_fp,0L,SEEK_SET);
2052: while(!feof(smb[cur_smb].sid_fp)) {
2053: if(!fread(&idx,sizeof(idxrec_t),1,smb[cur_smb].sid_fp))
2054: break;
2055:
2056: if(idx.number<=ptr || idx.attr&MSG_DELETE)
2057: continue;
2058:
2059: if(idx.attr&MSG_MODERATED && !(idx.attr&MSG_VALIDATED))
2060: break;
2061:
2062: (*post)[l].offset=idx.offset;
2063: (*post)[l].number=idx.number;
2064: (*post)[l].to=idx.to;
2065: (*post)[l].from=idx.from;
2066: (*post)[l].subj=idx.subj;
2067: l++; }
2068: smb_unlocksmbhdr(&smb[cur_smb]);
2069: if(!l)
2070: LFREE(*post);
2071: return(l);
2072: }
2073:
2074: void allocfail(uint size)
2075: {
2076: printf("\7ERROR allocating %u bytes of memory.\n",size);
2077: bail(1);
2078: }
2079:
2080: void bail(int code)
2081: {
2082: exit(code);
2083: }
2084:
2085: /****************************************************************************/
2086: /* Returns the length of the file in 'filespec' */
2087: /****************************************************************************/
2088: long flength(char *filespec)
2089: {
2090: struct find_t f;
2091: uint i;
2092:
2093: i=_dos_findfirst(filespec,0,&f);
2094: #ifdef __WATCOMC__
2095: _dos_findclose(&f);
2096: #endif
2097: if(!i)
2098: return(f.size);
2099: return(-1L);
2100: }
2101:
2102: /****************************************************************************/
2103: /* Checks the disk drive for the existence of a file. Returns 1 if it */
2104: /* exists, 0 if it doesn't. */
2105: /* Called from upload */
2106: /****************************************************************************/
2107: char fexist(char *filespec)
2108: {
2109: struct find_t f;
2110: uint i;
2111:
2112: i=_dos_findfirst(filespec,0,&f);
2113: #ifdef __WATCOMC__
2114: _dos_findclose(&f);
2115: #endif
2116: if(!i)
2117: return(1);
2118: return(0);
2119: }
2120:
2121: typedef struct {
2122: ulong alias,
2123: real;
2124: } username_t;
2125:
2126: /****************************************************************************/
2127: /* Note: Wrote another version of this function that read all userdata into */
2128: /****************************************************************************/
2129: /* Looks for a perfect match amoung all usernames (not deleted users) */
2130: /* Returns the number of the perfect matched username or 0 if no match */
2131: /* Called from functions waitforcall and newuser */
2132: /* memory then scanned it from memory... took longer - always. */
2133: /****************************************************************************/
2134: ulong matchname(char *inname)
2135: {
2136: static ulong total_users;
2137: static username_t *username;
2138: ulong last_user;
2139: int userdat,i;
2140: char str[256],name[LEN_NAME+1],alias[LEN_ALIAS+1],c;
2141: ulong l,crc;
2142:
2143: if(!total_users) { /* Load CRCs */
2144: fprintf(stderr,"\n%-25s","Loading user names...");
2145: sprintf(str,"%sUSER\\USER.DAT",data_dir);
2146: if((userdat=nopen(str,O_RDONLY|O_DENYNONE))==-1)
2147: return(0);
2148: last_user=filelength(userdat)/U_LEN;
2149: for(total_users=0;total_users<last_user;total_users++) {
2150: printf("%5ld\b\b\b\b\b",total_users);
2151: if((username=(username_t *)REALLOC(username
2152: ,(total_users+1L)*sizeof(username_t)))==NULL)
2153: break;
2154: username[total_users].alias=0;
2155: username[total_users].real=0;
2156: i=0;
2157: while(i<LOOP_NODEDAB
2158: && lock(userdat,(long)((long)(total_users)*U_LEN)+U_ALIAS
2159: ,LEN_ALIAS+LEN_NAME)==-1)
2160: i++;
2161: if(i>=LOOP_NODEDAB) { /* Couldn't lock USER.DAT record */
2162: logprintf("ERROR locking USER.DAT record #%ld",total_users);
2163: continue; }
2164: lseek(userdat,(long)((long)(total_users)*U_LEN)+U_ALIAS,SEEK_SET);
2165: read(userdat,alias,LEN_ALIAS);
2166: read(userdat,name,LEN_NAME);
2167: lseek(userdat,(long)(((long)total_users)*U_LEN)+U_MISC,SEEK_SET);
2168: read(userdat,tmp,8);
2169: for(c=0;c<8;c++)
2170: if(tmp[c]==ETX || tmp[c]==CR) break;
2171: tmp[c]=0;
2172: unlock(userdat,(long)((long)(total_users)*U_LEN)+U_ALIAS
2173: ,LEN_ALIAS+LEN_NAME);
2174: if(ahtoul(tmp)&DELETED)
2175: continue;
2176: for(c=0;c<LEN_ALIAS;c++)
2177: if(alias[c]==ETX || alias[c]==CR) break;
2178: alias[c]=0;
2179: strupr(alias);
2180: for(c=0;c<LEN_NAME;c++)
2181: if(name[c]==ETX || name[c]==CR) break;
2182: name[c]=0;
2183: strupr(name);
2184: username[total_users].alias=crc32(alias);
2185: username[total_users].real=crc32(name); }
2186: close(userdat);
2187: fprintf(stderr," \b\b\b\b\b"); // Clear counter
2188: fprintf(stderr,
2189: "\b\b\b\b\b\b\b\b\b\b\b\b\b\b\b\b\b\b\b\b\b\b\b\b\b"
2190: "%25s"
2191: "\b\b\b\b\b\b\b\b\b\b\b\b\b\b\b\b\b\b\b\b\b\b\b\b\b"
2192: ,""); }
2193:
2194: strcpy(str,inname);
2195: strupr(str);
2196: crc=crc32(str);
2197: for(l=0;l<total_users;l++)
2198: if((crc==username[l].alias || crc==username[l].real))
2199: return(l+1);
2200: return(0);
2201: }
2202:
2203: /****************************************************************************/
2204: /* Converts goofy FidoNet time format into Unix format */
2205: /****************************************************************************/
2206: time_t fmsgtime(char *str)
2207: {
2208: char month[4];
2209: struct tm tm;
2210:
2211: memset(&tm,0,sizeof(tm));
2212: if(isdigit(str[1])) { /* Regular format: "01 Jan 86 02:34:56" */
2213: tm.tm_mday=atoi(str);
2214: sprintf(month,"%3.3s",str+3);
2215: if(!stricmp(month,"jan"))
2216: tm.tm_mon=0;
2217: else if(!stricmp(month,"feb"))
2218: tm.tm_mon=1;
2219: else if(!stricmp(month,"mar"))
2220: tm.tm_mon=2;
2221: else if(!stricmp(month,"apr"))
2222: tm.tm_mon=3;
2223: else if(!stricmp(month,"may"))
2224: tm.tm_mon=4;
2225: else if(!stricmp(month,"jun"))
2226: tm.tm_mon=5;
2227: else if(!stricmp(month,"jul"))
2228: tm.tm_mon=6;
2229: else if(!stricmp(month,"aug"))
2230: tm.tm_mon=7;
2231: else if(!stricmp(month,"sep"))
2232: tm.tm_mon=8;
2233: else if(!stricmp(month,"oct"))
2234: tm.tm_mon=9;
2235: else if(!stricmp(month,"nov"))
2236: tm.tm_mon=10;
2237: else
2238: tm.tm_mon=11;
2239: tm.tm_year=atoi(str+7);
1.1.1.2 ! root 2240: if(tm.tm_year<Y2K_2DIGIT_WINDOW)
! 2241: tm.tm_year+=100;
1.1 root 2242: tm.tm_hour=atoi(str+11);
2243: tm.tm_min=atoi(str+14);
2244: tm.tm_sec=atoi(str+17); }
2245:
2246: else { /* SEAdog format: "Mon 1 Jan 86 02:34" */
2247: tm.tm_mday=atoi(str+4);
2248: sprintf(month,"%3.3s",str+7);
2249: if(!stricmp(month,"jan"))
2250: tm.tm_mon=0;
2251: else if(!stricmp(month,"feb"))
2252: tm.tm_mon=1;
2253: else if(!stricmp(month,"mar"))
2254: tm.tm_mon=2;
2255: else if(!stricmp(month,"apr"))
2256: tm.tm_mon=3;
2257: else if(!stricmp(month,"may"))
2258: tm.tm_mon=4;
2259: else if(!stricmp(month,"jun"))
2260: tm.tm_mon=5;
2261: else if(!stricmp(month,"jul"))
2262: tm.tm_mon=6;
2263: else if(!stricmp(month,"aug"))
2264: tm.tm_mon=7;
2265: else if(!stricmp(month,"sep"))
2266: tm.tm_mon=8;
2267: else if(!stricmp(month,"oct"))
2268: tm.tm_mon=9;
2269: else if(!stricmp(month,"nov"))
2270: tm.tm_mon=10;
2271: else
2272: tm.tm_mon=11;
2273: tm.tm_year=atoi(str+11);
1.1.1.2 ! root 2274: if(tm.tm_year<Y2K_2DIGIT_WINDOW)
! 2275: tm.tm_year+=100;
1.1 root 2276: tm.tm_hour=atoi(str+14);
2277: tm.tm_min=atoi(str+17);
2278: tm.tm_sec=0; }
2279: return(mktime(&tm));
2280: }
2281:
2282: #if 1 /* Old way */
2283:
2284: char HUGE16 *getfmsg(FILE *stream, ulong *outlen)
2285: {
2286: uchar HUGE16 *fbuf;
2287: int ch;
2288: ulong l,length,start;
2289:
2290: length=0L;
2291: start=ftell(stream); /* Beginning of Message */
2292: while(1) {
2293: ch=fgetc(stream); /* Look for Terminating NULL */
2294: if(!ch || ch==EOF) /* Found end of message */
2295: break;
2296: length++; } /* Increment the Length */
2297:
2298: if((fbuf=(char *)LMALLOC(length+1))==NULL) {
2299: printf("Unable to allocate %lu bytes for message.\n",length+1);
2300: logprintf("ERROR line %d allocating %lu bytes of memory",__LINE__,length+1);
2301: exit(0); }
2302:
2303: fseek(stream,start,SEEK_SET);
2304: for(l=0;l<length;l++)
2305: fbuf[l]=fgetc(stream);
2306: fbuf[length]=0;
2307: if(!ch)
2308: fgetc(stream); /* Read NULL */
2309: if(outlen)
2310: *outlen=length;
2311: return(fbuf);
2312: }
2313:
2314: #else
2315:
2316: #define FBUF_BLOCK 4096
2317:
2318: char *getfmsg(FILE *stream)
2319: {
2320: uchar *fbuf,*p;
2321: ulong l,n,length,start;
2322:
2323: length=0L;
2324: start=ftell(stream); /* Beginning of Message */
2325: if((fbuf=LMALLOC(FBUF_BLOCK))==NULL)
2326: return(fbuf);
2327: while(!feof(stream)) {
2328: l=fread(fbuf+length,1,FBUF_BLOCK,stream);
2329: if(l<1)
2330: break;
2331: *(fbuf+length+l)=0;
2332: n=strlen(fbuf+length);
2333: if(n<l) {
2334: length+=(n+1);
2335: break; }
2336: printf(",");
2337: length+=l;
2338: if(l<FBUF_BLOCK)
2339: break;
2340: printf("<");
2341: if((p=REALLOC(fbuf,length+FBUF_BLOCK+1))==NULL) {
2342: LFREE(fbuf);
2343: printf("!");
2344: fseek(stream,-l,SEEK_CUR);
2345: return(NULL); }
2346: fbuf=p;
2347: printf(">");
2348: }
2349: printf(".");
2350:
2351: fseek(stream,start+length,SEEK_SET);
2352: return(fbuf);
2353: }
2354:
2355: #endif
2356:
2357: #define MAX_TAILLEN 1024
2358:
2359: /****************************************************************************/
2360: /* Coverts a FidoNet message into a Synchronet message */
2361: /* Returns 1 on success, 0 on failure, -1 on dupe. */
2362: /****************************************************************************/
2363: int fmsgtosmsg(uchar HUGE16 *fbuf, fmsghdr_t fmsghdr, uint user, uint subnum)
2364: {
2365: uchar ch,HUGE16 *sbody,HUGE16 *stail,HUGE16 *outbuf
2366: ,done,col,esc,cr,*p,str[128];
2367: int i,chunk,lzh=0,storage;
2368: ushort xlat,net;
2369: ulong l,m,length,lzhlen,bodylen,taillen,crc;
2370: faddr_t faddr,origaddr,destaddr;
2371: smbmsg_t msg;
2372: smb_t *smbfile;
2373:
2374: memset(&msg,0,sizeof(smbmsg_t));
2375: memcpy(msg.hdr.id,"SHD\x1a",4);
1.1.1.2 ! root 2376: msg.hdr.version=smb_ver();
1.1 root 2377: if(fmsghdr.attr&FIDO_PRIVATE)
2378: msg.idx.attr|=MSG_PRIVATE;
2379: msg.hdr.attr=msg.idx.attr;
2380:
2381: if(fmsghdr.attr&FIDO_FILE)
2382: msg.hdr.auxattr|=MSG_FILEATTACH;
2383:
2384: msg.hdr.when_imported.time=time(NULL);
2385: msg.hdr.when_imported.zone=sys_timezone;
2386: msg.hdr.when_written.time=fmsgtime(fmsghdr.time);
2387:
2388: origaddr.zone=fmsghdr.origzone; /* only valid if NetMail */
2389: origaddr.net=fmsghdr.orignet;
2390: origaddr.node=fmsghdr.orignode;
2391: origaddr.point=fmsghdr.origpoint;
2392:
2393: destaddr.zone=fmsghdr.destzone; /* only valid if NetMail */
2394: destaddr.net=fmsghdr.destnet;
2395: destaddr.node=fmsghdr.destnode;
2396: destaddr.point=fmsghdr.destpoint;
2397:
2398: smb_hfield(&msg,SENDER,strlen(fmsghdr.from),fmsghdr.from);
2399: strlwr(fmsghdr.from);
2400: if(subnum==INVALID_SUB)
2401: msg.idx.from=0;
2402: else
2403: msg.idx.from=crc16(fmsghdr.from);
2404:
2405: smb_hfield(&msg,RECIPIENT,strlen(fmsghdr.to),fmsghdr.to);
2406: strlwr(fmsghdr.to);
2407: msg.idx.to=crc16(fmsghdr.to);
2408:
2409: if(user) {
2410: sprintf(str,"%u",user);
2411: smb_hfield(&msg,RECIPIENTEXT,strlen(str),str);
2412: msg.idx.to=user; }
2413:
2414: smb_hfield(&msg,SUBJECT,strlen(fmsghdr.subj),fmsghdr.subj);
2415: remove_re(fmsghdr.subj);
2416: strlwr(fmsghdr.subj);
2417: msg.idx.subj=crc16(fmsghdr.subj);
2418: if(fbuf==NULL) {
2419: printf("ERROR allocating fbuf\n");
2420: logprintf("ERROR line %d allocating fbuf",__LINE__);
2421: smb_freemsgmem(&msg);
2422: return(0); }
2423: length=strlen((char *)fbuf);
2424: if((sbody=(char HUGE16 *)LMALLOC((length+1)*2))==NULL) {
2425: printf("ERROR allocating %lu bytes for body",(length+1)*2L);
2426: logprintf("ERROR line %d allocating %lu bytes for body",__LINE__
2427: ,(length+1)*2L);
2428: smb_freemsgmem(&msg);
2429: return(0); }
2430: if((stail=(char HUGE16 *)LMALLOC(MAX_TAILLEN))==NULL) {
2431: printf("ERROR allocating %lu bytes\n",MAX_TAILLEN);
2432: logprintf("ERROR line %d allocating %lu bytes for tail",__LINE__
2433: ,MAX_TAILLEN);
2434: LFREE(sbody);
2435: smb_freemsgmem(&msg);
2436: return(0); }
2437:
2438: for(col=l=esc=done=bodylen=taillen=0,cr=1;l<length;l++) {
2439:
2440: if(!l && !strncmp((char *)fbuf,"AREA:",5)) {
2441: l+=5;
2442: while(l<length && fbuf[l]<=SP) l++;
2443: m=l;
2444: while(m<length && fbuf[m]!=CR) m++;
2445: while(m && fbuf[m-1]<=SP) m--;
2446: if(m>l)
2447: smb_hfield(&msg,FIDOAREA,m-l,fbuf+l);
2448: while(l<length && fbuf[l]!=CR) l++;
2449: continue; }
2450:
2451: ch=fbuf[l];
2452: if(ch==1 && cr) { /* kludge line */
2453:
2454: if(!strncmp((char *)fbuf+l+1,"TOPT ",5))
2455: destaddr.point=atoi((char *)fbuf+l+6);
2456:
2457: else if(!strncmp((char *)fbuf+l+1,"FMPT ",5))
2458: origaddr.point=atoi((char *)fbuf+l+6);
2459:
2460: else if(!strncmp((char *)fbuf+l+1,"INTL ",5)) {
2461: faddr=atofaddr((char *)fbuf+l+6);
2462: destaddr.zone=faddr.zone;
2463: destaddr.net=faddr.net;
2464: destaddr.node=faddr.node;
2465: l+=6;
2466: while(l<length && fbuf[l]!=SP) l++;
2467: faddr=atofaddr((char *)fbuf+l+1);
2468: origaddr.zone=faddr.zone;
2469: origaddr.net=faddr.net;
2470: origaddr.node=faddr.node; }
2471:
2472: else if(!strncmp((char *)fbuf+l+1,"MSGID:",6)) {
2473: l+=7;
2474: while(l<length && fbuf[l]<=SP) l++;
2475: m=l;
2476: while(m<length && fbuf[m]!=CR) m++;
2477: while(m && fbuf[m-1]<=SP) m--;
2478: if(m>l)
2479: smb_hfield(&msg,FIDOMSGID,m-l,fbuf+l); }
2480:
2481: else if(!strncmp((char *)fbuf+l+1,"REPLY:",6)) {
2482: l+=7;
2483: while(l<length && fbuf[l]<=SP) l++;
2484: m=l;
2485: while(m<length && fbuf[m]!=CR) m++;
2486: while(m && fbuf[m-1]<=SP) m--;
2487: if(m>l)
2488: smb_hfield(&msg,FIDOREPLYID,m-l,fbuf+l); }
2489:
2490: else if(!strncmp((char *)fbuf+l+1,"FLAGS:",6)) {
2491: l+=7;
2492: while(l<length && fbuf[l]<=SP) l++;
2493: m=l;
2494: while(m<length && fbuf[m]!=CR) m++;
2495: while(m && fbuf[m-1]<=SP) m--;
2496: if(m>l)
2497: smb_hfield(&msg,FIDOFLAGS,m-l,fbuf+l); }
2498:
2499: else if(!strncmp((char *)fbuf+l+1,"PATH:",5)) {
2500: l+=6;
2501: while(l<length && fbuf[l]<=SP) l++;
2502: m=l;
2503: while(m<length && fbuf[m]!=CR) m++;
2504: while(m && fbuf[m-1]<=SP) m--;
2505: if(m>l && misc&STORE_PATH)
2506: smb_hfield(&msg,FIDOPATH,m-l,fbuf+l); }
2507:
2508: else if(!strncmp((char *)fbuf+l+1,"PID:",4)) {
2509: l+=5;
2510: while(l<length && fbuf[l]<=SP) l++;
2511: m=l;
2512: while(m<length && fbuf[m]!=CR) m++;
2513: while(m && fbuf[m-1]<=SP) m--;
2514: if(m>l)
2515: smb_hfield(&msg,FIDOPID,m-l,fbuf+l); }
2516:
2517: else { /* Unknown kludge line */
2518: while(l<length && fbuf[l]<=SP) l++;
2519: m=l;
2520: while(m<length && fbuf[m]!=CR) m++;
2521: while(m && fbuf[m-1]<=SP) m--;
2522: if(m>l && misc&STORE_KLUDGE)
2523: smb_hfield(&msg,FIDOCTRL,m-l,fbuf+l); }
2524:
2525: while(l<length && fbuf[l]!=CR) l++;
2526: continue; }
2527:
2528: if(ch!=LF && ch!=0x8d) { /* ignore LF and soft CRs */
2529: if(cr && (!strncmp((char *)fbuf+l,"--- ",4)
2530: || !strncmp((char *)fbuf+l,"---\r",4)))
2531: done=1; /* tear line and down go into tail */
2532: if(done && cr && !strncmp((char *)fbuf+l,"SEEN-BY:",8)) {
2533: l+=8;
2534: while(l<length && fbuf[l]<=SP) l++;
2535: m=l;
2536: while(m<length && fbuf[m]!=CR) m++;
2537: while(m && fbuf[m-1]<=SP) m--;
2538: if(m>l && misc&STORE_SEENBY)
2539: smb_hfield(&msg,FIDOSEENBY,m-l,fbuf+l);
2540: while(l<length && fbuf[l]!=CR) l++;
2541: continue; }
2542: if(done) {
2543: if(taillen<MAX_TAILLEN)
2544: stail[taillen++]=ch; }
2545: else
2546: sbody[bodylen++]=ch;
2547: col++;
2548: if(ch==CR) {
2549: cr=1;
2550: col=0;
2551: if(done) {
2552: if(taillen<MAX_TAILLEN)
2553: stail[taillen++]=LF; }
2554: else
2555: sbody[bodylen++]=LF; }
2556: else {
2557: cr=0;
2558: if(col==1 && !strncmp((char *)fbuf+l," * Origin: ",11)) {
2559: p=(char *)fbuf+l+11;
2560: while(*p && *p!=CR) p++; /* Find CR */
2561: while(p && *p!='(') p--; /* rewind to '(' */
2562: if(p)
2563: origaddr=atofaddr(p+1); /* get orig address */
2564: done=1; }
2565: if(done)
2566: continue;
2567:
2568: if(ch==ESC) esc=1; /* ANSI codes */
2569: if(ch==SP && col>40 && !esc) { /* word wrap */
2570: for(m=l+1;m<length;m++) /* find next space */
2571: if(fbuf[m]<=SP)
2572: break;
2573: if(m<length && m-l>80-col) { /* if it's beyond the eol */
2574: sbody[bodylen++]=CR;
2575: sbody[bodylen++]=LF;
2576: col=0; } }
2577: } } }
2578:
2579: if(bodylen>=2 && sbody[bodylen-2]==CR && sbody[bodylen-1]==LF)
2580: bodylen-=2; /* remove last CRLF if present */
2581:
2582: if(smb[cur_smb].status.max_crcs) {
2583: for(l=0,crc=0xffffffff;l<bodylen;l++)
2584: crc=ucrc32(sbody[l],crc);
2585: crc=~crc;
2586: i=smb_addcrc(&smb[cur_smb],crc);
2587: if(i) {
2588: if(i==1)
2589: printf("Duplicate ");
2590: else
2591: printf("smb_addcrc returned %d ",i);
2592: smb_freemsgmem(&msg);
2593: LFREE(sbody);
2594: LFREE(stail);
2595: if(i==1)
2596: return(-1);
2597: return(0); } }
2598:
2599: while(taillen && stail[taillen-1]<=SP) /* trim all garbage off the tail */
2600: taillen--;
2601:
2602: if(!origaddr.zone && subnum==INVALID_SUB)
2603: net=NET_NONE; /* Message from SBBSecho */
2604: else
2605: net=NET_FIDO; /* Record origin address */
2606:
2607: if(net) {
2608: smb_hfield(&msg,SENDERNETTYPE,sizeof(ushort),&net);
2609: smb_hfield(&msg,SENDERNETADDR,sizeof(fidoaddr_t),&origaddr); }
2610:
2611: if(subnum==INVALID_SUB) {
2612: smbfile=email;
2613: if(net) {
2614: smb_hfield(&msg,RECIPIENTNETTYPE,sizeof(ushort),&net);
2615: smb_hfield(&msg,RECIPIENTNETADDR,sizeof(fidoaddr_t),&destaddr); } }
2616: else
2617: smbfile=&smb[cur_smb];
2618:
2619: if(subnum!=INVALID_SUB && sub[subnum]->misc&SUB_LZH
2620: && bodylen+2L+taillen+2L>=SDT_BLOCK_LEN && bodylen) {
2621: if((outbuf=(char *)LMALLOC(bodylen*2L))==NULL) {
2622: printf("ERROR allocating %lu bytes for lzh\n",bodylen*2);
2623: logprintf("ERROR line %d allocating %lu bytes for lzh",__LINE__
2624: ,bodylen*2);
2625: smb_freemsgmem(&msg);
2626: LFREE(sbody);
2627: LFREE(stail);
2628: return(0); }
2629: lzhlen=lzh_encode((uchar *)sbody,bodylen,(uchar *)outbuf);
2630: if(lzhlen>1 &&
2631: smb_datblocks(lzhlen+4L+taillen+2L)<
2632: smb_datblocks(bodylen+2L+taillen+2L)) {
2633: bodylen=lzhlen; /* Compressable */
2634: l=bodylen+4;
2635: LFREE(sbody);
2636: lzh=1;
2637: sbody=outbuf; }
2638: else { /* Uncompressable */
2639: l=bodylen+2;
2640: LFREE(outbuf); } }
2641: else
2642: l=bodylen+2;
2643:
2644: if(taillen)
2645: l+=(taillen+2);
2646:
2647: if(l&0xfff00000) {
2648: printf("ERROR checking msg len %lu\n",l);
2649: logprintf("ERROR line %d checking msg len %lu",__LINE__,l);
2650: smb_freemsgmem(&msg);
2651: LFREE(sbody);
2652: LFREE(stail);
2653: return(0); }
2654:
2655: if(smbfile->status.attr&SMB_HYPERALLOC) {
2656: if((i=smb_locksmbhdr(smbfile))!=0) {
2657: printf("ERROR %d locking %s\n",i,smbfile->file);
2658: logprintf("ERROR %d line %d locking %s",i,__LINE__,smbfile->file);
2659: smb_freemsgmem(&msg);
2660: LFREE(sbody);
2661: LFREE(stail);
2662: return(0); }
2663: msg.hdr.offset=smb_hallocdat(smbfile);
2664: storage=SMB_HYPERALLOC; }
2665: else {
2666: if((i=smb_open_da(smbfile))!=0) {
2667: smb_freemsgmem(&msg);
2668: printf("ERROR %d opening %s.SDA\n",i,smbfile->file);
2669: logprintf("ERROR %d line %d opening %s.SDA",i,__LINE__
2670: ,smbfile->file);
2671: LFREE(sbody);
2672: LFREE(stail);
2673: return(0); }
2674: if(subnum!=INVALID_SUB && sub[subnum]->misc&SUB_FAST) {
2675: msg.hdr.offset=smb_fallocdat(smbfile,l,1);
2676: storage=SMB_FASTALLOC; }
2677: else {
2678: msg.hdr.offset=smb_allocdat(smbfile,l,1);
2679: storage=SMB_SELFPACK; }
2680: smb_close_da(smbfile); }
2681:
2682: if(msg.hdr.offset && msg.hdr.offset<1L) {
2683: if(smbfile->status.attr&SMB_HYPERALLOC)
2684: smb_unlocksmbhdr(smbfile);
2685: smb_freemsgmem(&msg);
2686: LFREE(sbody);
2687: LFREE(stail);
2688: printf("ERROR %ld allocating records\n",msg.hdr.offset);
2689: logprintf("ERROR line %d %ld allocating records",__LINE__,msg.hdr.offset);
2690: return(0); }
2691: fseek(smbfile->sdt_fp,msg.hdr.offset,SEEK_SET);
2692: if(lzh) {
2693: xlat=XLAT_LZH;
2694: fwrite(&xlat,2,1,smbfile->sdt_fp); }
2695: xlat=XLAT_NONE;
2696: fwrite(&xlat,2,1,smbfile->sdt_fp);
2697: chunk=30000;
2698: for(l=0;l<bodylen;l+=chunk) {
2699: if(l+chunk>bodylen)
2700: chunk=bodylen-l;
2701: fwrite(sbody+l,1,chunk,smbfile->sdt_fp); }
2702: if(taillen) {
2703: fwrite(&xlat,2,1,smbfile->sdt_fp);
2704: fwrite(stail,1,taillen,smbfile->sdt_fp); }
2705: LFREE(sbody);
2706: LFREE(stail);
2707: fflush(smbfile->sdt_fp);
2708: if(smbfile->status.attr&SMB_HYPERALLOC)
2709: smb_unlocksmbhdr(smbfile);
2710:
2711: if(lzh)
2712: bodylen+=2;
2713: bodylen+=2;
2714: smb_dfield(&msg,TEXT_BODY,bodylen);
2715: if(taillen)
2716: smb_dfield(&msg,TEXT_TAIL,taillen+2);
2717:
2718: i=smb_addmsghdr(smbfile,&msg,storage);
2719: smb_freemsgmem(&msg);
2720: if(i) {
2721: printf("ERROR smb_addmsghdr returned %d\n",i);
2722: logprintf("ERROR line %d smb_addmsghdr returned %d"
2723: ,__LINE__,i);
2724: return(0); }
2725: return(1);
2726: }
2727:
2728: /***********************************************************************/
2729: /* Get zone and point from kludge lines from the stream if they exist */
2730: /***********************************************************************/
2731: void getzpt(FILE *stream, fmsghdr_t *hdr)
2732: {
2733: char buf[0x1000];
2734: int i,len,cr=0;
2735: long pos;
2736: faddr_t faddr;
2737:
2738: pos=ftell(stream);
2739: len=fread(buf,1,0x1000,stream);
2740: for(i=0;i<len;i++) {
2741: if((!i || cr) && buf[i]==1) { /* kludge */
2742: if(!strncmp(buf+i+1,"TOPT ",5))
2743: hdr->destpoint=atoi(buf+i+6);
2744: else if(!strncmp(buf+i+1,"FMPT ",5))
2745: hdr->origpoint=atoi(buf+i+6);
2746: else if(!strncmp(buf+i+1,"INTL ",5)) {
2747: faddr=atofaddr(buf+i+6);
2748: hdr->destzone=faddr.zone;
2749: hdr->destnet=faddr.net;
2750: hdr->destnode=faddr.node;
2751: i+=6;
2752: while(buf[i] && buf[i]!=SP) i++;
2753: faddr=atofaddr(buf+i+1);
2754: hdr->origzone=faddr.zone;
2755: hdr->orignet=faddr.net;
2756: hdr->orignode=faddr.node; }
2757: while(i<len && buf[i]!=CR) i++;
2758: cr=1;
2759: continue; }
2760: if(buf[i]==CR)
2761: cr=1;
2762: else
2763: cr=0; }
2764: fseek(stream,pos,SEEK_SET);
2765: }
2766: /******************************************************************************
2767: This function will seek to the next NULL found in stream
2768: ******************************************************************************/
2769: void seektonull(FILE *stream)
2770: {
2771: char ch;
2772:
2773: while(!feof(stream)) {
2774: if(!fread(&ch,1,1,stream))
2775: break;
2776: if(!ch)
2777: break; }
2778:
2779: }
2780:
2781: /******************************************************************************
2782: This function returns a packet name - used for outgoing packets
2783: ******************************************************************************/
2784: char *pktname(void)
2785: {
2786: static char str[128];
2787: int i;
2788: time_t now;
2789: struct tm *tm;
2790:
2791: now=time(NULL);
2792: for(i=0;i<MAX_TOTAL_PKTS*2;i++) {
2793: now+=i;
2794: tm=gmtime(&now);
2795: sprintf(str,"%s%02u%02u%02u%02u.PK_",cfg.outbound,tm->tm_mday,tm->tm_hour
2796: ,tm->tm_min,tm->tm_sec);
2797: if(!fexist(str)) /* Add 1 second if name exists */
2798: break; }
2799: return(str);
2800: }
2801: /******************************************************************************
2802: This function puts a message into a Fido packet, writing both the header
2803: information and the message body
2804: ******************************************************************************/
2805: void putfmsg(FILE *stream,uchar HUGE16 *fbuf,fmsghdr_t fmsghdr,areasbbs_t area
2806: ,addrlist_t seenbys,addrlist_t paths)
2807: {
2808: char str[256],seenby[256],*p;
2809: short i,j,lastlen=0,net_exists=0;
2810: faddr_t addr,sysaddr;
2811:
2812: addr=getsysfaddr(fmsghdr.destzone);
2813:
2814: i=0x0002;
2815: fwrite(&i,2,1,stream);
2816: fwrite(&addr.node,2,1,stream);
2817: fwrite(&fmsghdr.destnode,2,1,stream);
2818: fwrite(&addr.net,2,1,stream);
2819: fwrite(&fmsghdr.destnet,2,1,stream);
2820: fwrite(&fmsghdr.attr,2,1,stream);
2821: fwrite(&fmsghdr.cost,2,1,stream);
2822: fwrite(fmsghdr.time,strlen(fmsghdr.time)+1,1,stream);
2823: fwrite(fmsghdr.to,strlen(fmsghdr.to)+1,1,stream);
2824: fwrite(fmsghdr.from,strlen(fmsghdr.from)+1,1,stream);
2825: fwrite(fmsghdr.subj,strlen(fmsghdr.subj)+1,1,stream);
2826: if(area.name)
2827: if(strncmp((char *)fbuf,"AREA:",5)) /* No AREA: Line */
2828: fprintf(stream,"AREA:%s\r",area.name); /* So add one */
2829: fwrite(fbuf,strlen((char *)fbuf),1,stream);
2830: lastlen=9;
2831: if(fbuf[strlen((char *)fbuf)-1]!=CR)
2832: fputc(CR,stream);
2833:
2834: if(area.name && addr.zone!=fmsghdr.destzone) /* Zone Gate */
2835: fprintf(stream,"SEEN-BY: %d/%d\r",fmsghdr.destnet,fmsghdr.destnode);
2836:
2837: if(area.name && addr.zone==fmsghdr.destzone) { /* Not NetMail */
2838: fprintf(stream,"SEEN-BY:");
2839: for(i=0;i<seenbys.addrs;i++) { /* Put back original SEEN-BYs */
2840: strcpy(seenby," ");
2841: if(seenbys.addr[i].zone!=addr.zone)
2842: continue;
2843: if(seenbys.addr[i].net!=addr.net || !net_exists) {
2844: net_exists=1;
2845: addr.net=seenbys.addr[i].net;
2846: sprintf(str,"%d/",addr.net);
2847: strcat(seenby,str); }
2848: sprintf(str,"%d",seenbys.addr[i].node);
2849: strcat(seenby,str);
2850: if(lastlen+strlen(seenby)<80) {
2851: fwrite(seenby,strlen(seenby),1,stream);
2852: lastlen+=strlen(seenby); }
2853: else {
2854: --i;
2855: lastlen=9; /* +strlen(seenby); */
2856: net_exists=0;
2857: fprintf(stream,"\rSEEN-BY:"); } }
2858:
2859: for(i=0;i<area.uplinks;i++) { /* Add all uplinks to SEEN-BYs */
2860: strcpy(seenby," ");
2861: if(area.uplink[i].zone!=addr.zone || area.uplink[i].point)
2862: continue;
2863: for(j=0;j<seenbys.addrs;j++)
2864: if(!memcmp(&area.uplink[i],&seenbys.addr[j],sizeof(faddr_t)))
2865: break;
2866: if(j==seenbys.addrs) {
2867: if(area.uplink[i].net!=addr.net || !net_exists) {
2868: net_exists=1;
2869: addr.net=area.uplink[i].net;
2870: sprintf(str,"%d/",addr.net);
2871: strcat(seenby,str); }
2872: sprintf(str,"%d",area.uplink[i].node);
2873: strcat(seenby,str);
2874: if(lastlen+strlen(seenby)<80) {
2875: fwrite(seenby,strlen(seenby),1,stream);
2876: lastlen+=strlen(seenby); }
2877: else {
2878: --i;
2879: lastlen=9; /* +strlen(seenby); */
2880: net_exists=0;
2881: fprintf(stream,"\rSEEN-BY:"); } } }
2882:
2883: for(i=0;i<total_faddrs;i++) { /* Add AKAs to SEEN-BYs */
2884: strcpy(seenby," ");
2885: if(faddr[i].zone!=addr.zone || faddr[i].point)
2886: continue;
2887: for(j=0;j<seenbys.addrs;j++)
2888: if(!memcmp(&faddr[i],&seenbys.addr[j],sizeof(faddr_t)))
2889: break;
2890: if(j==seenbys.addrs) {
2891: if(faddr[i].net!=addr.net || !net_exists) {
2892: net_exists=1;
2893: addr.net=faddr[i].net;
2894: sprintf(str,"%d/",addr.net);
2895: strcat(seenby,str); }
2896: sprintf(str,"%d",faddr[i].node);
2897: strcat(seenby,str);
2898: if(lastlen+strlen(seenby)<80) {
2899: fwrite(seenby,strlen(seenby),1,stream);
2900: lastlen+=strlen(seenby); }
2901: else {
2902: --i;
2903: lastlen=9; /* +strlen(seenby); */
2904: net_exists=0;
2905: fprintf(stream,"\rSEEN-BY:"); } } }
2906:
2907: lastlen=7;
2908: net_exists=0;
2909: fprintf(stream,"\r\1PATH:");
2910: addr=getsysfaddr(fmsghdr.destzone);
2911: for(i=0;i<paths.addrs;i++) { /* Put back the original PATH */
2912: strcpy(seenby," ");
2913: if(paths.addr[i].zone!=addr.zone || paths.addr[i].point)
2914: continue;
2915: if(paths.addr[i].net!=addr.net || !net_exists) {
2916: net_exists=1;
2917: addr.net=paths.addr[i].net;
2918: sprintf(str,"%d/",addr.net);
2919: strcat(seenby,str); }
2920: sprintf(str,"%d",paths.addr[i].node);
2921: strcat(seenby,str);
2922: if(lastlen+strlen(seenby)<80) {
2923: fwrite(seenby,strlen(seenby),1,stream);
2924: lastlen+=strlen(seenby); }
2925: else {
2926: --i;
2927: lastlen=7; /* +strlen(seenby); */
2928: net_exists=0;
2929: fprintf(stream,"\r\1PATH:"); } }
2930:
2931: strcpy(seenby," "); /* Add first address with same zone to PATH */
2932: sysaddr=getsysfaddr(fmsghdr.destzone);
2933: if(!sysaddr.point) {
2934: if(sysaddr.net!=addr.net || !net_exists) {
2935: net_exists=1;
2936: addr.net=sysaddr.net;
2937: sprintf(str,"%d/",addr.net);
2938: strcat(seenby,str); }
2939: sprintf(str,"%d",sysaddr.node);
2940: strcat(seenby,str);
2941: if(lastlen+strlen(seenby)<80)
2942: fwrite(seenby,strlen(seenby),1,stream);
2943: else {
2944: fprintf(stream,"\r\1PATH:");
2945: fwrite(seenby,strlen(seenby),1,stream); } }
2946:
2947: fputc(CR,stream); }
2948:
2949: fputc(0,stream);
2950: }
2951:
2952: /******************************************************************************
2953: This function creates a binary list of the message seen-bys and path from
2954: inbuf.
2955: ******************************************************************************/
2956: void gen_psb(addrlist_t *seenbys,addrlist_t *paths,char HUGE16 *inbuf
2957: ,ushort zone)
2958: {
2959: char str[128],seenby[256],*p,*p1,*p2,HUGE16 *fbuf;
2960: int i,j,len;
2961: faddr_t addr;
2962:
2963: if(!inbuf)
2964: return;
2965: fbuf=strstr((char *)inbuf,"\r * Origin: ");
2966: if(!fbuf)
2967: fbuf=strstr((char *)inbuf,"\n * Origin: ");
2968: if(!fbuf)
2969: fbuf=inbuf;
2970: if(seenbys->addr) {
2971: FREE(seenbys->addr);
2972: seenbys->addr=0;
2973: seenbys->addrs=0; }
2974: addr.zone=addr.net=addr.node=addr.point=seenbys->addrs=0;
2975: p=strstr((char *)fbuf,"\rSEEN-BY:");
2976: if(!p) p=strstr((char *)fbuf,"\nSEEN-BY:");
2977: if(p) {
2978: while(1) {
2979: sprintf(str,"%-.100s",p+10);
2980: if((p1=strchr(str,CR))!=NULL)
2981: *p1=0;
2982: p1=str;
2983: i=j=0;
2984: len=strlen(str);
2985: while(i<len) {
2986: j=i;
2987: while(i<len && *(p1+i)!=SP)
2988: ++i;
2989: if(j>len)
2990: break;
2991: sprintf(seenby,"%-.*s",(i-j),p1+j);
2992: if((p2=strchr(seenby,':'))!=NULL) {
2993: addr.zone=atoi(seenby);
2994: addr.net=atoi(p2+1); }
2995: else if((p2=strchr(seenby,'/'))!=NULL)
2996: addr.net=atoi(seenby);
2997: if((p2=strchr(seenby,'/'))!=NULL)
2998: addr.node=atoi(p2+1);
2999: else
3000: addr.node=atoi(seenby);
3001: if((p2=strchr(seenby,'.'))!=NULL)
3002: addr.point=atoi(p2+1);
3003: if(!addr.zone)
3004: addr.zone=zone; /* Was 1 */
3005: if((seenbys->addr=(faddr_t *)REALLOC(seenbys->addr
3006: ,sizeof(faddr_t)*(seenbys->addrs+1)))==NULL) {
3007: printf("ERROR allocating memory for seenbys\n");
3008: logprintf("ERROR line %d allocating memory for message "
3009: "seenbys.",__LINE__);
3010: exit(1); }
3011: memcpy(&seenbys->addr[seenbys->addrs],&addr,sizeof(faddr_t));
3012: seenbys->addrs++;
3013: ++i; }
3014: p1=strstr(p+10,"\rSEEN-BY:");
3015: if(!p1)
3016: p1=strstr(p+10,"\nSEEN-BY:");
3017: if(!p1)
3018: break;
3019: p=p1; } }
3020: else {
3021: if((seenbys->addr=(faddr_t *)REALLOC(seenbys->addr
3022: ,sizeof(faddr_t)))==NULL) {
3023: printf("ERROR allocating memory for seenbys\n");
3024: logprintf("ERROR line %d allocating memory for message seenbys."
3025: ,__LINE__);
3026: exit(1); }
3027: memset(&seenbys->addr[0],0,sizeof(faddr_t)); }
3028:
3029: if(paths->addr) {
3030: FREE(paths->addr);
3031: paths->addr=0;
3032: paths->addrs=0; }
3033: addr.zone=addr.net=addr.node=addr.point=paths->addrs=0;
3034: if((p=strstr((char *)fbuf,"\1PATH:"))!=NULL) {
3035: while(1) {
3036: sprintf(str,"%-.100s",p+7);
3037: if((p1=strchr(str,CR))!=NULL)
3038: *p1=0;
3039: p1=str;
3040: i=j=0;
3041: len=strlen(str);
3042: while(i<len) {
3043: j=i;
3044: while(i<len && *(p1+i)!=SP)
3045: ++i;
3046: if(j>len)
3047: break;
3048: sprintf(seenby,"%-.*s",(i-j),p1+j);
3049: if((p2=strchr(seenby,':'))!=NULL) {
3050: addr.zone=atoi(seenby);
3051: addr.net=atoi(p2+1); }
3052: else if((p2=strchr(seenby,'/'))!=NULL)
3053: addr.net=atoi(seenby);
3054: if((p2=strchr(seenby,'/'))!=NULL)
3055: addr.node=atoi(p2+1);
3056: else
3057: addr.node=atoi(seenby);
3058: if((p2=strchr(seenby,'.'))!=NULL)
3059: addr.point=atoi(p2+1);
3060: if(!addr.zone)
3061: addr.zone=zone; /* Was 1 */
3062: if((paths->addr=(faddr_t *)REALLOC(paths->addr
3063: ,sizeof(faddr_t)*(paths->addrs+1)))==NULL) {
3064: printf("ERROR allocating memory for paths\n");
3065: logprintf("ERROR line %d allocating memory for message "
3066: "paths.",__LINE__);
3067: exit(1); }
3068: memcpy(&paths->addr[paths->addrs],&addr,sizeof(faddr_t));
3069: paths->addrs++;
3070: ++i; }
3071: if((p1=strstr(p+7,"\1PATH:"))==NULL)
3072: break;
3073: p=p1; } }
3074: else {
3075: if((paths->addr=(faddr_t *)REALLOC(paths->addr
3076: ,sizeof(faddr_t)))==NULL) {
3077: printf("ERROR allocating memory for paths\n");
3078: logprintf("ERROR line %d allocating memory for message paths."
3079: ,__LINE__);
3080: exit(1); }
3081: memset(&paths->addr[0],0,sizeof(faddr_t)); }
3082: }
3083:
3084: /******************************************************************************
3085: This function takes the addrs passed to it and compares them to the address
3086: passed in inaddr. 1 is returned if inaddr matches any of the addrs
3087: otherwise a 0 is returned.
3088: ******************************************************************************/
3089: char check_psb(addrlist_t addrlist,faddr_t inaddr)
3090: {
3091: int i;
3092:
3093: for(i=0;i<addrlist.addrs;i++) {
3094: if(!memcmp(&addrlist.addr[i],&inaddr,sizeof(faddr_t)))
3095: return(1); }
3096: return(0);
3097: }
3098: /******************************************************************************
3099: This function strips the message seen-bys and path from inbuf.
3100: ******************************************************************************/
3101: void strip_psb(char HUGE16 *inbuf)
3102: {
3103: char *p,HUGE16 *fbuf;
3104:
3105: if(!inbuf)
3106: return;
3107: fbuf=strstr((char *)inbuf,"\r * Origin: ");
3108: if(!fbuf)
3109: fbuf=inbuf;
3110: if((p=strstr((char *)fbuf,"\rSEEN-BY:"))!=NULL)
3111: *(p)=0;
3112: if((p=strstr((char *)fbuf,"\r\1PATH:"))!=NULL)
3113: *(p)=0;
3114: }
3115: void attach_bundles()
3116: {
3117: FILE *fidomsg;
3118: char str[1025],path[512],packet[128];
3119: int fmsg;
3120: ulong l;
3121: faddr_t pkt_faddr;
3122: pkthdr_t pkthdr;
3123: struct find_t ff;
3124:
3125: sprintf(path,"%s*.PK_",cfg.outbound);
3126: for(l=_dos_findfirst(path,0,&ff);!l && !kbhit();l=_dos_findnext(&ff)) {
3127: sprintf(packet,"%s%s",cfg.outbound,ff.name);
3128: printf("%21s: %s ","Outbound Packet",packet);
3129: if((fmsg=sopen(packet,O_RDWR,SH_DENYRW))==-1) {
3130: printf("ERROR opening.\n");
3131: logprintf("ERROR line %d opening %s",__LINE__,packet);
3132: continue; }
3133: if((fidomsg=fdopen(fmsg,"r+b"))==NULL) {
3134: close(fmsg);
3135: printf("\7ERROR fdopening.\n");
3136: logprintf("ERROR line %d fdopening %s",__LINE__,packet);
3137: continue; }
3138: if(filelength(fmsg)<sizeof(pkthdr_t)) {
3139: printf("ERROR invalid length of %u bytes for %s\n",filelength(fmsg)
3140: ,packet);
3141: logprintf("ERROR line %d invalid length of %u bytes for %s"
3142: ,__LINE__,filelength(fmsg),packet);
3143: fclose(fidomsg);
3144: if(delfile(packet))
3145: logprintf("ERROR line %d removing %s %s",__LINE__,packet
3146: ,sys_errlist[errno]);
3147: continue; }
3148: if(fread(&pkthdr,sizeof(pkthdr_t),1,fidomsg)!=1) {
3149: fclose(fidomsg);
3150: printf("\7ERROR reading %u bytes from %s\n",sizeof(pkthdr_t),packet);
3151: logprintf("ERROR line %d reading %u bytes from %s",__LINE__
3152: ,sizeof(pkthdr_t),packet);
3153: continue; }
3154: fseek(fidomsg,-2L,SEEK_END);
3155: fread(str,2,1,fidomsg);
3156: fclose(fidomsg);
3157: if(!str[0] && !str[1]) { /* Check for two nulls at end of packet */
3158: pkt_faddr.zone=pkthdr.destzone;
3159: pkt_faddr.net=pkthdr.destnet;
3160: pkt_faddr.node=pkthdr.destnode;
3161: pkt_faddr.point=0; /* No point info in the 2.0 hdr! */
3162: memcpy(&two_plus,&pkthdr.empty,20);
3163: if(two_plus.cword==_rotr(two_plus.cwcopy,8) /* 2+ Packet Header */
3164: && two_plus.cword && two_plus.cword&1)
3165: pkt_faddr.point=two_plus.destpoint;
3166: else if(pkthdr.baud==2) { /* Type 2.2 Packet Header */
3167: memcpy(&two_two,&pkthdr.empty,20);
3168: pkt_faddr.point=pkthdr.month; }
3169: printf("Sending to %s\n",faddrtoa(pkt_faddr));
3170: pack_bundle(packet,pkt_faddr); }
3171: else {
3172: fclose(fidomsg);
3173: printf("Possibly still in use\n"); } }
3174: #ifdef __WATCOMC__
3175: _dos_findclose(&ff);
3176: #endif
3177: }
3178: /******************************************************************************
3179: This is where we put outgoing messages into packets. Set the 'cleanup'
3180: parameter to 1 to force all the remaining packets closed and stuff them into
3181: a bundle.
3182: ******************************************************************************/
3183: void pkt_to_pkt(uchar HUGE16 *fbuf,areasbbs_t area,faddr_t faddr
3184: ,fmsghdr_t fmsghdr,addrlist_t seenbys,addrlist_t paths,char cleanup)
3185: {
3186: int i,j,k,file;
3187: short node;
3188: time_t now;
3189: struct tm *tm;
3190: pkthdr_t pkthdr;
3191: static ushort openpkts,totalpkts;
3192: static outpkt_t outpkt[MAX_TOTAL_PKTS];
3193: faddr_t sysaddr;
3194: two_two_t two;
3195: two_plus_t two_p;
3196:
3197:
3198: if(cleanup==1) {
3199: for(i=0;i<totalpkts;i++) {
1.1.1.2 ! root 3200: if(i>=MAX_TOTAL_PKTS) {
! 3201: printf("MAX_TOTAL_PKTS (%d) REACHED!\n",MAX_TOTAL_PKTS);
! 3202: logprintf("MAX_TOTAL_PKTS (%d) REACHED!\n",MAX_TOTAL_PKTS);
! 3203: break;
! 3204: }
1.1 root 3205: if(outpkt[i].curopen) {
3206: fputc(0,outpkt[i].stream);
3207: fputc(0,outpkt[i].stream);
3208: fclose(outpkt[i].stream); }
3209: else {
3210: if((outpkt[i].stream=fnopen(&file,outpkt[i].filename
3211: ,O_WRONLY|O_APPEND))==NULL) {
3212: printf("ERROR opening %s for write.\n",outpkt[i].filename);
3213: logprintf("ERROR line %d opening %s %s",__LINE__
3214: ,outpkt[i].filename,sys_errlist[errno]);
3215: continue; }
3216: fputc(0,outpkt[i].stream);
3217: fputc(0,outpkt[i].stream);
3218: fclose(outpkt[i].stream); }
3219: // pack_bundle(outpkt[i].filename,outpkt[i].uplink);
3220: memset(&outpkt[i],0,sizeof(outpkt_t)); }
3221: totalpkts=openpkts=0;
3222: attach_bundles();
3223: attachment(0,faddr,1);
3224: return; }
3225:
3226: if(fbuf==NULL) {
3227: printf("ERROR allocating fbuf\n");
3228: logprintf("ERROR line %d allocating fbuf",__LINE__);
3229: return; }
3230: /* We want to see if there's already a packet open for this area. */
3231: /* If not, we'll open a new one. Once we have a packet, we'll add */
3232: /* messages to it as they come in. If necessary, we'll close an */
3233: /* open packet to open a new one. */
3234:
3235: for(j=0;j<area.uplinks;j++) {
3236: if((cleanup==2 && memcmp(&faddr,&area.uplink[j],sizeof(faddr_t))) ||
3237: (!cleanup && (!memcmp(&faddr,&area.uplink[j],sizeof(faddr_t)) ||
3238: check_psb(seenbys,area.uplink[j]))))
3239: continue;
3240: node=matchnode(area.uplink[j],0);
3241: if(node<cfg.nodecfgs && cfg.nodecfg[node].attr&ATTR_PASSIVE)
3242: continue;
3243: sysaddr=getsysfaddr(area.uplink[j].zone);
3244: printf("%s ",faddrtoa(area.uplink[j]));
3245: for(i=0;i<totalpkts;i++) {
1.1.1.2 ! root 3246: if(i>=MAX_TOTAL_PKTS) {
! 3247: printf("MAX_TOTAL_PKTS (%d) REACHED!\n",MAX_TOTAL_PKTS);
! 3248: logprintf("MAX_TOTAL_PKTS (%d) REACHED!\n",MAX_TOTAL_PKTS);
! 3249: break;
! 3250: }
1.1 root 3251: if(!memcmp(&area.uplink[j],&outpkt[i].uplink,sizeof(faddr_t))) {
3252: if(!outpkt[i].curopen) {
3253: if(openpkts==DFLT_OPEN_PKTS)
3254: for(k=0;k<totalpkts;k++) {
3255: if(outpkt[k].curopen) {
3256: fclose(outpkt[k].stream);
3257: outpkt[k].curopen=0;
3258: break; } }
3259: if((outpkt[i].stream=fnopen(&file,outpkt[i].filename
3260: ,O_WRONLY|O_APPEND))==NULL) {
3261: printf("Unable to open %s for write.\n"
3262: ,outpkt[i].filename);
3263: logprintf("ERROR line %d opening %s %s",__LINE__
3264: ,outpkt[i].filename,sys_errlist[errno]);
3265: exit(1); }
3266: outpkt[i].curopen=1; }
3267: if((strlen((char *)fbuf)+1+ftell(outpkt[i].stream))
3268: <=cfg.maxpktsize) {
3269: fmsghdr.destnode=area.uplink[j].node;
3270: fmsghdr.destnet=area.uplink[j].net;
3271: fmsghdr.destzone=area.uplink[j].zone;
3272: putfmsg(outpkt[i].stream,fbuf,fmsghdr,area,seenbys,paths); }
3273: else {
3274: fputc(0,outpkt[i].stream);
3275: fputc(0,outpkt[i].stream);
3276: fclose(outpkt[i].stream);
3277: // pack_bundle(outpkt[i].filename,outpkt[i].uplink);
3278: outpkt[i].stream=outpkt[totalpkts-1].stream;
3279: memcpy(&outpkt[i],&outpkt[totalpkts-1],sizeof(outpkt_t));
3280: memset(&outpkt[totalpkts-1],0,sizeof(outpkt_t));
3281: --totalpkts;
3282: --openpkts;
3283: i=totalpkts; }
3284: break; } }
3285: if(i==totalpkts) {
3286: if(openpkts==DFLT_OPEN_PKTS)
3287: for(k=0;k<totalpkts;k++) {
3288: if(outpkt[k].curopen) {
3289: fclose(outpkt[k].stream);
3290: outpkt[k].curopen=0;
3291: --openpkts;
3292: break; } }
3293: strcpy(outpkt[i].filename,pktname());
3294: now=time(NULL);
3295: tm=gmtime(&now);
3296: if((outpkt[i].stream=fnopen(&file,outpkt[i].filename
3297: ,O_WRONLY|O_CREAT))==NULL) {
3298: printf("Unable to open %s for write.\n"
3299: ,outpkt[i].filename);
3300: logprintf("ERROR line %d opening %s %s"
3301: ,__LINE__,outpkt[i].filename,sys_errlist[errno]);
3302: exit(1); }
3303: pkthdr.orignode=sysaddr.node;
3304: fmsghdr.destnode=pkthdr.destnode=area.uplink[j].node;
3305: if(cfg.nodecfg[node].pkt_type==PKT_TWO_TWO) {
3306: pkthdr.year=sysaddr.point;
3307: pkthdr.month=area.uplink[j].point;
3308: pkthdr.day=0;
3309: pkthdr.hour=0;
3310: pkthdr.min=0;
3311: pkthdr.sec=0;
3312: pkthdr.baud=0x0002; }
3313: else {
1.1.1.2 ! root 3314: pkthdr.year=tm->tm_year+1900;
1.1 root 3315: pkthdr.month=tm->tm_mon;
3316: pkthdr.day=tm->tm_mday;
3317: pkthdr.hour=tm->tm_hour;
3318: pkthdr.min=tm->tm_min;
3319: pkthdr.sec=tm->tm_sec;
3320: pkthdr.baud=0; }
3321: pkthdr.pkttype=0x0002;
3322: pkthdr.orignet=sysaddr.net;
3323: fmsghdr.destnet=pkthdr.destnet=area.uplink[j].net;
3324: pkthdr.prodcode=0;
3325: pkthdr.sernum=0;
3326: if(node<cfg.nodecfgs)
3327: memcpy(pkthdr.password,cfg.nodecfg[node].pktpwd,8);
3328: else
3329: memset(pkthdr.password,0,8);
3330: pkthdr.origzone=sysaddr.zone;
3331: fmsghdr.destzone=pkthdr.destzone=area.uplink[j].zone;
3332: memset(pkthdr.empty,0,sizeof(two_two_t));
3333:
3334: if(cfg.nodecfg[node].pkt_type==PKT_TWO_TWO) {
3335: memset(&two,0,20);
3336: strcpy(two.origdomn,"fidonet");
3337: strcpy(two.destdomn,"fidonet");
3338: memcpy(&pkthdr.empty,&two,20); }
3339: else if(cfg.nodecfg[node].pkt_type==PKT_TWO_PLUS) {
3340: memset(&two_p,0,20);
3341: if(sysaddr.point) {
3342: pkthdr.orignet=-1;
3343: two_p.auxnet=sysaddr.net; }
3344: two_p.cwcopy=0x0100;
3345: two_p.prodcode=pkthdr.prodcode;
3346: two_p.revision=pkthdr.sernum;
3347: two_p.cword=0x0001;
3348: two_p.origzone=pkthdr.origzone;
3349: two_p.destzone=pkthdr.destzone;
3350: two_p.origpoint=sysaddr.point;
3351: two_p.destpoint=area.uplink[j].point;
3352: memcpy(&pkthdr.empty,&two_p,sizeof(two_plus_t)); }
3353:
3354: fwrite(&pkthdr,sizeof(pkthdr_t),1,outpkt[totalpkts].stream);
3355: putfmsg(outpkt[totalpkts].stream,fbuf,fmsghdr,area,seenbys,paths);
3356: outpkt[totalpkts].curopen=1;
3357: memcpy(&outpkt[totalpkts].uplink,&area.uplink[j]
3358: ,sizeof(faddr_t));
3359: ++openpkts;
3360: ++totalpkts;
3361: if(totalpkts>=MAX_TOTAL_PKTS) {
3362: fclose(outpkt[totalpkts-1].stream);
3363: // pack_bundle(outpkt[totalpkts-1].filename
3364: // ,outpkt[totalpkts-1].uplink);
3365: --totalpkts;
3366: --openpkts; }
3367: } }
3368: }
3369:
3370: /**************************************/
3371: /* Send netmail, returns 0 on success */
3372: /**************************************/
3373: int import_netmail(char *path,fmsghdr_t hdr, FILE *fidomsg)
3374: {
3375: uchar info[512],str[256],tmp[256],subj[256]
3376: ,HUGE16 *fmsgbuf=NULL,*p,*tp,*sp;
3377: int i,match,usernumber;
3378: ulong l;
3379: faddr_t addr;
3380:
3381: hdr.destzone=hdr.origzone=sys_faddr.zone;
3382: hdr.destpoint=hdr.origpoint=0;
3383: getzpt(fidomsg,&hdr); /* use kludge if found */
3384: for(match=0;match<total_faddrs;match++)
3385: if((hdr.destzone==faddr[match].zone || misc&FUZZY_ZONE)
3386: && hdr.destnet==faddr[match].net
3387: && hdr.destnode==faddr[match].node
3388: && hdr.destpoint==faddr[match].point)
3389: break;
3390: if(match<total_faddrs && misc&FUZZY_ZONE)
3391: hdr.origzone=hdr.destzone=faddr[match].zone;
3392: if(hdr.origpoint)
3393: sprintf(tmp,".%u",hdr.origpoint);
3394: else
3395: tmp[0]=0;
3396: if(hdr.destpoint)
3397: sprintf(str,".%u",hdr.destpoint);
3398: else
3399: str[0]=0;
3400: sprintf(info,"%s%s%s (%u:%u/%u%s) To: %s (%u:%u/%u%s)"
3401: ,path,path[0] ? " ":""
3402: ,hdr.from,hdr.origzone,hdr.orignet,hdr.orignode,tmp
3403: ,hdr.to,hdr.destzone,hdr.destnet,hdr.destnode,str);
3404: printf("%s ",info);
3405:
3406: if(!(misc&IMPORT_NETMAIL)) {
3407: if(!path[0]) {
3408: fmsgbuf=getfmsg(fidomsg,&l);
3409: if(!fmsgbuf) {
3410: printf("ERROR Netmail allocation");
3411: logprintf("ERROR line %d netmail allocation",__LINE__);
3412: return(2); }
3413:
3414: if(!l && misc&KILL_EMPTY_MAIL)
3415: printf("Empty NetMail - ");
3416: else {
3417: for(i=1;i;i++) {
3418: sprintf(str,"%s%u.MSG",netmail_dir,i);
3419: if(!fexist(str))
3420: break; }
3421: if(!i) {
3422: printf("Too many netmail messages");
3423: logprintf("Too many netmail messages");
3424: return(2); }
3425: if((i=nopen(str,O_WRONLY|O_CREAT))==-1) {
3426: printf("ERROR opening %s",str);
3427: logprintf("ERROR opening %s",str);
3428: return(2); }
3429: write(i,&hdr,sizeof(hdr));
3430: write(i,fmsgbuf,strlen((char *)fmsgbuf)+1); /* Write the NULL too */
3431: close(i); }
3432: FREE(fmsgbuf); }
3433: printf("Ignored");
3434: if(cfg.log&LOG_IGNORED)
3435: logprintf("%s Ignored",info);
3436: return(-1); }
3437:
3438: if(hdr.attr&FIDO_ORPHAN) {
3439: printf("Orphaned");
3440: return(1); }
3441: if(!(misc&IGNORE_ADDRESS) && match==total_faddrs && path[0]) {
3442: printf("Skipped");
3443: return(2); }
3444: if(!(misc&IGNORE_RECV) && hdr.attr&FIDO_RECV) {
3445: printf("Already received");
3446: return(3); }
3447: if(hdr.attr&FIDO_LOCAL && !(misc&LOCAL_NETMAIL)) {
3448: printf("Created locally");
3449: return(4); }
3450:
3451: if(email->shd_fp==NULL) {
3452: sprintf(email->file,"%sMAIL",data_dir);
3453: email->retry_time=smb_retry_time;
3454: if((i=smb_open(email))!=0) {
3455: printf("ERROR %d opening %s\n",i,email->file);
3456: logprintf("ERROR %d line %d opening %s",i,__LINE__,email->file);
3457: exit(1); } }
3458:
3459: if(!filelength(fileno(email->shd_fp))) {
3460: email->status.max_crcs=mail_maxcrcs;
3461: email->status.max_msgs=MAX_SYSMAIL;
3462: email->status.max_age=mail_maxage;
3463: email->status.attr=SMB_EMAIL;
3464: if((i=smb_create(email))!=0) {
3465: sprintf(str,"ERROR %d creating %s",i,email->file);
3466: printf("%s\n",str);
3467: logprintf(str);
3468: exit(1); } }
3469:
3470: if(!stricmp(hdr.to,"AREAFIX") || !stricmp(hdr.to,"SBBSECHO")) {
3471: fmsgbuf=getfmsg(fidomsg,NULL);
3472: if(path[0]) {
3473: if(misc&DELETE_NETMAIL) {
3474: fclose(fidomsg);
3475: if(delfile(path))
3476: logprintf("ERROR line %d removing %s %s",__LINE__,path
3477: ,sys_errlist[errno]); }
3478: else {
3479: hdr.attr|=FIDO_RECV;
3480: fseek(fidomsg,0L,SEEK_SET);
3481: fwrite(&hdr,sizeof(fmsghdr_t),1,fidomsg);
3482: fclose(fidomsg); } } /* Gotta close it here for areafix stuff */
3483: addr.zone=hdr.origzone;
3484: addr.net=hdr.orignet;
3485: addr.node=hdr.orignode;
3486: addr.point=hdr.origpoint;
3487: strcpy(hdr.to,sys_op);
3488: strcpy(hdr.from,"SBBSecho");
3489: strcpy(str,hdr.subj);
3490: strcpy(hdr.subj,"Areafix Request");
3491: hdr.origzone=hdr.orignet=hdr.orignode=hdr.origpoint=0;
3492: p=process_areafix(addr,fmsgbuf,str);
3493: #if 0 // Not necessary with SMBLIB v2.0
3494: if((i=smb_locksmbhdr(email))!=0) {
3495: printf("ERROR %d locking %s smbhdr",i,email->file);
3496: logprintf("ERROR %d line %d locking %s smbhdr",i,__LINE__,email->file);
3497: exit(1); }
3498: if((i=smb_getstatus(email))!=0) {
3499: printf("ERROR %d reading %s status header",i,email->file);
3500: logprintf("ERROR %d line %d reading %s status header",i,__LINE__
3501: ,email->file);
3502: exit(1); }
3503: #endif
3504: if(p && cfg.notify)
3505: if(fmsgtosmsg(p,hdr,cfg.notify,INVALID_SUB)==1) {
3506: sprintf(str,"\7\1n\1hSBBSecho \1n\1msent you mail\r\n");
3507: putsmsg(cfg.notify,str); }
3508: // smb_unlocksmbhdr(email);
3509: if(fmsgbuf)
3510: FREE(fmsgbuf);
3511: if(cfg.log&LOG_AREAFIX)
3512: logprintf(info);
3513: return(-2); }
3514:
3515: usernumber=atoi(hdr.to);
3516: if(!stricmp(hdr.to,"SYSOP")) /* NetMail to "sysop" goes to #1 */
3517: usernumber=1;
3518: if(!usernumber && match<total_faddrs)
3519: usernumber=matchname(hdr.to);
3520: if(!usernumber) {
3521: if(misc&UNKNOWN_NETMAIL && match<total_faddrs) /* receive unknown user */
3522: usernumber=1; /* mail to 1 */
3523: else {
3524: if(match<total_faddrs) {
3525: printf("Unknown user ");
3526: if(cfg.log&LOG_UNKNOWN)
3527: logprintf("%s Unknown user",info); }
3528: /***
3529: hdr.attr|=FIDO_ORPHAN;
3530: fseek(fidomsg,0L,SEEK_SET);
3531: fwrite(&hdr,sizeof(fmsghdr_t),1,fidomsg);
3532: ***/
3533: if(!path[0]) {
3534: fmsgbuf=getfmsg(fidomsg,&l);
3535: if(!fmsgbuf) {
3536: printf("ERROR Netmail allocation");
3537: logprintf("ERROR line %d netmail allocation",__LINE__);
3538: return(2); }
3539: if(!l && misc&KILL_EMPTY_MAIL) {
3540: printf("Empty NetMail - Ignored");
3541: if(cfg.log&LOG_IGNORED)
3542: logprintf("%s Empty - Ignored",info); }
3543: else {
3544: for(i=1;i;i++) {
3545: sprintf(str,"%s%u.MSG",netmail_dir,i);
3546: if(!fexist(str))
3547: break; }
3548: if(!i) {
3549: printf("Too many netmail messages");
3550: logprintf("Too many netmail messages");
3551: return(2); }
3552: if((i=nopen(str,O_WRONLY|O_CREAT))==-1) {
3553: printf("ERROR opening %s",str);
3554: logprintf("ERROR opening %s",str);
3555: return(2); }
3556: write(i,&hdr,sizeof(hdr));
3557: write(i,fmsgbuf,strlen((char *)fmsgbuf)+1); /* Write the NULL too */
3558: close(i); }
3559: FREE(fmsgbuf); }
3560: return(2); } }
3561:
3562: /*********************/
3563: /* Importing NetMail */
3564: /*********************/
3565:
3566: fmsgbuf=getfmsg(fidomsg,&l);
3567:
3568: #if 0 // Unnecessary with SMBLIB v2.0
3569: if((i=smb_locksmbhdr(email))!=0) {
3570: printf("ERROR %d locking %s smbhdr",i,email->file);
3571: logprintf("ERROR %d line %d locking %s smbhdr",i,__LINE__,email->file);
3572: exit(1); }
3573: if((i=smb_getstatus(email))!=0) {
3574: printf("ERROR %d reading %s status header",i,email->file);
3575: logprintf("ERROR %d line %d reading %s status header"
3576: ,i,__LINE__,email->file);
3577: exit(1); }
3578: #endif
3579:
3580: if(!l && misc&KILL_EMPTY_MAIL) {
3581: printf("Empty NetMail - Ignored");
3582: if(cfg.log&LOG_IGNORED)
3583: logprintf("%s Empty - Ignored",info);
3584: if(fmsgbuf)
3585: FREE(fmsgbuf);
3586: return(0); }
3587:
3588: i=fmsgtosmsg(fmsgbuf,hdr,usernumber,INVALID_SUB);
3589: if(i!=1) {
3590: printf("ERROR (%d) Importing",i);
3591: logprintf("ERROR (%d) Importing %s",i,info);
3592: if(fmsgbuf)
3593: FREE(fmsgbuf);
3594: return(10); }
3595:
3596: addr.zone=hdr.origzone;
3597: addr.net=hdr.orignet;
3598: addr.node=hdr.orignode;
3599: addr.point=hdr.origpoint;
3600: sprintf(str,"\7\1n\1hSBBSecho: \1m%.36s \1n\1msent you NetMail from "
3601: "\1h%s\1n\r\n",hdr.from,faddrtoa(addr));
3602: putsmsg(usernumber,str);
3603:
3604: if(hdr.attr&FIDO_FILE) { /* File attachment */
3605: strcpy(subj,hdr.subj);
3606: tp=subj;
3607: while(1) {
3608: p=strchr(tp,SP);
3609: if(p) *p=0;
3610: sp=strrchr(tp,'/'); /* sp is slash pointer */
3611: if(!sp) sp=strrchr(tp,'\\');
3612: if(sp) tp=sp+1;
3613: sprintf(str,"%s%s",fidofile_dir,tp);
3614: sprintf(tmp,"%sFILE\\%04u.IN",data_dir,usernumber);
3615: mkdir(tmp);
3616: strcat(tmp,"\\");
3617: strcat(tmp,tp);
3618: mv(str,tmp,0);
3619: if(!p)
3620: break;
3621: tp=p+1; } }
3622: netmail++;
3623:
3624: if(fmsgbuf)
3625: FREE(fmsgbuf);
3626:
3627: /***************************/
3628: /* Updating message header */
3629: /***************************/
3630: /*** NOT packet compatible
3631: if(!(misc&DONT_SET_RECV)) {
3632: hdr.attr|=FIDO_RECV;
3633: fseek(fidomsg,0L,SEEK_SET);
3634: fwrite(&hdr,sizeof(fmsghdr_t),1,fidomsg); }
3635: ***/
3636: if(cfg.log&LOG_IMPORTED)
3637: logprintf("%s Imported",info);
3638: return(0);
3639: }
3640:
3641: /******************************************************************************
3642: This is where we export echomail. This was separated from function main so
3643: it could be used for the remote rescan function. Passing anything but an
3644: empty address as 'addr' designates that a rescan should be done for that
3645: address.
3646: ******************************************************************************/
3647: void export_echomail(char *sub_code,faddr_t addr)
3648: {
3649: char str[1025],tear,cr,HUGE16 *buf;
3650: uchar HUGE16 *fmsgbuf=NULL;
3651: int g,i,j,k,file;
3652: ulong f,l,m,exp,ptr,msgs,lastmsg,posts,exported=0;
3653: float export_time;
3654: smbmsg_t msg;
3655: fmsghdr_t hdr;
3656: struct tm *tm;
3657: faddr_t pkt_faddr;
3658: post_t HUGE16 *post;
3659: areasbbs_t fakearea,curarea;
3660: addrlist_t msg_seen,msg_path;
3661: clock_t start_tick=0,export_ticks=0;
3662:
3663: memset(&msg_seen,0,sizeof(addrlist_t));
3664: memset(&msg_path,0,sizeof(addrlist_t));
3665: memset(&pkt_faddr,0,sizeof(faddr_t));
3666: start_tick=0;
3667:
3668: printf("\nScanning for Outbound EchoMail...\n");
3669:
3670: for(g=0;g<total_grps;g++)
3671: for(i=0;i<total_subs;i++)
3672: if(sub[i]->misc&SUB_FIDO && sub[i]->grp==g) {
3673: for(j=0;j<cfg.areas;j++) /* Skip areas with no uplinks */
3674: if(cfg.area[j].sub==i)
3675: break;
3676: if(j==cfg.areas || (j<cfg.areas && !cfg.area[j].uplinks))
3677: continue;
3678: if(addr.zone) { /* Skip areas not meant for this address */
3679: if(j<cfg.areas)
3680: for(k=0;k<cfg.area[j].uplinks;k++)
3681: if(!memcmp(&cfg.area[j].uplink[k],&addr,sizeof(faddr_t)))
3682: break;
3683: if(k==cfg.area[j].uplinks)
3684: continue; }
3685: if(sub_code[0] && stricmp(sub_code,sub[i]->code))
3686: continue;
3687: printf("\nScanning %-15.15s %s\n"
3688: ,grp[sub[i]->grp]->sname,sub[i]->lname);
3689: ptr=0;
3690: if(!addr.zone && !(misc&IGNORE_MSGPTRS)) {
3691: sprintf(str,"%s%s.SFP",sub[i]->data_dir,sub[i]->code);
3692: if((file=nopen(str,O_RDONLY))!=-1) {
3693: read(file,&ptr,sizeof(time_t));
3694: close(file); } }
3695:
3696: msgs=getlastmsg(i,&lastmsg,0);
3697: if(!msgs || (!addr.zone && !(misc&IGNORE_MSGPTRS) && ptr>=lastmsg)) {
3698: printf("No new messages.");
3699: if(ptr>lastmsg && !addr.zone && !(misc&LEAVE_MSGPTRS)) {
3700: printf("Fixing new-scan pointer.");
3701: sprintf(str,"%s%s.SFP",sub[i]->data_dir,sub[i]->code);
3702: if((file=nopen(str,O_WRONLY|O_CREAT))==-1) {
3703: printf("\7ERROR opening/creating %s",str);
3704: logprintf("ERROR line %d opening/creating %s"
3705: ,__LINE__,str); }
3706: else {
3707: write(file,&lastmsg,4);
3708: close(file); } }
3709: continue; }
3710:
3711: sprintf(smb[cur_smb].file,"%s%s"
3712: ,sub[i]->data_dir,sub[i]->code);
3713: smb[cur_smb].retry_time=smb_retry_time;
3714: if((j=smb_open(&smb[cur_smb]))!=0) {
3715: printf("ERROR %d opening %s\n",j,smb[cur_smb].file);
3716: logprintf("ERROR %d line %d opening %s",j,__LINE__
3717: ,smb[cur_smb].file);
3718: continue; }
3719:
3720: post=NULL;
3721: posts=loadmsgs(&post,ptr);
3722:
3723: if(!posts) { /* no new messages */
3724: smb_close(&smb[cur_smb]);
3725: if(post)
3726: LFREE(post);
3727: continue; }
3728:
3729: if(start_tick)
3730: export_ticks+=clock()-start_tick;
3731: start_tick=clock();
3732:
3733: for(m=exp=0;m<posts;m++) {
3734: printf("\r%8s %5lu of %-5lu "
3735: ,sub[i]->code,m+1,posts);
3736: msg.idx.offset=post[m].offset;
3737: if((k=smb_lockmsghdr(&smb[cur_smb],&msg))!=0) {
3738: printf("ERROR %d locking %s msghdr\n",k,smb[cur_smb].file);
3739: logprintf("ERROR %d line %d locking %s msghdr\n"
3740: ,k,__LINE__,smb[cur_smb].file);
3741: continue; }
3742: k=smb_getmsghdr(&smb[cur_smb],&msg);
3743: if(k || msg.hdr.number!=post[m].number) {
3744: smb_unlockmsghdr(&smb[cur_smb],&msg);
3745: smb_freemsgmem(&msg);
3746:
3747: msg.hdr.number=post[m].number;
3748: if((k=smb_getmsgidx(&smb[cur_smb],&msg))!=0) {
3749: printf("ERROR %d reading %s index\n",k,smb[cur_smb].file);
3750: logprintf("ERROR %d line %d reading %s index",k,__LINE__
3751: ,smb[cur_smb].file);
3752: continue; }
3753: if((k=smb_lockmsghdr(&smb[cur_smb],&msg))!=0) {
3754: printf("ERROR %d locking %s msghdr\n",k,smb[cur_smb].file);
3755: logprintf("ERROR %d line %d locking %s msghdr",k,__LINE__
3756: ,smb[cur_smb].file);
3757: continue; }
3758: if((k=smb_getmsghdr(&smb[cur_smb],&msg))!=0) {
3759: smb_unlockmsghdr(&smb[cur_smb],&msg);
3760: printf("ERROR %d reading %s msghdr\n",k,smb[cur_smb].file);
3761: logprintf("ERROR %d line %d reading %s msghdr",k,__LINE__
3762: ,smb[cur_smb].file);
3763: continue; } }
3764:
3765: if((!addr.zone && !(misc&EXPORT_ALL)
3766: && msg.from_net.type==NET_FIDO)
3767: || !strnicmp(msg.subj,"NE:",3)) { /* no echo */
3768: smb_unlockmsghdr(&smb[cur_smb],&msg);
3769: smb_freemsgmem(&msg);
3770: continue; } /* From a Fido node, ignore it */
3771:
3772: if(msg.from_net.type && msg.from_net.type!=NET_FIDO
3773: && !(sub[i]->misc&SUB_GATE)) {
3774: smb_unlockmsghdr(&smb[cur_smb],&msg);
3775: smb_freemsgmem(&msg);
3776: continue; }
3777:
3778: memset(&hdr,0,sizeof(fmsghdr_t)); /* Zero the header */
3779: hdr.origzone=sub[i]->faddr.zone;
3780: hdr.orignet=sub[i]->faddr.net;
3781: hdr.orignode=sub[i]->faddr.node;
3782: hdr.origpoint=sub[i]->faddr.point;
3783:
3784: hdr.attr=FIDO_LOCAL;
3785: if(msg.hdr.attr&MSG_PRIVATE)
3786: hdr.attr|=FIDO_PRIVATE;
3787:
3788: sprintf(hdr.from,"%.35s",msg.from);
3789:
3790: tm=gmtime((time_t *)&msg.hdr.when_written.time);
3791: sprintf(hdr.time,"%02u %3.3s %02u %02u:%02u:%02u"
1.1.1.2 ! root 3792: ,tm->tm_mday,mon[tm->tm_mon],TM_YEAR(tm->tm_year)
1.1 root 3793: ,tm->tm_hour,tm->tm_min,tm->tm_sec);
3794:
3795: sprintf(hdr.to,"%.35s",msg.to);
3796:
3797: sprintf(hdr.subj,"%.71s",msg.subj);
3798:
3799: buf=smb_getmsgtxt(&smb[cur_smb],&msg,GETMSGTXT_TAILS);
3800: if(!buf) {
3801: smb_unlockmsghdr(&smb[cur_smb],&msg);
3802: smb_freemsgmem(&msg);
3803: continue; }
3804: fmsgbuf=MALLOC(strlen((char *)buf)+512);
3805: if(!fmsgbuf) {
3806: printf("ERROR allocating %lu bytes for fmsgbuf\n");
3807: logprintf("ERROR line %d allocating %lu bytes for fmsgbuf"
3808: ,__LINE__,strlen((char *)buf)+512);
3809: smb_unlockmsghdr(&smb[cur_smb],&msg);
3810: smb_freemsgmem(&msg);
3811: continue; }
3812:
3813: tear=0;
3814: for(l=f=0,cr=1;buf[l];l++) {
3815: if(buf[l]==1) { /* Ctrl-A, so skip it and the next char */
3816: l++;
3817: if(!buf[l])
3818: break;
3819: continue; }
3820: if(buf[l]==LF) /* Ignore line feeds */
3821: continue;
3822: if(cr) {
3823: if(buf[l]=='-' && buf[l+1]=='-'
3824: && buf[l+2]=='-'
3825: && (buf[l+3]==SP || buf[l+3]==CR)) {
3826: if(misc&CONVERT_TEAR) /* Convert to === */
3827: buf[l]=buf[l+1]=buf[l+2]='=';
3828: else
3829: tear=1; }
3830: else if(!strncmp((char *)buf+l," * Origin: ",11))
3831: buf[l+1]='#'; } /* Convert * Origin into # Origin */
3832:
3833: if(buf[l]==CR)
3834: cr=1;
3835: else
3836: cr=0;
3837: if(sub[i]->misc&SUB_ASCII || misc&ASCII_ONLY) {
3838: if(buf[l]<SP && buf[l]!=CR) /* Ctrl ascii */
3839: buf[l]='.'; /* converted to '.' */
3840: if((uchar)buf[l]>0x7f) /* extended ASCII */
3841: buf[l]='*'; } /* converted to '*' */
3842:
3843: fmsgbuf[f++]=buf[l]; }
3844:
3845: FREE(buf);
3846: fmsgbuf[f]=0;
3847:
3848: if(!(sub[i]->misc&SUB_NOTAG)) {
3849: if(!tear) { /* No previous tear line */
3850: sprintf(str,"--- Synchronet+SBBSecho v%s\r",SBBSECHO_VER);
3851: strcat((char *)fmsgbuf,str); }
3852:
3853: sprintf(str," * Origin: %s (%s)\r"
3854: ,sub[i]->origline[0] ? sub[i]->origline : origline
3855: ,faddrtoa(sub[i]->faddr));
3856: strcat((char *)fmsgbuf,str); }
3857:
3858: for(k=0;k<cfg.areas;k++)
3859: if(cfg.area[k].sub==i) {
3860: cfg.area[k].exported++;
3861: pkt_to_pkt(fmsgbuf,cfg.area[k]
3862: ,(addr.zone) ? addr:pkt_faddr,hdr,msg_seen
3863: ,msg_path,(addr.zone) ? 2:0);
3864: break; }
3865: FREE(fmsgbuf);
3866: exported++;
3867: exp++;
3868: printf("Exp: %lu ",exp);
3869: smb_unlockmsghdr(&smb[cur_smb],&msg);
3870: smb_freemsgmem(&msg); }
3871:
3872: smb_close(&smb[cur_smb]);
3873: LFREE(post);
3874:
3875: /***********************/
3876: /* Update FIDO_PTR.DAB */
3877: /***********************/
3878: if(!addr.zone && !(misc&LEAVE_MSGPTRS) && lastmsg>ptr) {
3879: sprintf(str,"%s%s.SFP",sub[i]->data_dir,sub[i]->code);
3880: if((file=nopen(str,O_WRONLY|O_CREAT))==-1) {
3881: printf("\7ERROR opening/creating %s",str);
3882: logprintf("ERROR line %d opening/creating %s",__LINE__,str); }
3883: else {
3884: write(file,&lastmsg,4);
3885: close(file); } } }
3886:
3887: printf("\n");
3888: if(start_tick) /* Last possible increment of export_ticks */
3889: export_ticks+=clock()-start_tick;
3890:
3891: pkt_to_pkt(buf,fakearea,pkt_faddr,hdr,msg_seen,msg_path,1);
3892:
3893: if(!addr.zone && cfg.log&LOG_AREA_TOTALS && exported)
3894: for(i=0;i<cfg.areas;i++)
3895: if(cfg.area[i].exported)
3896: logprintf("Exported: %5u msgs %8s -> %s"
3897: ,cfg.area[i].exported,sub[cfg.area[i].sub]->code
3898: ,cfg.area[i].name);
3899:
3900: export_time=((float)export_ticks)/(float)CLK_TCK;
3901: if(cfg.log&LOG_TOTALS && exported && export_time) {
3902: printf("\nExported %lu EchoMail messages in %.1f seconds "
3903: ,exported,export_time);
3904: logprintf("Exported: %5lu msgs in %.1f sec (%.1f/min %.1f/sec)"
3905: ,exported,export_time
3906: ,export_time/60.0 ? (float)exported/(export_time/60.0) :(float)exported
3907: ,(float)exported/export_time);
3908: if(export_time/60.0)
3909: printf("(%.1f/min) ",(float)exported/(export_time/60.0));
3910: printf("(%.1f/sec)\n",(float)exported/export_time); }
3911:
3912: }
3913: /***********************************/
3914: /* Synchronet/FidoNet Message util */
3915: /***********************************/
3916: int main(int argc, char **argv)
3917: {
3918: FILE *fidomsg;
3919: char ch,str[1025],fname[256],path[512],sub_code[9]
3920: ,*p,*tp,*sp,*buf,cr,tear,lzh
1.1.1.2 ! root 3921: ,areatagstr[129],packet[128],outbound[128]
! 3922: ,password[16];
1.1 root 3923: uchar HUGE16 *fmsgbuf=NULL;
3924: ushort xlat,attr;
3925: int i,j,k,n,x,y,z,last,file,fmsg,g,grunged;
3926: uint subnum[MAX_OPEN_SMBS]={INVALID_SUB};
3927: ulong files,msgfiles,echomail=0,crc,ptr,
3928: l,m,f,length,lastmsg,posts,msgs,exp,areatag;
3929: time_t now;
3930: float import_time;
3931: clock_t start_tick=0,import_ticks=0;
3932: read_cfg_text_t txt;
3933: struct find_t ff;
3934: struct tm *tm;
3935: fmsghdr_t hdr;
3936: faddr_t addr,pkt_faddr;
3937: post_t HUGE16 *post;
3938: FILE *stream,*fstream;
3939: smbmsg_t msg;
3940: pkthdr_t pkthdr;
3941: addrlist_t msg_seen,msg_path;
3942: areasbbs_t fakearea,curarea;
3943: char *usage="\n"
3944: "usage: sbbsecho [cfg_file] [/switches] [sub_code]\n"
3945: "\n"
3946: "where: cfg_file is the filename of config file (default is ctrl\\sbbsecho.cfg)\n"
3947: " sub_code is the internal code for a sub-board (default is ALL subs)\n"
3948: "\n"
3949: "valid switches:\n"
3950: "\n"
3951: "p: do not import packets x: do not delete packets after import\n"
3952: "n: do not import netmail d: do not delete netmail after import\n"
3953: "i: do not import echomail e: do not export echomail\n"
3954: "m: ignore echomail ptrs (export all) u: update echomail ptrs (export none)\n"
3955: "j: ignore recieved bit on netmail t: do not update echomail ptrs\n"
3956: "l: create log file (data\\sbbsecho.log) r: create report of import totals\n"
3957: "h: export all echomail (hub rescan) b: import locally created netmail too\n"
3958: "a: export ASCII characters only f: create packets for outbound netmail\n"
3959: "g: generate notify lists =: change existing tear lines to ===\n"
3960: "y: import netmail for unknown users to sysop\n"
3961: "o: import all netmail regardless of destination address\n"
3962: "s: import private echomail override (strip private status)\n"
3963: "!: notify users of received echomail\n";
3964:
3965: if((email=(smb_t *)MALLOC(sizeof(smb_t)))==NULL) {
3966: printf("ERROR allocating memory for email.\n");
3967: exit(1); }
3968: memset(email,0,sizeof(smb_t));
3969: if((smb=(smb_t *)MALLOC(MAX_OPEN_SMBS*sizeof(smb_t)))==NULL) {
3970: printf("ERROR allocating memory for smbs.\n");
3971: exit(1); }
3972: for(i=0;i<MAX_OPEN_SMBS;i++)
3973: memset(&smb[i],0,sizeof(smb_t));
3974: memset(&cfg,0,sizeof(config_t));
3975: memset(&msg_seen,0,sizeof(addrlist_t));
3976: memset(&msg_path,0,sizeof(addrlist_t));
3977: printf("\nSBBSecho Version %s (%s) SMBLIB %s � Synchronet FidoNet Packet "
3978: "Tosser\n"
3979: ,SBBSECHO_VER
3980: #if defined(__OS2__)
3981: ,"OS/2"
3982: #elif defined(__NT__)
3983: ,"Win32"
3984: #elif defined(__DOS4G__)
3985: ,"DOS4G"
3986: #elif defined(__FLAT__)
3987: ,"DOS32"
3988: #else
3989: ,"DOS16"
3990: #endif
1.1.1.2 ! root 3991: ,smb_lib_ver()
1.1 root 3992: );
3993:
3994: putenv("TZ=UCT0");
3995: putenv("TMP=");
3996: _fmode=O_BINARY;
3997: setvbuf(stdout,NULL,_IONBF,0);
3998:
3999: txt.openerr="\7\nError opening %s for read.\n";
4000: txt.reading="\nReading %s...";
4001: txt.readit="\rRead %s ";
4002: txt.allocerr="\7\nError allocating %u bytes of memory\n";
4003: txt.error="\7\nERROR: Offset %lu in %s\n\n";
4004:
4005: node_dir[0]=sub_code[0]=0;
4006: for(i=1;i<argc;i++) {
4007: if(argv[i][0]=='/') {
4008: j=1;
4009: while(argv[i][j]) {
4010: switch(toupper(argv[i][j])) {
4011: case 'A':
4012: misc|=ASCII_ONLY;
4013: break;
4014: case 'B':
4015: misc|=LOCAL_NETMAIL;
4016: break;
4017: case 'D':
4018: misc&=~DELETE_NETMAIL;
4019: break;
4020: case 'E':
4021: misc&=~EXPORT_ECHOMAIL;
4022: break;
4023: case 'F':
4024: misc|=PACK_NETMAIL;
4025: break;
4026: case 'G':
4027: misc|=GEN_NOTIFY_LIST;
4028: break;
4029: case 'H':
4030: misc|=EXPORT_ALL;
4031: break;
4032: case 'I':
4033: misc&=~IMPORT_ECHOMAIL;
4034: break;
4035: case 'J':
4036: misc|=IGNORE_RECV;
4037: break;
4038: case 'L':
4039: misc|=LOGFILE;
4040: break;
4041: case 'M':
4042: misc|=IGNORE_MSGPTRS;
4043: break;
4044: case 'N':
4045: misc&=~IMPORT_NETMAIL;
4046: break;
4047: case 'O':
4048: misc|=IGNORE_ADDRESS;
4049: break;
4050: case 'P':
4051: misc&=~IMPORT_PACKETS;
4052: break;
4053: case 'R':
4054: misc|=REPORT;
4055: break;
4056: case 'S':
4057: misc|=IMPORT_PRIVATE;
4058: break;
4059: case 'T':
4060: misc|=LEAVE_MSGPTRS;
4061: break;
4062: case 'U':
4063: misc|=UPDATE_MSGPTRS;
4064: misc&=~EXPORT_ECHOMAIL;
4065: break;
4066: case 'X':
4067: misc&=~DELETE_PACKETS;
4068: break;
4069: case 'Y':
4070: misc|=UNKNOWN_NETMAIL;
4071: break;
4072: case '=':
4073: misc|=CONVERT_TEAR;
4074: break;
4075: case '!':
4076: misc|=NOTIFY_RECEIPT;
4077: break;
4078: case 'Q':
4079: exit(0);
4080: default:
4081: printf(usage);
4082: exit(0); }
4083: j++; } }
4084: else {
4085: if(strchr(argv[i],'\\') || argv[i][1]==':' || strchr(argv[i],'.'))
4086: sprintf(cfg.cfgfile,"%.100s",argv[i]);
4087: else
4088: sprintf(sub_code,"%.8s",argv[i]); } }
4089:
4090: if(!(misc&(IMPORT_NETMAIL|IMPORT_ECHOMAIL)))
4091: misc&=~IMPORT_PACKETS;
4092: if(!node_dir[0]) {
4093: p=getenv("SBBSNODE");
4094: if(p==NULL) {
4095: printf("\7\nSBBSNODE environment variable not set.\n");
4096: exit(1); }
4097: strcpy(node_dir,p); }
4098:
4099: strupr(node_dir);
4100:
4101: if(node_dir[strlen(node_dir)-1]!='\\')
4102: strcat(node_dir,"\\");
4103:
4104: read_node_cfg(txt);
4105: if(ctrl_dir[0]=='.') { /* Relative path */
4106: strcpy(str,ctrl_dir);
4107: sprintf(ctrl_dir,"%s%s",node_dir,str);
4108: if(_fullpath(str,ctrl_dir,40))
4109: strcpy(ctrl_dir,str); }
4110: backslash(ctrl_dir);
4111:
4112: read_main_cfg(txt);
4113: if(data_dir[0]=='.') { /* Relative path */
4114: strcpy(str,data_dir);
4115: sprintf(data_dir,"%s%s",node_dir,str);
4116: if(_fullpath(str,data_dir,40))
4117: strcpy(data_dir,str); }
4118: backslash(data_dir);
4119: if(text_dir[0]=='.') { /* Relative path */
4120: strcpy(str,text_dir);
4121: sprintf(text_dir,"%s%s",node_dir,str);
4122: if(_fullpath(str,text_dir,40))
4123: strcpy(text_dir,str); }
4124: backslash(text_dir);
4125: read_msgs_cfg(txt);
4126:
4127: #ifndef __FLAT__
4128:
4129: __spawn_ext = (node_swap & SWAP_EXT) != 0 ;
4130: __spawn_ems = (node_swap & SWAP_EMS) != 0 ;
4131: __spawn_xms = (node_swap & SWAP_XMS) != 0 ;
4132:
4133: #endif
4134:
4135: if(total_faddrs<1) {
4136: sys_faddr.zone=sys_faddr.net=sys_faddr.node=1;
4137: sys_faddr.point=0; }
4138: else
4139: sys_faddr=faddr[0];
4140:
4141: sprintf(str,"%s%s",ctrl_dir,"NODE.DAB");
4142: if((nodefile=sopen(str,O_BINARY|O_RDWR,SH_DENYNO))==-1) {
4143: printf("\n\7ERROR opening %s\n",str);
4144: exit(1); }
4145:
4146: if(!cfg.cfgfile[0])
4147: sprintf(cfg.cfgfile,"%sSBBSECHO.CFG",ctrl_dir);
4148: strcpy(cfg.inbound,fidofile_dir);
4149: sprintf(cfg.areafile,"%sAREAS.BBS",data_dir);
4150: sprintf(cfg.logfile,"%sSBBSECHO.LOG",data_dir);
4151:
4152: read_cfg();
4153:
4154: if(misc&LOGFILE)
4155: if((fidologfile=_fsopen(cfg.logfile,"ab",SH_DENYNO))==NULL) {
4156: printf("\7ERROR opening %s\n",cfg.logfile);
4157: exit(1); }
4158:
4159: if(exec_dir[0]!='\\' && exec_dir[1]!=':') {
4160: strcpy(path,node_dir);
4161: strcat(path,exec_dir);
4162: if(_fullpath(str,path,40))
4163: strcpy(path,str);
4164: backslash(path); }
4165: else
4166: strcpy(path,exec_dir);
4167:
4168: /******* READ IN AREAS.BBS FILE *********/
4169:
4170: printf("Reading %s",cfg.areafile);
4171: if((stream=fnopen(&file,cfg.areafile,O_RDONLY))==NULL) {
4172: printf("Unable to open %s for read.\n",cfg.areafile);
4173: exit(1); }
4174: cfg.areas=0; /* Total number of areas in AREAS.BBS */
4175: cfg.area=NULL;
4176: while(1) {
4177: if(!fgets(str,1024,stream))
4178: break;
4179: truncsp(str);
4180: p=str;
4181: while(*p && *p<=SP) p++; /* Find first printable char */
4182: if(*p==';' || !*p) /* Ignore blank lines or start with ; */
4183: continue;
4184: if((cfg.area=(areasbbs_t *)REALLOC(cfg.area,sizeof(areasbbs_t)*
4185: (cfg.areas+1)))==NULL) {
4186: printf("ERROR allocating memory for area #%u.\n",cfg.areas+1);
4187: exit(1); }
4188: memset(&cfg.area[cfg.areas],0,sizeof(areasbbs_t));
4189:
4190: cfg.area[cfg.areas].sub=INVALID_SUB; /* Default to passthru */
4191:
4192: sprintf(tmp,"%-.8s",p);
4193: tp=tmp;
4194: while(*tp>SP) tp++;
4195: *tp=0;
4196: for(i=0;i<total_subs;i++)
4197: if(!stricmp(tmp,sub[i]->code))
4198: break;
4199: if(i<total_subs)
4200: cfg.area[cfg.areas].sub=i;
4201: else if(stricmp(tmp,"P")) {
4202: printf("\n%s: Unrecongized internal code, assumed passthru",tmp);
4203: logprintf("%s: Unrecognized internal code, assumed passthru",tmp); }
4204:
4205: while(*p>SP) p++; /* Skip code */
4206: while(*p && *p<=SP) p++; /* Skip white space */
4207: sprintf(tmp,"%-.50s",p); /* Area tag */
4208: if((tp=strchr(tmp,TAB))!=NULL) /* Chop off any TABs */
4209: *tp=0;
4210: if((tp=strchr(tmp,SP))!=NULL) /* Chop off any spaces */
4211: *tp=0;
4212: strupr(tmp);
4213: if(tmp[0]=='*') /* UNKNOWN-ECHO area */
4214: cfg.badecho=cfg.areas;
4215: if((cfg.area[cfg.areas].name=(char *)MALLOC(strlen(tmp)+1))==NULL) {
4216: printf("ERROR allocating memory for area #%u tag name.\n"
4217: ,cfg.areas+1);
4218: exit(1); }
4219: strcpy(cfg.area[cfg.areas].name,tmp);
4220: strupr(tmp);
4221: cfg.area[cfg.areas].tag=crc32(tmp);
4222:
4223: while(*p>SP) p++; /* Skip tag */
4224: while(*p && *p<=SP) p++; /* Skip white space */
4225:
4226: while(*p && *p!=';') {
4227: if((cfg.area[cfg.areas].uplink=(faddr_t *)
4228: REALLOC(cfg.area[cfg.areas].uplink
4229: ,sizeof(faddr_t)*(cfg.area[cfg.areas].uplinks+1)))==NULL) {
4230: printf("ERROR allocating memory for area #%u uplinks.\n"
4231: ,cfg.areas+1);
4232: exit(1); }
4233: cfg.area[cfg.areas].uplink[cfg.area[cfg.areas].uplinks]=atofaddr(p);
4234: while(*p>SP) p++; /* Skip address */
4235: while(*p && *p<=SP) p++; /* Skip white space */
4236: cfg.area[cfg.areas].uplinks++; }
4237:
4238: if(cfg.area[cfg.areas].sub!=INVALID_SUB || cfg.area[cfg.areas].uplinks)
4239: cfg.areas++; /* Don't allocate if no tossing */
4240: }
4241: fclose(stream);
4242:
4243: printf("\n");
4244:
4245: if(!cfg.areas) {
4246: printf("No areas defined!\n");
4247: exit(1); }
4248:
4249: #if 0
4250: /* AREAS.BBS DEBUG */
4251: for(i=0;i<cfg.areas;i++) {
4252: printf("%4u: %-8s"
4253: ,i+1
4254: ,cfg.area[i].sub==INVALID_SUB ? "Passthru" :
4255: sub[cfg.area[i].sub]->code);
4256: for(j=0;j<cfg.area[i].uplinks;j++)
4257: printf(" %s",faddrtoa(cfg.area[i].uplink[j]));
4258: printf("\n"); }
4259: #endif
4260:
4261: if(misc&GEN_NOTIFY_LIST) {
4262: printf("\nGenerating Notify Lists...\n");
4263: notify_list(); }
4264:
4265: /* Find any packets that have been left behind in the OUTBOUND directory */
4266: printf("\nScanning for Stray Outbound Packets...\n");
4267: sprintf(path,"%s*.PK_",cfg.outbound);
4268: for(l=_dos_findfirst(path,0,&ff);!l && !kbhit();l=_dos_findnext(&ff)) {
4269: sprintf(packet,"%s%s",cfg.outbound,ff.name);
4270: printf("%21s: %s ","Outbound Packet",packet);
4271: if((fmsg=sopen(packet,O_RDWR,SH_DENYRW))==-1) {
4272: printf("ERROR opening.\n");
4273: logprintf("ERROR line %d opening %s",__LINE__,packet);
4274: continue; }
4275: if((fidomsg=fdopen(fmsg,"r+b"))==NULL) {
4276: close(fmsg);
4277: printf("\7ERROR fdopening.\n");
4278: logprintf("ERROR line %d fdopening %s",__LINE__,packet);
4279: continue; }
4280: if(filelength(fmsg)<sizeof(pkthdr_t)) {
4281: printf("ERROR invalid length of %u bytes for %s\n",filelength(fmsg)
4282: ,packet);
4283: logprintf("ERROR line %d invalid length of %u bytes for %s"
4284: ,__LINE__,filelength(fmsg),packet);
4285: fclose(fidomsg);
4286: if(delfile(packet))
4287: logprintf("ERROR line %d removing %s %s",__LINE__,packet
4288: ,sys_errlist[errno]);
4289: continue; }
4290: if(fread(&pkthdr,sizeof(pkthdr_t),1,fidomsg)!=1) {
4291: fclose(fidomsg);
4292: printf("\7ERROR reading %u bytes from %s\n",sizeof(pkthdr_t),packet);
4293: logprintf("ERROR line %d reading %u bytes from %s",__LINE__
4294: ,sizeof(pkthdr_t),packet);
4295: continue; }
4296: if((ddtol(ff.wr_time,ff.wr_date)+(60L*60L))<=time(NULL)) {
4297: fseek(fidomsg,-3L,SEEK_END);
4298: fread(str,3,1,fidomsg);
4299: if(str[2]) /* No ending NULL, probably junk */
4300: fputc(0,fidomsg);
4301: if(str[1])
4302: fputc(0,fidomsg);
4303: if(str[0])
4304: fputc(0,fidomsg);
4305: fclose(fidomsg);
4306: pkt_faddr.zone=pkthdr.destzone;
4307: pkt_faddr.net=pkthdr.destnet;
4308: pkt_faddr.node=pkthdr.destnode;
4309: pkt_faddr.point=0; /* No point info in the 2.0 hdr! */
4310: memcpy(&two_plus,&pkthdr.empty,20);
4311: if(two_plus.cword==_rotr(two_plus.cwcopy,8) /* 2+ Packet Header */
4312: && two_plus.cword && two_plus.cword&1)
4313: pkt_faddr.point=two_plus.destpoint;
4314: else if(pkthdr.baud==2) { /* Type 2.2 Packet Header */
4315: memcpy(&two_two,&pkthdr.empty,20);
4316: pkt_faddr.point=pkthdr.month; }
4317: printf("Sending to %s\n",faddrtoa(pkt_faddr));
4318: pack_bundle(packet,pkt_faddr); }
4319: else {
4320: fclose(fidomsg);
4321: printf("Possibly still in use\n"); } }
4322: #ifdef __WATCOMC__
4323: _dos_findclose(&ff);
4324: #endif
4325:
4326: if(misc&IMPORT_PACKETS) {
4327:
4328: printf("\nScanning for Inbound Packets...\n");
4329:
4330: /* We want to loop while there are bundles waiting for us, but first we want */
4331: /* to take care of any packets that may already be hanging around for some */
4332: /* reason or another (thus the do/while loop) */
4333:
4334: echomail=0;
4335: for(secure=0;secure<2;secure++) {
4336: if(secure && !cfg.secure[0])
4337: break;
4338: do {
4339: /****** START OF IMPORT PKT ROUTINE ******/
4340:
4341: sprintf(path,"%s*.PKT",secure ? cfg.secure : cfg.inbound);
4342: for(l=_dos_findfirst(path,0,&ff);!l && !kbhit();l=_dos_findnext(&ff)) {
4343:
4344: sprintf(packet,"%s%s",secure ? cfg.secure : cfg.inbound,ff.name);
4345:
4346: if((fidomsg=fnopen(&fmsg,packet,O_RDWR))==NULL) {
4347: printf("\7ERROR opening %s\n",packet);
4348: logprintf("ERROR line %d opening %s %s",__LINE__,packet
4349: ,sys_errlist[errno]);
4350: continue; }
4351: if(filelength(fmsg)<sizeof(pkthdr_t)) {
4352: printf("\7Invalid length of %u bytes\n",filelength(fmsg));
4353: fclose(fidomsg);
4354: continue; }
4355:
4356: fseek(fidomsg,-2L,SEEK_END);
4357: fread(str,2,1,fidomsg);
4358: if((str[0] || str[1]) &&
4359: (ddtol(ff.wr_time,ff.wr_date)+(48L*60L*60L))<=time(NULL)) {
4360: fclose(fidomsg);
4361: printf("\7ERROR packet %s not terminated correctly\n",packet);
4362: logprintf("ERROR line %d packet %s not terminated correctly",__LINE__
4363: ,packet);
4364: continue; }
4365: fseek(fidomsg,0L,SEEK_SET);
4366: if(fread(&pkthdr,sizeof(pkthdr_t),1,fidomsg)!=1) {
4367: fclose(fidomsg);
4368: printf("\7ERROR reading %u bytes\n",sizeof(pkthdr_t));
4369: logprintf("ERROR line %d reading %u bytes from %s",__LINE__
4370: ,sizeof(pkthdr_t),packet);
4371: continue; }
4372:
4373: pkt_faddr.zone=pkthdr.origzone ? pkthdr.origzone:sys_faddr.zone;
4374: pkt_faddr.net=pkthdr.orignet;
4375: pkt_faddr.node=pkthdr.orignode;
4376: pkt_faddr.point=0;
4377:
4378: printf("%21s: %s "
4379: ,secure ? "Importing Secure Pkt" : "Importing Packet",ff.name);
4380: memcpy(&two_plus,&pkthdr.empty,20);
4381: if(two_plus.cword==_rotr(two_plus.cwcopy,8) /* 2+ Packet Header */
4382: && two_plus.cword && two_plus.cword&1) {
4383: pkt_type=PKT_TWO_PLUS;
4384: pkt_faddr.point=two_plus.origpoint ? two_plus.origpoint:0;
4385: if(pkt_faddr.point && pkthdr.orignet==-1)
4386: pkt_faddr.net=two_plus.auxnet ? two_plus.auxnet:sys_faddr.zone;
4387: printf("(Type 2+)");
4388: if(cfg.log&LOG_PACKETS)
4389: logprintf("Importing %s%s (Type 2+) from %s"
4390: ,secure ? "(secure) ":"",ff.name,faddrtoa(pkt_faddr)); }
4391: else if(pkthdr.baud==2) { /* Type 2.2 Packet Header */
4392: pkt_type=PKT_TWO_TWO;
4393: memcpy(&two_two,&pkthdr.empty,20);
4394: pkt_faddr.point=pkthdr.year ? pkthdr.year:0;
4395: printf("(Type 2.2)");
4396: if(cfg.log&LOG_PACKETS)
4397: logprintf("Importing %s%s (Type 2.2) from %s"
4398: ,secure ? "(secure) ":"",ff.name,faddrtoa(pkt_faddr)); }
4399: else {
4400: pkt_type=PKT_TWO;
4401: printf("(Type 2)");
4402: if(cfg.log&LOG_PACKETS)
4403: logprintf("Importing %s%s (Type 2) from %s"
4404: ,secure ? "(secure) ":"",ff.name,faddrtoa(pkt_faddr)); }
4405:
4406: printf(" from %s\n",faddrtoa(pkt_faddr));
4407:
4408: if(misc&SECURE) {
4409: k=matchnode(pkt_faddr,1);
1.1.1.2 ! root 4410: sprintf(password,"%.8s",pkthdr.password);
1.1 root 4411: if(k<cfg.nodecfgs && cfg.nodecfg[k].pktpwd[0] &&
1.1.1.2 ! root 4412: stricmp(password,cfg.nodecfg[k].pktpwd)) {
1.1 root 4413: sprintf(str,"Packet %s from %s - "
4414: "Incorrect password ('%s' instead of '%s')"
4415: ,ff.name,faddrtoa(pkt_faddr)
1.1.1.2 ! root 4416: ,password,cfg.nodecfg[k].pktpwd);
1.1 root 4417: printf("Security Violation (Incorrect Password)\n");
4418: if(cfg.log&LOG_SECURITY)
4419: logprintf(str);
4420: fclose(fidomsg);
4421: continue; } }
4422:
4423: while(!feof(fidomsg)) {
4424:
4425: memset(&hdr,0,sizeof(fmsghdr_t));
4426:
4427: if(start_tick)
4428: import_ticks+=clock()-start_tick;
4429: start_tick=clock();
4430:
4431: if(fmsgbuf) {
4432: FREE(fmsgbuf);
4433: fmsgbuf=0; }
4434: if(misc&CHECKMEM)
4435: checkmem();
4436: if(!fread(&ch,1,1,fidomsg)) /* Message type (0200h) */
4437: break;
4438: if(ch!=02)
4439: continue;
4440: if(!fread(&ch,1,1,fidomsg))
4441: break;
4442: if(ch!=00)
4443: continue;
4444: fread(&hdr.orignode,2,1,fidomsg);
4445: fread(&hdr.destnode,2,1,fidomsg);
4446: fread(&hdr.orignet,2,1,fidomsg);
4447: fread(&hdr.destnet,2,1,fidomsg);
4448: fread(&hdr.attr,2,1,fidomsg);
4449: fread(&hdr.cost,2,1,fidomsg);
4450:
4451: grunged=0;
4452:
4453: for(i=0;i<sizeof(hdr.time);i++) /* Read in the Date/Time */
4454: if(!fread(hdr.time+i,1,1,fidomsg) || !hdr.time[i])
4455: break;
4456: if(i==sizeof(hdr.time)) grunged=1;
4457:
4458: for(i=0;!grunged && i<sizeof(hdr.to);i++) /* Read in the 'To' Field */
4459: if(!fread(hdr.to+i,1,1,fidomsg) || !hdr.to[i])
4460: break;
4461: if(i==sizeof(hdr.to)) grunged=1;
4462:
4463: for(i=0;!grunged && i<sizeof(hdr.from);i++) /* Read in 'From' Field */
4464: if(!fread(hdr.from+i,1,1,fidomsg) || !hdr.from[i])
4465: break;
4466: if(i==sizeof(hdr.from)) grunged=1;
4467:
4468: for(i=0;!grunged && i<sizeof(hdr.subj);i++) /* Read in 'Subj' Field */
4469: if(!fread(hdr.subj+i,1,1,fidomsg) || !hdr.subj[i])
4470: break;
4471: if(i==sizeof(hdr.subj)) grunged=1;
4472:
4473: str[0]=0;
4474: for(i=0;!grunged && i<sizeof(str);i++) /* Read in the 'AREA' Field */
4475: if(!fread(str+i,1,1,fidomsg) || str[i]==CR)
4476: break;
4477: if(i<sizeof(str))
4478: str[i]=0;
4479: else
4480: grunged=1;
4481:
4482: if(!str[0] || grunged) {
4483: start_tick=0;
4484: if(cfg.log&LOG_GRUNGED)
4485: logprintf("Grunged message");
4486: seektonull(fidomsg);
4487: printf("Grunged message!\n");
4488: continue; }
4489:
4490: if(i)
4491: fseek(fidomsg,(long)-(i+1),SEEK_CUR);
4492:
4493: truncsp(str);
4494: strupr(str);
4495: p=strstr(str,"AREA:");
4496: if(!p) { /* Netmail */
4497: start_tick=0;
4498: if(import_netmail("",hdr,fidomsg))
4499: seektonull(fidomsg);
4500: printf("\n");
4501: continue; }
4502:
4503: if(!(misc&IMPORT_ECHOMAIL)) {
4504: start_tick=0;
4505: printf("EchoMail Ignored");
4506: seektonull(fidomsg);
4507: printf("\n");
4508: continue; }
4509:
4510: p+=5; /* Skip "AREA:" */
4511: while(*p && *p<=SP) p++; /* Skip any white space */
4512: printf("%21s: ",p); /* Show areaname: */
4513: sprintf(areatagstr,"%.128s",p);
4514: strupr(p);
4515: areatag=crc32(p);
4516:
4517: for(i=0;i<cfg.areas;i++) /* Do we carry this area? */
4518: if(cfg.area[i].tag==areatag) {
4519: if(cfg.area[i].sub!=INVALID_SUB)
4520: printf("%s ",sub[cfg.area[i].sub]->code);
4521: else
4522: printf("(Passthru) ");
4523: fmsgbuf=getfmsg(fidomsg,NULL);
4524: gen_psb(&msg_seen,&msg_path,fmsgbuf,pkthdr.destzone);
4525: break; }
4526:
4527: if(i==cfg.areas) {
4528: printf("(Unknown) ");
4529: if(cfg.badecho>=0) {
4530: i=cfg.badecho;
4531: if(cfg.area[i].sub!=INVALID_SUB)
4532: printf("%s ",sub[cfg.area[i].sub]->code);
4533: else
4534: printf("(Passthru) ");
4535: fmsgbuf=getfmsg(fidomsg,NULL);
4536: gen_psb(&msg_seen,&msg_path,fmsgbuf,pkthdr.destzone); }
4537: else {
4538: start_tick=0;
4539: printf("Skipped\n");
4540: seektonull(fidomsg);
4541: continue; } }
4542:
4543: if(misc&SECURE && cfg.area[i].sub!=INVALID_SUB) {
4544: for(j=0;j<cfg.area[i].uplinks;j++)
4545: if(!memcmp(&cfg.area[i].uplink[j],&pkt_faddr,sizeof(faddr_t)))
4546: break;
4547: if(j==cfg.area[i].uplinks) {
4548: if(cfg.log&LOG_SECURITY)
4549: logprintf("%s: Security violation - %s not in AREAS.BBS"
4550: ,areatagstr,faddrtoa(pkt_faddr));
4551: printf("Security Violation (Not in AREAS.BBS)\n");
4552: seektonull(fidomsg);
4553: continue; } }
4554:
4555: /* From here on out, i = area number and area[i].sub = sub number */
4556:
4557: memcpy(&curarea,&cfg.area[i],sizeof(areasbbs_t));
4558: curarea.name=areatagstr;
4559:
4560: if(cfg.area[i].sub==INVALID_SUB) { /* Passthru */
4561: start_tick=0;
4562: strip_psb(fmsgbuf);
4563: pkt_to_pkt(fmsgbuf,curarea,pkt_faddr,hdr,msg_seen,msg_path,0);
4564: printf("\n");
4565: continue; } /* On to the next message */
4566:
4567:
4568: for(j=0;j<total_faddrs;j++)
4569: if(check_psb(msg_path,faddr[j]))
4570: break;
4571: if(j<total_faddrs) {
4572: start_tick=0;
4573: printf("Circular path (%s) ",faddrtoa(faddr[j]));
4574: cfg.area[i].circular++;
4575: if(cfg.log&LOG_CIRCULAR)
4576: logprintf("%s: Circular path detected for %s"
4577: ,areatagstr,faddrtoa(faddr[j]));
4578: strip_psb(fmsgbuf);
4579: pkt_to_pkt(fmsgbuf,curarea,pkt_faddr,hdr,msg_seen,msg_path,0);
4580: printf("\n");
4581: continue; }
4582:
4583: #if 0 // Allen's way (broken?)
4584: for(j=0;j<num_open;j++)
4585: if(openbase[j]==cfg.area[i].sub)
4586: break;
4587: if(j && j<num_open) {
4588: cur_smb=j;
4589: k=openbase[0];
4590: openbase[0]=openbase[j];
4591: openbase[j]=k; }
4592: else if(j && j==num_open && j<MAX_OPEN_SMBS) {
4593: cur_smb=j;
4594: openbase[j]=openbase[0];
4595: openbase[0]=INVALID_SUB; }
4596: else if(j==num_open && j>=MAX_OPEN_SMBS) {
4597: cur_smb=j-1;
4598: k=openbase[0];
4599: openbase[0]=openbase[j-1];
4600: openbase[j-1]=k; }
4601:
4602: if(openbase[0]!=cfg.area[i].sub) {
4603: if(openbase[0]!=INVALID_SUB) {
4604: smb_close(&smb[cur_smb]);
4605: --num_open; }
4606: #endif
4607:
4608: // Rob's way
4609: for(j=0;j<MAX_OPEN_SMBS;j++)
4610: if(subnum[j]==cfg.area[i].sub)
4611: break;
4612: if(j<MAX_OPEN_SMBS) /* already open */
4613: cur_smb=j;
4614: else {
4615: if(smb[cur_smb].shd_fp) /* If open */
4616: cur_smb=!cur_smb; /* toggle between 0 and 1 */
4617: smb_close(&smb[cur_smb]); /* close, if open */
4618: subnum[cur_smb]=INVALID_SUB; } /* reset subnum (just incase) */
4619:
4620: if(smb[cur_smb].shd_fp==NULL) { /* Currently closed */
4621: sprintf(smb[cur_smb].file,"%s%s",sub[cfg.area[i].sub]->data_dir
4622: ,sub[cfg.area[i].sub]->code);
4623: smb[cur_smb].retry_time=smb_retry_time;
4624: if((j=smb_open(&smb[cur_smb]))!=0) {
4625: sprintf(str,"ERROR %d opening %s area #%d, sub #%d)"
4626: ,j,smb[cur_smb].file,i+1,cfg.area[i].sub+1);
4627: printf(str);
4628: logprintf(str);
4629: strip_psb(fmsgbuf);
4630: pkt_to_pkt(fmsgbuf,curarea,pkt_faddr,hdr,msg_seen
4631: ,msg_path,0);
4632: printf("\n");
4633: continue; }
4634: if(!filelength(fileno(smb[cur_smb].shd_fp))) {
4635: smb[cur_smb].status.max_crcs=sub[cfg.area[i].sub]->maxcrcs;
4636: smb[cur_smb].status.max_msgs=sub[cfg.area[i].sub]->maxmsgs;
4637: smb[cur_smb].status.max_age=sub[cfg.area[i].sub]->maxage;
4638: smb[cur_smb].status.attr=sub[cfg.area[i].sub]->misc&SUB_HYPER
4639: ? SMB_HYPERALLOC:0;
4640: if((j=smb_create(&smb[cur_smb]))!=0) {
4641: sprintf(str,"ERROR %d creating %s",j,smb[cur_smb].file);
4642: printf(str);
4643: logprintf(str);
4644: smb_close(&smb[cur_smb]);
4645: strip_psb(fmsgbuf);
4646: pkt_to_pkt(fmsgbuf,curarea,pkt_faddr,hdr,msg_seen
4647: ,msg_path,0);
4648: printf("\n");
4649: continue; } }
4650:
4651: #if 0 // Unnecessary with SMBLIB v2.0
4652:
4653: if((j=smb_locksmbhdr(&smb[cur_smb]))!=0) {
4654: printf("ERROR %d locking %s smbhdr\n",j,smb[cur_smb].file);
4655: logprintf("ERROR %d line %d locking %s smbhdr",j,__LINE__
4656: ,smb[cur_smb].file);
4657: smb_close(&smb[cur_smb]);
4658: strip_psb(fmsgbuf);
4659: pkt_to_pkt(fmsgbuf,curarea,pkt_faddr,hdr,msg_seen
4660: ,msg_path,0);
4661: printf("\n");
4662: continue; }
4663:
4664: if((j=smb_getstatus(&smb[cur_smb]))!=0) {
4665: sprintf(str,"ERROR %d reading %s SMB header",j
4666: ,smb[cur_smb].file);
4667: printf(str);
4668: logprintf(str);
4669: smb_unlocksmbhdr(&smb[cur_smb]);
4670: smb_close(&smb[cur_smb]);
4671: strip_psb(fmsgbuf);
4672: pkt_to_pkt(fmsgbuf,curarea,pkt_faddr,hdr,msg_seen
4673: ,msg_path,0);
4674: printf("\n");
4675: continue; }
4676:
4677: smb_unlocksmbhdr(&smb[cur_smb]);
4678: #endif
4679: //openbase[0]=cfg.area[i].sub;
4680: //++num_open;
4681: subnum[cur_smb]=cfg.area[i].sub;
4682: }
4683:
4684: if(hdr.attr&FIDO_PRIVATE && !(sub[cfg.area[i].sub]->misc&SUB_PRIV)) {
4685: if(misc&IMPORT_PRIVATE)
4686: hdr.attr&=~FIDO_PRIVATE;
4687: else {
4688: start_tick=0;
4689: printf("Private posts disallowed.");
4690: if(cfg.log&LOG_PRIVATE)
4691: logprintf("%s: Private posts disallowed"
4692: ,areatagstr);
4693: strip_psb(fmsgbuf);
4694: pkt_to_pkt(fmsgbuf,curarea,pkt_faddr,hdr,msg_seen
4695: ,msg_path,0);
4696: printf("\n");
4697: continue; } }
4698:
4699: if(!(hdr.attr&FIDO_PRIVATE) && sub[cfg.area[i].sub]->misc&SUB_PONLY)
4700: hdr.attr|=MSG_PRIVATE;
4701:
4702: /**********************/
4703: /* Importing EchoMail */
4704: /**********************/
4705: j=fmsgtosmsg(fmsgbuf,hdr,0,cfg.area[i].sub);
4706:
4707: if(start_tick) {
4708: import_ticks+=clock()-start_tick;
4709: start_tick=0; }
4710:
4711: if(j==-1) {
4712: if(cfg.log&LOG_DUPES)
4713: logprintf("%s Duplicate message",areatagstr);
4714: cfg.area[i].dupes++; }
4715: else { /* Not a dupe */
4716: strip_psb(fmsgbuf);
4717: pkt_to_pkt(fmsgbuf,curarea,pkt_faddr
4718: ,hdr,msg_seen,msg_path,0); }
4719:
4720: if(j==1) { /* Successful import */
4721: echomail++;
4722: cfg.area[i].imported++;
4723: if(misc&NOTIFY_RECEIPT && (m=matchname(hdr.to))!=0) {
4724: sprintf(str
4725: ,"\7\1n\1hSBBSecho: \1m%.36s \1n\1msent you EchoMail on "
4726: "\1h%s \1n\1m%s\1n\r\n"
4727: ,hdr.from
4728: ,grp[sub[cfg.area[i].sub]->grp]->sname
4729: ,sub[cfg.area[i].sub]->sname);
4730: putsmsg(m,str); } }
4731: printf("\n");
4732: }
4733: fclose(fidomsg);
1.1.1.2 ! root 4734:
1.1 root 4735: if(misc&DELETE_PACKETS)
4736: if(delfile(packet))
4737: logprintf("ERROR line %d removing %s %s",__LINE__,packet
4738: ,sys_errlist[errno]); }
4739: #ifdef __WATCOMC__
4740: _dos_findclose(&ff);
4741: #endif
4742:
4743: if(start_tick) {
4744: import_ticks+=clock()-start_tick;
4745: start_tick=0; }
4746:
4747: } while(!kbhit() && unpack_bundle());
4748:
4749: if(kbhit()) printf("\nKey pressed - premature termination\n");
4750: while(kbhit()) getch();
4751:
4752: } /* End of Secure : Inbound loop */
4753:
4754: if(start_tick) /* Last possible increment of import_ticks */
4755: import_ticks+=clock()-start_tick;
4756:
4757: for(j=MAX_OPEN_SMBS;j>0;j--) /* Close open bases */
4758: if(smb[j].shd_fp)
4759: smb_close(&smb[j]);
4760:
4761: pkt_to_pkt(fmsgbuf,fakearea,pkt_faddr,hdr,msg_seen,msg_path,1);
4762:
4763: /******* END OF IMPORT PKT ROUTINE *******/
4764:
4765: if(cfg.log&LOG_AREA_TOTALS) {
4766: for(i=0;i<cfg.areas;i++) {
4767: if(cfg.area[i].imported)
4768: logprintf("Imported: %5u msgs %8s <- %s"
4769: ,cfg.area[i].imported,sub[cfg.area[i].sub]->code
4770: ,cfg.area[i].name); }
4771: for(i=0;i<cfg.areas;i++) {
4772: if(cfg.area[i].circular)
4773: logprintf("Circular: %5u detected in %s"
4774: ,cfg.area[i].circular,cfg.area[i].name); }
4775: for(i=0;i<cfg.areas;i++) {
4776: if(cfg.area[i].dupes)
4777: logprintf("Duplicate: %5u detected in %s"
4778: ,cfg.area[i].dupes,cfg.area[i].name); } }
4779:
4780: import_time=((float)import_ticks)/(float)CLK_TCK;
4781: if(cfg.log&LOG_TOTALS && import_time && echomail) {
4782: printf("\nImported %lu EchoMail messages in %.1f seconds "
4783: ,echomail,import_time);
4784: logprintf("Imported: %5lu msgs in %.1f sec (%.1f/min %.1f/sec)"
4785: ,echomail,import_time
4786: ,import_time/60.0 ? (float)echomail/(import_time/60.0) :(float)echomail
4787: ,(float)echomail/import_time);
4788: if(import_time/60.0)
4789: printf("(%.1f/min) ",(float)echomail/(import_time/60.0));
4790: printf("(%.1f/sec)\n",(float)echomail/import_time); }
4791: if(fmsgbuf) {
4792: FREE(fmsgbuf);
4793: fmsgbuf=0; }
4794:
4795: }
4796:
4797: if(misc&IMPORT_NETMAIL) {
4798:
4799: printf("\nScanning for Inbound NetMail Messages...\n");
4800:
4801: sprintf(str,"%s*.MSG",netmail_dir);
4802:
4803: for(last=_dos_findfirst(str,0,&ff);!last;last=_dos_findnext(&ff)) {
4804: sprintf(path,"%s%s",netmail_dir,ff.name);
4805: strupr(path);
4806: if((fidomsg=fnopen(&fmsg,path,O_RDWR))==NULL) {
4807: printf("\7ERROR opening %s\n",path);
4808: logprintf("ERROR line %d opening %s %s",__LINE__,path
4809: ,sys_errlist[errno]);
4810: continue; }
4811: if(filelength(fmsg)<sizeof(fmsghdr_t)) {
4812: printf("\7ERROR invalid length of %u bytes for %s\n",filelength(fmsg)
4813: ,path);
4814: logprintf("ERROR line %d invalid length of %u bytes for %s",__LINE__
4815: ,filelength(fmsg),path);
4816: fclose(fidomsg);
4817: continue; }
4818: if(fread(&hdr,sizeof(fmsghdr_t),1,fidomsg)!=1) {
4819: fclose(fidomsg);
4820: printf("\7ERROR reading %u bytes from %s"
4821: ,sizeof(fmsghdr_t),path);
4822: logprintf("ERROR line %d reading %u bytes from %s",__LINE__
4823: ,sizeof(fmsghdr_t),path);
4824: continue; }
4825: i=import_netmail(path,hdr,fidomsg);
4826: /**************************************/
4827: /* Delete source netmail if specified */
4828: /**************************************/
4829: if(i==0) {
4830: if(misc&DELETE_NETMAIL) {
4831: fclose(fidomsg);
4832: if(delfile(path))
4833: logprintf("ERROR line %d removing %s %s",__LINE__,path
4834: ,sys_errlist[errno]); }
4835: else {
4836: hdr.attr|=FIDO_RECV;
4837: fseek(fidomsg,0L,SEEK_SET);
4838: fwrite(&hdr,sizeof(fmsghdr_t),1,fidomsg);
4839: fclose(fidomsg); } }
4840: else if(i!=-2)
4841: fclose(fidomsg);
1.1.1.2 ! root 4842: printf("\n");
! 4843: }
1.1 root 4844: #ifdef __WATCOMC__
4845: _dos_findclose(&ff);
4846: #endif
4847: }
4848:
4849:
4850: if(misc&EXPORT_ECHOMAIL) {
4851: memset(&addr,0,sizeof(faddr_t));
4852: export_echomail(sub_code,addr);
4853: }
4854:
4855:
4856: if(misc&PACK_NETMAIL) {
4857:
4858: memset(&msg_seen,0,sizeof(addrlist_t));
4859: memset(&msg_path,0,sizeof(addrlist_t));
4860: memset(&fakearea,0,sizeof(areasbbs_t));
4861:
4862: printf("\nPacking Outbound NetMail...\n");
4863:
4864: sprintf(str,"%s*.MSG",netmail_dir);
4865:
4866: for(last=_dos_findfirst(str,0,&ff);!last;last=_dos_findnext(&ff)) {
4867: sprintf(path,"%s%s",netmail_dir,ff.name);
4868: strupr(path);
4869: if((fidomsg=fnopen(&fmsg,path,O_RDWR))==NULL) {
4870: printf("\7ERROR opening %s\n",path);
4871: logprintf("ERROR line %d opening %s %s",__LINE__,path
4872: ,sys_errlist[errno]);
4873: continue; }
4874: if(filelength(fmsg)<sizeof(fmsghdr_t)) {
4875: printf("\7%s Invalid length of %u bytes\n",path,filelength(fmsg));
4876: fclose(fidomsg);
4877: continue; }
4878: if(fread(&hdr,sizeof(fmsghdr_t),1,fidomsg)!=1) {
4879: fclose(fidomsg);
4880: printf("\7ERROR reading %u bytes from %s"
4881: ,sizeof(fmsghdr_t),path);
4882: logprintf("ERROR line %d reading %u bytes from %s",__LINE__
4883: ,sizeof(fmsghdr_t),path);
4884: continue; }
4885: hdr.destzone=hdr.origzone=sys_faddr.zone;
4886: hdr.destpoint=hdr.origpoint=0;
4887: getzpt(fidomsg,&hdr); /* use kludge if found */
4888: addr.zone=hdr.destzone;
4889: addr.net=hdr.destnet;
4890: addr.node=hdr.destnode;
4891: addr.point=hdr.destpoint;
4892: for(i=0;i<total_faddrs;i++)
4893: if(!memcmp(&addr,&faddr[i],sizeof(faddr_t)))
4894: break;
1.1.1.2 ! root 4895: if(i<total_faddrs) { /* In-bound, so ignore */
! 4896: fclose(fidomsg);
1.1 root 4897: continue;
1.1.1.2 ! root 4898: }
1.1 root 4899: printf("\n%s to %s ",path,faddrtoa(addr));
4900: if(cfg.log&LOG_PACKING)
4901: logprintf("Packing %s (%s)",path,faddrtoa(addr));
4902: fmsgbuf=getfmsg(fidomsg,NULL);
4903: if(!fmsgbuf) {
4904: printf("ERROR allocating memory for NetMail fmsgbuf\n");
4905: logprintf("ERROR line %d allocating memory for NetMail fmsgbuf"
4906: ,__LINE__);
4907: exit(1); }
4908: fclose(fidomsg);
4909:
4910: if(misc&FLO_MAILER) {
4911: attr=0;
4912: i=matchnode(addr,0);
4913: if(i<cfg.nodecfgs)
4914: if(cfg.nodecfg[i].route.zone
4915: && !(hdr.attr&(FIDO_CRASH|FIDO_HOLD))) {
4916: addr=cfg.nodecfg[i].route; /* Routed */
4917: if(cfg.log&LOG_ROUTING)
4918: logprintf("Routing %s to %s",path,faddrtoa(addr));
4919: i=matchnode(addr,0); }
4920: if(i<cfg.nodecfgs)
4921: attr=cfg.nodecfg[i].attr;
4922: if(hdr.attr&FIDO_CRASH)
4923: attr|=ATTR_CRASH;
4924: else if(hdr.attr&FIDO_HOLD)
4925: attr|=ATTR_HOLD;
4926: if(attr&ATTR_CRASH) ch='C';
4927: else if(attr&ATTR_HOLD) ch='H';
4928: else if(attr&ATTR_DIRECT) ch='D';
4929: else ch='O';
4930: if(addr.zone==faddr[0].zone) /* Default zone, use default outbound */
4931: strcpy(outbound,cfg.outbound);
4932: else /* Inter-zone outbound is OUTBOUND.XXX */
4933: sprintf(outbound,"%.*s.%03X\\"
4934: ,strlen(cfg.outbound)-1,cfg.outbound,addr.zone);
4935: if(addr.point) { /* Point destination is OUTBOUND.PNT */
4936: sprintf(str,"%04X%04X.PNT"
4937: ,addr.net,addr.node);
4938: strcat(outbound,str); }
4939: if(outbound[strlen(outbound)-1]=='\\')
4940: outbound[strlen(outbound)-1]=0;
4941: mkdir(outbound);
4942: strcat(outbound,"\\");
4943: if(addr.point)
4944: sprintf(packet,"%s%08X.%cUT",outbound,addr.point,ch);
4945: else
4946: sprintf(packet,"%s%04X%04X.%cUT",outbound,addr.net,addr.node,ch);
4947: if(hdr.attr&FIDO_FILE)
4948: if(write_flofile(hdr.subj,addr))
4949: exit(1); }
4950: else
4951: strcpy(packet,pktname());
4952:
4953: now=time(NULL);
4954: tm=gmtime(&now);
4955: if((stream=fnopen(&file,packet,O_WRONLY|O_APPEND|O_CREAT))==NULL) {
4956: printf("Unable to open %s for write.\n"
4957: ,packet);
4958: logprintf("ERROR line %d opening %s %s",__LINE__,packet
4959: ,sys_errlist[errno]);
4960: exit(1); }
4961:
4962: if(!filelength(file)) {
4963: pkthdr.orignode=hdr.orignode;
4964: pkthdr.destnode=hdr.destnode;
1.1.1.2 ! root 4965: pkthdr.year=tm->tm_year+1900;
1.1 root 4966: pkthdr.month=tm->tm_mon;
4967: pkthdr.day=tm->tm_mday;
4968: pkthdr.hour=tm->tm_hour;
4969: pkthdr.min=tm->tm_min;
4970: pkthdr.sec=tm->tm_sec;
4971: pkthdr.baud=0x00;
4972: pkthdr.pkttype=0x0002;
4973: pkthdr.orignet=hdr.orignet;
4974: pkthdr.destnet=hdr.destnet;
4975: pkthdr.prodcode=0x00;
4976: pkthdr.sernum=0;
4977: i=matchnode(addr,0);
4978: if(i<cfg.nodecfgs)
4979: memcpy(pkthdr.password,cfg.nodecfg[i].pktpwd,8);
4980: else
4981: memset(pkthdr.password,0,8);
4982: pkthdr.origzone=hdr.origzone;
4983: pkthdr.destzone=hdr.destzone;
4984: memset(pkthdr.empty,0,20);
4985: fwrite(&pkthdr,sizeof(pkthdr_t),1,stream); }
4986:
4987: putfmsg(stream,fmsgbuf,hdr,fakearea,msg_seen,msg_path);
4988:
4989: FREE(fmsgbuf);
4990: fclose(stream);
4991: /**************************************/
4992: /* Delete source netmail if specified */
4993: /**************************************/
4994: if(misc&DELETE_NETMAIL)
4995: if(delfile(path))
4996: logprintf("ERROR line %d removing %s %s",__LINE__,path
4997: ,sys_errlist[errno]);
4998: printf("\n"); }
4999: #ifdef __WATCOMC__
5000: _dos_findclose(&ff);
5001: #endif
5002: }
5003:
5004:
5005: if(misc&UPDATE_MSGPTRS) {
5006:
5007: printf("\nUpdating Message Pointers to Last Posted Message...\n");
5008:
5009: for(g=0;g<total_grps;g++)
5010: for(i=0;i<total_subs;i++)
5011: if(sub[i]->misc&SUB_FIDO && sub[i]->grp==g) {
5012: printf("\n%-15.15s %s\n"
5013: ,grp[sub[i]->grp]->sname,sub[i]->lname);
5014: getlastmsg(i,&l,0);
5015: sprintf(str,"%s%s.SFP",sub[i]->data_dir,sub[i]->code);
5016: if((file=nopen(str,O_WRONLY|O_CREAT))==-1) {
5017: printf("\7ERROR opening/creating %s",str);
5018: logprintf("ERROR line %d opening/creating %s",__LINE__,str); }
5019: else {
5020: write(file,&l,sizeof(time_t));
1.1.1.2 ! root 5021: close(file); } }
! 5022: }
1.1 root 5023:
5024: if(misc&(IMPORT_NETMAIL|IMPORT_ECHOMAIL) && misc&REPORT) {
5025: now=time(NULL);
5026: sprintf(str,"%sSBBSECHO.MSG",text_dir);
5027: if((file=nopen(str,O_WRONLY|O_CREAT|O_TRUNC))==-1) {
5028: printf("ERROR opening %s\n",str);
5029: logprintf("ERROR line %d opening %s",__LINE__,str);
5030: exit(1); }
5031: sprintf(fname,"\1c\1h "
5032: "���������������������������������������������������\r\n");
5033: sprintf(path,"\1c\1h "
5034: "���������������������������������������������������\r\n");
5035: write(file,fname,strlen(fname));
5036: sprintf(str," \1n\1k\0016"
5037: " Last FidoNet Transfer on %.24s \1n\r\n",ctime(&now));
5038: write(file,str,strlen(str));
5039: write(file,path,strlen(path));
5040: write(file,fname,strlen(fname));
5041: sprintf(tmp,"Imported %lu EchoMail and %lu NetMail Messages"
5042: ,echomail,netmail);
5043: sprintf(str," \1n\1k\0016 %-50.50s\1n\r\n",tmp);
5044: write(file,str,strlen(str));
5045: write(file,path,strlen(path));
5046: close(file); }
5047:
5048: pkt_to_pkt(buf,fakearea,pkt_faddr,hdr,msg_seen,msg_path,1);
5049: if(email->shd_fp)
5050: smb_close(email);
1.1.1.2 ! root 5051:
1.1 root 5052: FREE(smb);
5053: FREE(email);
5054: return(0);
5055: }
This archive runs on limited infrastructure. Preserving old code on modern bandwidth. Automated agents are requested to crawl responsibly.