Annotation of sbbs/sbbs3/postmsg.cpp, revision 1.1.1.1

1.1       root        1: /* postmsg.cpp */
                      2: 
                      3: /* Synchronet user create/post public message routine */
                      4: 
                      5: /* $Id: postmsg.cpp,v 1.3 2000/12/31 03:41:55 rswindell Exp $ */
                      6: 
                      7: /****************************************************************************
                      8:  * @format.tab-size 4          (Plain Text/Source Code File Header)                    *
                      9:  * @format.use-tabs true       (see http://www.synchro.net/ptsc_hdr.html)              *
                     10:  *                                                                                                                                                     *
                     11:  * Copyright 2000 Rob Swindell - http://www.synchro.net/copyright.html         *
                     12:  *                                                                                                                                                     *
                     13:  * This program is free software; you can redistribute it and/or                       *
                     14:  * modify it under the terms of the GNU General Public License                         *
                     15:  * as published by the Free Software Foundation; either version 2                      *
                     16:  * of the License, or (at your option) any later version.                                      *
                     17:  * See the GNU General Public License for more details: gpl.txt or                     *
                     18:  * http://www.fsf.org/copyleft/gpl.html                                                                                *
                     19:  *                                                                                                                                                     *
                     20:  * Anonymous FTP access to the most recent released source is available at     *
                     21:  * ftp://vert.synchro.net, ftp://cvs.synchro.net and ftp://ftp.synchro.net     *
                     22:  *                                                                                                                                                     *
                     23:  * Anonymous CVS access to the development source and modification history     *
                     24:  * is available at cvs.synchro.net:/cvsroot/sbbs, example:                                     *
                     25:  * cvs -d :pserver:[email protected]:/cvsroot/sbbs login                       *
                     26:  *     (just hit return, no password is necessary)                                                     *
                     27:  * cvs -d :pserver:[email protected]:/cvsroot/sbbs checkout src                *
                     28:  *                                                                                                                                                     *
                     29:  * For Synchronet coding style and modification guidelines, see                                *
                     30:  * http://www.synchro.net/source.html                                                                          *
                     31:  *                                                                                                                                                     *
                     32:  * You are encouraged to submit any modifications (preferably in Unix diff     *
                     33:  * format) via e-mail to [email protected]                                                                      *
                     34:  *                                                                                                                                                     *
                     35:  * Note: If this box doesn't appear square, then you need to fix your tabs.    *
                     36:  ****************************************************************************/
                     37: 
                     38: #include "sbbs.h"
                     39: 
                     40: /****************************************************************************/
                     41: /* Posts a message on subboard number sub, with 'top' as top of message.    */
                     42: /* Returns 1 if posted, 0 if not.                                           */
                     43: /****************************************************************************/
                     44: bool sbbs_t::postmsg(uint subnum, smbmsg_t *remsg, long wm_mode)
                     45: {
                     46:        char    str[256],touser[256],title[LEN_TITLE+1],buf[SDT_BLOCK_LEN]
                     47:                        ,top[256];
                     48:        ushort  xlat,msgattr;
                     49:        int     i,j,x,file,storage;
                     50:        ulong   l,length,offset,crc=0xffffffff;
                     51:        FILE    *instream;
                     52:        smbmsg_t msg,tmpmsg;
                     53: 
                     54:        if(remsg) {
                     55:                sprintf(title,"%.*s",LEN_TITLE,remsg->subj);
                     56:                if(cfg.sub[subnum]->misc&SUB_INET)      // All Internet posts to "All" 05/20/97
                     57:                        touser[0]=0;
                     58:                else if(remsg->hdr.attr&MSG_ANONYMOUS)
                     59:                        strcpy(touser,text[Anonymous]);
                     60:                else
                     61:                        strcpy(touser,remsg->from);
                     62:                msgattr=(ushort)(remsg->hdr.attr&MSG_PRIVATE);
                     63:                sprintf(top,text[RegardingByToOn],title,touser,remsg->to
                     64:                        ,timestr((time_t *)&remsg->hdr.when_written.time)
                     65:                        ,zonestr(remsg->hdr.when_written.zone)); }
                     66:        else {
                     67:                title[0]=0;
                     68:                touser[0]=0;
                     69:                top[0]=0;
                     70:                msgattr=0; }
                     71: 
                     72:        if(useron.rest&FLAG('P')) {
                     73:                bputs(text[R_Post]);
                     74:                return(false); }
                     75: 
                     76:        if((cfg.sub[subnum]->misc&(SUB_QNET|SUB_FIDO|SUB_PNET|SUB_INET))
                     77:                && (useron.rest&FLAG('N'))) {
                     78:                bputs(text[CantPostOnSub]);
                     79:                return(false); }
                     80: 
                     81:        if(useron.ptoday>=cfg.level_postsperday[useron.level]) {
                     82:                bputs(text[TooManyPostsToday]);
                     83:                return(false); }
                     84: 
                     85:        bprintf(text[Posting],cfg.grp[cfg.sub[subnum]->grp]->sname,cfg.sub[subnum]->lname);
                     86:        action=NODE_PMSG;
                     87:        nodesync();
                     88: 
                     89:        if(!(msgattr&MSG_PRIVATE) && (cfg.sub[subnum]->misc&SUB_PONLY
                     90:                || (cfg.sub[subnum]->misc&SUB_PRIV && !noyes(text[PrivatePostQ]))))
                     91:                msgattr|=MSG_PRIVATE;
                     92: 
                     93:        if(sys_status&SS_ABORT)
                     94:                return(false);
                     95: 
                     96:        if(!(cfg.sub[subnum]->misc&SUB_INET)    // Prompt for TO: user
                     97:                && (cfg.sub[subnum]->misc&SUB_TOUSER || msgattr&MSG_PRIVATE || touser[0])) {
                     98:                if(!touser[0] && !(msgattr&MSG_PRIVATE))
                     99:                        strcpy(touser,"All");
                    100:                bputs(text[PostTo]);
                    101:                i=LEN_ALIAS;
                    102:                if(cfg.sub[subnum]->misc&(SUB_PNET|SUB_INET))
                    103:                        i=60;
                    104:                if(cfg.sub[subnum]->misc&SUB_FIDO)
                    105:                        i=35;
                    106:                if(cfg.sub[subnum]->misc&SUB_QNET)
                    107:                        i=25;
                    108:                getstr(touser,i,K_UPRLWR|K_LINE|K_EDIT|K_AUTODEL);
                    109:                if(stricmp(touser,"ALL")
                    110:                && !(cfg.sub[subnum]->misc&(SUB_PNET|SUB_FIDO|SUB_QNET|SUB_INET|SUB_ANON))) {
                    111:                        if(cfg.sub[subnum]->misc&SUB_NAME) {
                    112:                                if(!userdatdupe(useron.number,U_NAME,LEN_NAME,touser,0)) {
                    113:                                        bputs(text[UnknownUser]);
                    114:                                        return(false); } }
                    115:                        else {
                    116:                                if((i=finduser(touser))==0)
                    117:                                        return(false);
                    118:                                username(&cfg,i,touser); } }
                    119:                if(sys_status&SS_ABORT)
                    120:                        return(false); }
                    121: 
                    122:        if(!touser[0])
                    123:                strcpy(touser,"All");       // Default to ALL
                    124: 
                    125:        if(!stricmp(touser,"SYSOP") && !SYSOP)  // Change SYSOP to user #1
                    126:                username(&cfg,1,touser);
                    127: 
                    128:        if(msgattr&MSG_PRIVATE && !stricmp(touser,"ALL")) {
                    129:                bputs(text[NoToUser]);
                    130:                return(false); }
                    131:        if(msgattr&MSG_PRIVATE)
                    132:                wm_mode|=WM_PRIVATE;
                    133: 
                    134:        if(cfg.sub[subnum]->misc&SUB_AONLY
                    135:                || (cfg.sub[subnum]->misc&SUB_ANON && useron.exempt&FLAG('A')
                    136:                        && !noyes(text[AnonymousQ])))
                    137:                msgattr|=MSG_ANONYMOUS;
                    138: 
                    139:        if(cfg.sub[subnum]->mod_ar[0] && chk_ar(cfg.sub[subnum]->mod_ar,&useron))
                    140:                msgattr|=MSG_MODERATED;
                    141: 
                    142:        if(cfg.sub[subnum]->misc&SUB_SYSPERM && sub_op(subnum))
                    143:                msgattr|=MSG_PERMANENT;
                    144: 
                    145:        if(msgattr&MSG_PRIVATE)
                    146:                bputs(text[PostingPrivately]);
                    147: 
                    148:        if(msgattr&MSG_ANONYMOUS)
                    149:                bputs(text[PostingAnonymously]);
                    150: 
                    151:        if(cfg.sub[subnum]->misc&SUB_NAME)
                    152:                bputs(text[UsingRealName]);
                    153: 
                    154:        sprintf(str,"%sINPUT.MSG",cfg.node_dir);
                    155:        if(!writemsg(str,top,title,wm_mode,subnum,touser)) {
                    156:                bputs(text[Aborted]);
                    157:                return(false); }
                    158: 
                    159:        bputs(text[WritingIndx]);
                    160: 
                    161:        if((i=smb_stack(&smb,SMB_STACK_PUSH))!=0) {
                    162:                errormsg(WHERE,ERR_OPEN,cfg.sub[subnum]->code,i);
                    163:                return(false); }
                    164: 
                    165:        sprintf(smb.file,"%s%s",cfg.sub[subnum]->data_dir,cfg.sub[subnum]->code);
                    166:        smb.retry_time=cfg.smb_retry_time;
                    167:        if((i=smb_open(&smb))!=0) {
                    168:                smb_stack(&smb,SMB_STACK_POP);
                    169:                errormsg(WHERE,ERR_OPEN,smb.file,i,smb.last_error);
                    170:                return(false); }
                    171: 
                    172:        if(filelength(fileno(smb.shd_fp))<1) {   /* Create it if it doesn't exist */
                    173:                smb.status.max_crcs=cfg.sub[subnum]->maxcrcs;
                    174:                smb.status.max_msgs=cfg.sub[subnum]->maxmsgs;
                    175:                smb.status.max_age=cfg.sub[subnum]->maxage;
                    176:                smb.status.attr=cfg.sub[subnum]->misc&SUB_HYPER ? SMB_HYPERALLOC : 0;
                    177:                if((i=smb_create(&smb))!=0) {
                    178:                        smb_close(&smb);
                    179:                        smb_stack(&smb,SMB_STACK_POP);
                    180:                        errormsg(WHERE,ERR_CREATE,smb.file,i,smb.last_error);
                    181:                        return(false); } }
                    182: 
                    183:        if((i=smb_locksmbhdr(&smb))!=0) {
                    184:                smb_close(&smb);
                    185:                smb_stack(&smb,SMB_STACK_POP);
                    186:                errormsg(WHERE,ERR_LOCK,smb.file,i,smb.last_error);
                    187:                return(false); }
                    188: 
                    189:        if((i=smb_getstatus(&smb))!=0) {
                    190:                smb_close(&smb);
                    191:                smb_stack(&smb,SMB_STACK_POP);
                    192:                errormsg(WHERE,ERR_READ,smb.file,i,smb.last_error);
                    193:                return(false); }
                    194: 
                    195:        length=flength(str)+2;   /* +2 for translation string */
                    196: 
                    197:        if(length&0xfff00000UL) {
                    198:                smb_close(&smb);
                    199:                smb_stack(&smb,SMB_STACK_POP);
                    200:                errormsg(WHERE,ERR_LEN,str,length);
                    201:                return(false); }
                    202: 
                    203:        if(smb.status.attr&SMB_HYPERALLOC) {
                    204:                offset=smb_hallocdat(&smb);
                    205:                storage=SMB_HYPERALLOC; }
                    206:        else {
                    207:                if((i=smb_open_da(&smb))!=0) {
                    208:                        smb_unlocksmbhdr(&smb);
                    209:                        smb_close(&smb);
                    210:                        smb_stack(&smb,SMB_STACK_POP);
                    211:                        errormsg(WHERE,ERR_OPEN,smb.file,i,smb.last_error);
                    212:                        return(false); }
                    213:                if(cfg.sub[subnum]->misc&SUB_FAST) {
                    214:                        offset=smb_fallocdat(&smb,length,1);
                    215:                        storage=SMB_FASTALLOC; }
                    216:                else {
                    217:                        offset=smb_allocdat(&smb,length,1);
                    218:                        storage=SMB_SELFPACK; }
                    219:                smb_close_da(&smb); }
                    220: 
                    221:        if((file=open(str,O_RDONLY|O_BINARY))==-1
                    222:                || (instream=fdopen(file,"rb"))==NULL) {
                    223:                smb_freemsgdat(&smb,offset,length,1);
                    224:                smb_unlocksmbhdr(&smb);
                    225:                smb_close(&smb);
                    226:                smb_stack(&smb,SMB_STACK_POP);
                    227:                errormsg(WHERE,ERR_OPEN,str,O_RDONLY|O_BINARY);
                    228:                return(false); }
                    229: 
                    230:        setvbuf(instream,NULL,_IOFBF,2*1024);
                    231:        fseek(smb.sdt_fp,offset,SEEK_SET);
                    232:        xlat=XLAT_NONE;
                    233:        fwrite(&xlat,2,1,smb.sdt_fp);
                    234:        x=SDT_BLOCK_LEN-2;                              /* Don't read/write more than 255 */
                    235:        while(!feof(instream)) {
                    236:                memset(buf,0,x);
                    237:                j=fread(buf,1,x,instream);
                    238:                if((j!=x || feof(instream)) && buf[j-1]==LF && buf[j-2]==CR)
                    239:                        buf[j-1]=buf[j-2]=0;    /* Convert to NULL */
                    240:                if(cfg.sub[subnum]->maxcrcs) {
                    241:                        for(i=0;i<j;i++)
                    242:                                crc=ucrc32(buf[i],crc); }
                    243:                fwrite(buf,j,1,smb.sdt_fp);
                    244:                x=SDT_BLOCK_LEN; }
                    245:        fflush(smb.sdt_fp);
                    246:        fclose(instream);
                    247:        crc=~crc;
                    248: 
                    249:        memset(&msg,0,sizeof(smbmsg_t));
                    250:        memcpy(msg.hdr.id,"SHD\x1a",4);
                    251:        msg.hdr.version=smb_ver();
                    252:        msg.hdr.attr=msg.idx.attr=msgattr;
                    253:        msg.hdr.when_written.time=msg.hdr.when_imported.time=time(NULL);
                    254:        msg.hdr.when_written.zone=msg.hdr.when_imported.zone=cfg.sys_timezone;
                    255:        if(remsg) {
                    256:                msg.hdr.thread_orig=remsg->hdr.number;
                    257:                if(!remsg->hdr.thread_first) {
                    258:                        remsg->hdr.thread_first=smb.status.last_msg+1;
                    259:                        if((i=smb_lockmsghdr(&smb,remsg))!=0)
                    260:                                errormsg(WHERE,ERR_LOCK,smb.file,i,smb.last_error);
                    261:                        else {
                    262:                                i=smb_putmsghdr(&smb,remsg);
                    263:                                smb_unlockmsghdr(&smb,remsg);
                    264:                                if(i)
                    265:                                        errormsg(WHERE,ERR_WRITE,smb.file,i); } }
                    266:                else {
                    267:                        l=remsg->hdr.thread_first;
                    268:                        while(1) {
                    269:                                tmpmsg.idx.offset=0;
                    270:                                if(!loadmsg(&tmpmsg,l))
                    271:                                        break;
                    272:                                if(tmpmsg.hdr.thread_next && tmpmsg.hdr.thread_next!=l) {
                    273:                                        l=tmpmsg.hdr.thread_next;
                    274:                                        smb_unlockmsghdr(&smb,&tmpmsg);
                    275:                                        smb_freemsgmem(&tmpmsg);
                    276:                                        continue; }
                    277:                                tmpmsg.hdr.thread_next=smb.status.last_msg+1;
                    278:                                if((i=smb_putmsghdr(&smb,&tmpmsg))!=0)
                    279:                                        errormsg(WHERE,ERR_WRITE,smb.file,i);
                    280:                                smb_unlockmsghdr(&smb,&tmpmsg);
                    281:                                smb_freemsgmem(&tmpmsg);
                    282:                                break; } } }
                    283: 
                    284: 
                    285:        if(cfg.sub[subnum]->maxcrcs) {
                    286:                i=smb_addcrc(&smb,crc);
                    287:                if(i) {
                    288:                        smb_freemsgdat(&smb,offset,length,1);
                    289:                        smb_unlocksmbhdr(&smb);
                    290:                        smb_close(&smb);
                    291:                        smb_stack(&smb,SMB_STACK_POP);
                    292:                        bputs("\1r\1h\1iDuplicate message!\r\n");
                    293:                        return(false); } }
                    294: 
                    295:        msg.hdr.offset=offset;
                    296: 
                    297:        smb_hfield(&msg,RECIPIENT,strlen(touser),touser);
                    298:        strlwr(touser);
                    299:        msg.idx.to=crc16(touser);
                    300: 
                    301:        strcpy(str,cfg.sub[subnum]->misc&SUB_NAME ? useron.name : useron.alias);
                    302:        smb_hfield(&msg,SENDER,strlen(str),str);
                    303:        strlwr(str);
                    304:        msg.idx.from=crc16(str);
                    305: 
                    306:        sprintf(str,"%u",useron.number);
                    307:        smb_hfield(&msg,SENDEREXT,strlen(str),str);
                    308: 
                    309:        smb_hfield(&msg,SUBJECT,strlen(title),title);
                    310:        strcpy(str,title);
                    311:        strlwr(str);
                    312:        remove_re(str);
                    313:        msg.idx.subj=crc16(str);
                    314: 
                    315:        smb_dfield(&msg,TEXT_BODY,length);
                    316: 
                    317:        smb_unlocksmbhdr(&smb);
                    318:        i=smb_addmsghdr(&smb,&msg,storage);
                    319:        smb_close(&smb);
                    320:        smb_stack(&smb,SMB_STACK_POP);
                    321: 
                    322:        smb_freemsgmem(&msg);
                    323:        if(i) {
                    324:                smb_freemsgdat(&smb,offset,length,1);
                    325:                errormsg(WHERE,ERR_WRITE,smb.file,i);
                    326:                return(false); }
                    327: 
                    328:        useron.ptoday++;
                    329:        useron.posts++;
                    330:        logon_posts++;
                    331:        putuserrec(&cfg,useron.number,U_POSTS,5,ultoa(useron.posts,str,10));
                    332:        putuserrec(&cfg,useron.number,U_PTODAY,5,ultoa(useron.ptoday,str,10));
                    333:        bprintf(text[Posted],cfg.grp[cfg.sub[subnum]->grp]->sname
                    334:                ,cfg.sub[subnum]->lname);
                    335:        sprintf(str,"Posted on %s %s",cfg.grp[cfg.sub[subnum]->grp]->sname,cfg.sub[subnum]->lname);
                    336:        logline("P+",str);
                    337:        if(cfg.sub[subnum]->misc&SUB_FIDO && cfg.sub[subnum]->echomail_sem[0]) /* semaphore */
                    338:                if((file=nopen(cmdstr(cfg.sub[subnum]->echomail_sem,nulstr,nulstr,NULL)
                    339:                        ,O_WRONLY|O_CREAT|O_TRUNC))!=-1)
                    340:                        close(file);
                    341:        return(true);
                    342: }

unix.superglobalmegacorp.com

This archive runs on limited infrastructure. Preserving old code on modern bandwidth. Automated agents are requested to crawl responsibly.