|
|
1.1 root 1: #line 1 "QWKTOMSG.C"
2:
3: /* Developed 1990-1997 by Rob Swindell; PO Box 501, Yorba Linda, CA 92885 */
4:
5: #include "sbbs.h"
6: #include "qwk.h"
7:
8: /****************************************************************************/
9: /* Converts a QWK message packet into a message. The 'qwkbuf' pointer */
10: /* points to the message header and 'str' is the file to output to. */
11: /* Returns the 1 on success or 0 if failure. */
12: /****************************************************************************/
13: char qwktomsg(FILE *qwk_fp, uchar *hdrblk, char fromhub, uint subnum
14: , uint touser)
15: {
16: uchar str[256],*body,*tail,col=0,lastch=0,*p,*lzhbuf,qwkbuf[128];
17: int file,i,j,k,lzh=0,storage,skip=0;
18: ushort xlat;
19: long l,bodylen,taillen,length;
20: ulong crc,block,blocks;
21: smbmsg_t msg;
22:
23: memset(&msg,0,sizeof(smbmsg_t)); /* Initialize message header */
24: memcpy(msg.hdr.id,"SHD\x1a",4);
1.1.1.2 ! root 25: msg.hdr.version=smb_ver();
1.1 root 26:
27: blocks=atol(hdrblk+116);
28: if(blocks<2)
29: return(0);
30:
31: if(subnum!=INVALID_SUB
32: && (hdrblk[0]=='*' || hdrblk[0]=='+' || sub[subnum]->misc&SUB_PONLY))
33: msg.idx.attr|=MSG_PRIVATE;
34: if(subnum!=INVALID_SUB && sub[subnum]->misc&SUB_AONLY)
35: msg.idx.attr|=MSG_ANONYMOUS;
36: if(subnum==INVALID_SUB && sys_misc&SM_DELREADM)
37: msg.idx.attr|=MSG_KILLREAD;
38: if((fromhub || useron.rest&FLAG('Q')) &&
39: (hdrblk[0]=='*' || hdrblk[0]=='-' || hdrblk[0]=='`'))
40: msg.idx.attr|=MSG_READ;
41:
42: if(subnum!=INVALID_SUB && !fromhub && sub[subnum]->mod_ar[0]
43: && chk_ar(sub[subnum]->mod_ar,useron))
44: msg.idx.attr|=MSG_MODERATED;
45: if(subnum!=INVALID_SUB && !fromhub && sub[subnum]->misc&SUB_SYSPERM
46: && sub_op(subnum))
47: msg.idx.attr|=MSG_PERMANENT;
48:
49: msg.hdr.attr=msg.idx.attr;
50:
51: date.da_mon=((hdrblk[8]&0xf)*10)+(hdrblk[9]&0xf);
52: date.da_day=((hdrblk[11]&0xf)*10)+(hdrblk[12]&0xf);
1.1.1.2 ! root 53: date.da_year=((hdrblk[14]&0xf)*10)+(hdrblk[15]&0xf);
! 54: if(date.da_year<Y2K_2DIGIT_WINDOW)
! 55: date.da_year+=100;
! 56: date.da_year+=1900;
1.1 root 57: curtime.ti_hour=((hdrblk[16]&0xf)*10)+(hdrblk[17]&0xf);
58: curtime.ti_min=((hdrblk[19]&0xf)*10)+(hdrblk[20]&0xf);
59: curtime.ti_sec=0;
60: msg.hdr.when_written.time=dostounix(&date,&curtime);
61: if(!(useron.rest&FLAG('Q')) && !fromhub)
62: msg.hdr.when_written.zone=sys_timezone;
63: msg.hdr.when_imported.time=time(NULL);
64: msg.hdr.when_imported.zone=sys_timezone;
65:
1.1.1.2 ! root 66: hdrblk[116]=0; /* don't bleed number-of-blocks and re-msg-num fields together */
1.1 root 67: msg.hdr.thread_orig=atol(hdrblk+108);
68:
69: if((uint)subnum==INVALID_SUB) { /* E-mail */
70: msg.idx.to=touser;
71:
72: /*** Unnecessary code in v2.10a
73: if(!touser) {
74: sprintf(str,"%25.25s",hdrblk+21);
75: truncsp(str);
76: for(i=0;i<total_qhubs;i++)
77: if(!stricmp(qhub[i]->id,str))
78: break;
79: if(i==total_qhubs) {
80: errormsg(WHERE,ERR_CHK,str,0);
81: return(0); }
82: smb_hfield(&msg,RECIPIENT,strlen(str),str); }
83: else {
84: ***/
85: username(touser,str);
86: smb_hfield(&msg,RECIPIENT,strlen(str),str);
87: sprintf(str,"%u",touser);
88: smb_hfield(&msg,RECIPIENTEXT,strlen(str),str); }
89:
90: else {
91: sprintf(str,"%25.25s",hdrblk+21); /* To user */
92: truncsp(str);
93: smb_hfield(&msg,RECIPIENT,strlen(str),str);
94: strlwr(str);
95: msg.idx.to=crc16(str); }
96:
97: fread(qwkbuf,1,128,qwk_fp);
98:
99: if(useron.rest&FLAG('Q') || fromhub) { /* QWK Net */
100: if(!strnicmp(qwkbuf,"@VIA:",5)) {
101: p=strchr(qwkbuf,'\xe3');
102: if(p) {
103: *p=0;
104: skip=strlen(qwkbuf)+1; }
105: truncsp(qwkbuf);
106: p=qwkbuf+5; /* Skip "@VIA:" */
107: while(*p && *p<=SP) p++; /* Skip any spaces */
108: if(route_circ(p,sys_id)) {
109: smb_freemsgmem(&msg);
110: bprintf("\r\nCircular message path: %s\r\n",p);
111: sprintf(str,"Circular message path: %s from %s"
112: ,p,fromhub ? qhub[fromhub-1]->id:useron.alias);
113: errorlog(str);
114: return(0); }
115: sprintf(str,"%s/%s"
116: ,fromhub ? qhub[fromhub-1]->id : useron.alias,p);
117: strupr(str);
118: update_qwkroute(str); }
119: else {
120: if(fromhub)
121: strcpy(str,qhub[fromhub-1]->id);
122: else
123: strcpy(str,useron.alias); }
124: strupr(str);
125: j=NET_QWK;
126: smb_hfield(&msg,SENDERNETTYPE,2,&j);
127: smb_hfield(&msg,SENDERNETADDR,strlen(str),str);
128: sprintf(str,"%25.25s",hdrblk+46); /* From user */
129: truncsp(str);
130: if(!strnicmp(qwkbuf+skip,"@TZ:",4)) {
131: p=strchr(qwkbuf+skip,'\xe3');
132: i=skip;
133: if(p) {
134: *p=0;
135: skip+=strlen(qwkbuf+i)+1; }
136: p=qwkbuf+i+4; /* Skip "@TZ:" */
137: while(*p && *p<=SP) p++; /* Skip any spaces */
138: msg.hdr.when_written.zone=(short)ahtoul(p); }
139: }
140: else {
141: sprintf(str,"%u",useron.number);
142: smb_hfield(&msg,SENDEREXT,strlen(str),str);
143: if((uint)subnum!=INVALID_SUB && sub[subnum]->misc&SUB_NAME)
144: strcpy(str,useron.name);
145: else
146: strcpy(str,useron.alias); }
147:
148: smb_hfield(&msg,SENDER,strlen(str),str);
149: if((uint)subnum==INVALID_SUB) {
150: if(useron.rest&FLAG('Q') || fromhub)
151: msg.idx.from=0;
152: else
153: msg.idx.from=useron.number; }
154: else {
155: strlwr(str);
156: msg.idx.from=crc16(str); }
157:
158: sprintf(str,"%25.25s",hdrblk+71); /* Subject */
159: truncsp(str);
160: remove_re(str);
161: smb_hfield(&msg,SUBJECT,strlen(str),str);
162: strlwr(str);
163: msg.idx.subj=crc16(str);
164:
165: /********************************/
166: /* Convert the QWK message text */
167: /********************************/
168:
169: bodylen=0;
170: if((body=LMALLOC((blocks-1L)*128L*2L))==NULL) {
171: smb_freemsgmem(&msg);
172: errormsg(WHERE,ERR_ALLOC,"QWK msg",(blocks-1L)*128L*2L);
173: return(0); }
174:
175: taillen=0;
176: if((tail=LMALLOC((blocks-1L)*128L))==NULL) {
177: LFREE(body);
178: smb_freemsgmem(&msg);
179: errormsg(WHERE,ERR_ALLOC,"QWK msg",(blocks-1L)*128L);
180: return(0); }
181:
182: for(block=1;block<blocks;block++) {
183: if(block>1)
184: if(!fread(qwkbuf,1,128,qwk_fp))
185: break;
186: for(k=skip;k<128;k++,skip=0) {
187: if(qwkbuf[k]==0)
188: continue;
189: if(!taillen && qwkbuf[k]==SP && col==3 && bodylen>=3
190: && body[bodylen-3]=='-' && body[bodylen-2]=='-'
191: && body[bodylen-1]=='-') {
192: bodylen-=3;
193: strcpy(tail,"--- ");
194: taillen=4;
195: col++;
196: continue; }
197: if(qwkbuf[k]==0xE3) { /* expand 0xe3 to crlf */
198: if(!taillen && col==3 && bodylen>=3 && body[bodylen-3]=='-'
199: && body[bodylen-2]=='-' && body[bodylen-1]=='-') {
200: bodylen-=3;
201: strcpy(tail,"---");
202: taillen=3; }
203: col=0;
204: if(taillen) {
205: tail[taillen++]=CR;
206: tail[taillen++]=LF; }
207: else {
208: body[bodylen++]=CR;
209: body[bodylen++]=LF; }
210: continue; }
211: if(!fromhub && qwkbuf[k]==7 && useron.rest&FLAG('B')) /* beep res */
212: continue;
213: if(!fromhub && (qwkbuf[k]==1 || qwkbuf[k]==ESC) /* ANSI restriction */
214: && useron.rest&FLAG('A'))
215: continue;
216: if(qwkbuf[k]!=1 && lastch!=1)
217: col++;
218: if(lastch==1 && !validattr(qwkbuf[k])) {
219: if(taillen) taillen--;
220: else bodylen--;
221: lastch=0;
222: continue; }
223: lastch=qwkbuf[k];
224: if(taillen)
225: tail[taillen++]=qwkbuf[k];
226: else
227: body[bodylen++]=qwkbuf[k]; } }
228:
229: while(bodylen && body[bodylen-1]==SP) bodylen--; /* remove trailing spaces */
230: if(bodylen>=2 && body[bodylen-2]==CR && body[bodylen-1]==LF)
231: bodylen-=2;
232:
233: while(taillen && tail[taillen-1]<=SP) taillen--; /* remove trailing garbage */
234:
235: /*****************/
236: /* Calculate CRC */
237: /*****************/
238:
239: if(smb.status.max_crcs) {
240: crc=0xffffffffUL;
241: for(l=0;l<bodylen;l++)
242: crc=ucrc32(body[l],crc);
243: crc=~crc;
244:
245: /*******************/
246: /* Check for dupes */
247: /*******************/
248:
249: j=smb_addcrc(&smb,crc);
250: if(j) {
251: if(j==1) {
252: bprintf("\r\nDuplicate message\r\n");
253: logline(subnum==INVALID_SUB ? "E!":"P!","Duplicate message"); }
254: else
255: errormsg(WHERE,ERR_CHK,smb.file,j);
256:
257: smb_freemsgmem(&msg);
258: LFREE(body);
259: LFREE(tail);
260: return(0); } }
261:
262: bputs(text[WritingIndx]);
263:
264: /*************************************/
265: /* Write SMB message header and text */
266: /*************************************/
267:
268: if(subnum!=INVALID_SUB && sub[subnum]->misc&SUB_LZH && bodylen
269: && bodylen+2+taillen+2>=SDT_BLOCK_LEN
270: && (lzhbuf=(char *)LMALLOC(bodylen*2))!=NULL) {
271: length=lzh_encode((uchar *)body,bodylen,(uchar *)lzhbuf);
272: if(length>1L
273: && smb_datblocks(length+4L+taillen+2L)
274: <smb_datblocks(bodylen+2L+taillen+2L)) {
275: bodylen=length; /* Compressable */
276: length+=4L;
277: lzh=1;
278: LFREE(body);
279: body=lzhbuf; }
280: else { /* Non-compressable */
281: length=bodylen+2L;
282: LFREE(lzhbuf); } }
283: else
284: length=bodylen+2L; /* +2 for translation string */
285:
286: if(taillen)
287: length+=taillen+2L;
288:
289: if(length&0xfff00000UL) {
290: errormsg(WHERE,ERR_LEN,"REP msg",length);
291: smb_freemsgmem(&msg);
292: LFREE(body);
293: LFREE(tail);
294: return(0); }
295:
296: if((i=smb_locksmbhdr(&smb))!=0) {
297: errormsg(WHERE,ERR_LOCK,smb.file,i);
298: FREE(body);
299: FREE(tail);
300: return(0); }
301:
302: if(smb.status.attr&SMB_HYPERALLOC) {
303: msg.hdr.offset=smb_hallocdat(&smb);
304: storage=SMB_HYPERALLOC; }
305: else {
306: if((i=smb_open_da(&smb))!=0) {
307: errormsg(WHERE,ERR_OPEN,smb.file,i);
308: FREE(body);
309: FREE(tail);
310: return(0); }
311: if((subnum==INVALID_SUB && sys_misc&SM_FASTMAIL)
312: || (subnum!=INVALID_SUB && sub[subnum]->misc&SUB_FAST)) {
313: msg.hdr.offset=smb_fallocdat(&smb,length,1);
314: storage=SMB_FASTALLOC; }
315: else {
316: msg.hdr.offset=smb_allocdat(&smb,length,1);
317: storage=SMB_SELFPACK; }
318: smb_close_da(&smb); }
319:
320: if(msg.hdr.offset && msg.hdr.offset<1L) {
321: smb_unlocksmbhdr(&smb);
322: errormsg(WHERE,ERR_READ,smb.file,msg.hdr.offset);
323: smb_freemsgmem(&msg);
324: FREE(body);
325: FREE(tail); }
326: fseek(smb.sdt_fp,msg.hdr.offset,SEEK_SET);
327: if(lzh) {
328: xlat=XLAT_LZH;
329: fwrite(&xlat,2,1,smb.sdt_fp); }
330: xlat=XLAT_NONE;
331: fwrite(&xlat,2,1,smb.sdt_fp);
332: fwrite(body,bodylen,1,smb.sdt_fp);
333: smb_dfield(&msg,TEXT_BODY,bodylen+2+(lzh ? 2:0));
334: if(taillen) {
335: fwrite(&xlat,2,1,smb.sdt_fp);
336: fwrite(tail,taillen,1,smb.sdt_fp);
337: smb_dfield(&msg,TEXT_TAIL,taillen+2); }
338: fflush(smb.sdt_fp);
339: smb_unlocksmbhdr(&smb);
340:
341: if((i=smb_addmsghdr(&smb,&msg,storage))!=0)
342: errormsg(WHERE,ERR_WRITE,smb.file,i);
343:
344: smb_freemsgmem(&msg);
345:
346: LFREE(body);
347: LFREE(tail);
348:
349: return(1);
350: }
This archive runs on limited infrastructure. Preserving old code on modern bandwidth. Automated agents are requested to crawl responsibly.