|
|
1.1 ! root 1: /* $Header: respond.c,v 4.3.1.4 85/05/23 17:24:49 lwall Exp $ ! 2: * ! 3: * $Log: respond.c,v $ ! 4: * Revision 4.3.1.4 85/05/23 17:24:49 lwall ! 5: * Now allows 'r' and 'f' on null articles. ! 6: * ! 7: * Revision 4.3.1.3 85/05/15 14:42:32 lwall ! 8: * Removed duplicate include of intrp.h. ! 9: * ! 10: * Revision 4.3.1.2 85/05/14 08:55:15 lwall ! 11: * Default for normal/mailbox question was applied to wrong buffer. ! 12: * ! 13: * Revision 4.3.1.1 85/05/10 11:37:33 lwall ! 14: * Branch for patches. ! 15: * ! 16: * Revision 4.3 85/05/01 11:47:04 lwall ! 17: * Baseline for release with 4.3bsd. ! 18: * ! 19: */ ! 20: ! 21: #include "EXTERN.h" ! 22: #include "common.h" ! 23: #include "intrp.h" ! 24: #include "head.h" ! 25: #include "term.h" ! 26: #include "ng.h" ! 27: #include "util.h" ! 28: #include "rn.h" ! 29: #include "artio.h" ! 30: #include "final.h" ! 31: #include "INTERN.h" ! 32: #include "respond.h" ! 33: ! 34: static char nullart[] = "\nNull article\n"; ! 35: ! 36: void ! 37: respond_init() ! 38: { ! 39: ; ! 40: } ! 41: ! 42: int ! 43: save_article() ! 44: { ! 45: bool use_pref; ! 46: register char *s, *c; ! 47: char altbuf[CBUFLEN]; ! 48: int iter; ! 49: bool interactive = (buf[1] == FINISHCMD); ! 50: ! 51: if (!finish_command(interactive)) /* get rest of command */ ! 52: return SAVE_ABORT; ! 53: use_pref = isupper(*buf); ! 54: #ifdef ASYNC_PARSE ! 55: parse_maybe(art); ! 56: #endif ! 57: savefrom = (*buf=='w' || *buf=='W' ? htype[PAST_HEADER].ht_minpos : 0); ! 58: if (artopen(art) == Nullfp) { ! 59: #ifdef VERBOSE ! 60: IF(verbose) ! 61: fputs("\n\ ! 62: Saving null articles is not very productive! :-)\n\ ! 63: ",stdout) FLUSH; ! 64: ELSE ! 65: #endif ! 66: #ifdef TERSE ! 67: fputs(nullart,stdout) FLUSH; ! 68: #endif ! 69: return SAVE_DONE; ! 70: } ! 71: if (chdir(cwd)) { ! 72: printf(nocd,cwd) FLUSH; ! 73: sig_catcher(0); ! 74: } ! 75: if (savedest) ! 76: free(savedest); ! 77: if ((s = index(buf,'|')) != Nullch) { ! 78: /* is it a pipe command? */ ! 79: s++; /* skip the | */ ! 80: while (*s == ' ') s++; ! 81: safecpy(altbuf,filexp(s),sizeof altbuf); ! 82: savedest = altbuf; ! 83: interp(cmd_buf, (sizeof cmd_buf), getval("PIPESAVER",PIPESAVER)); ! 84: /* then set up for command */ ! 85: resetty(); /* restore tty state */ ! 86: if (use_pref) /* use preferred shell? */ ! 87: doshell(Nullch,cmd_buf); ! 88: /* do command with it */ ! 89: else ! 90: doshell(sh,cmd_buf); /* do command with sh */ ! 91: noecho(); /* and stop echoing */ ! 92: crmode(); /* and start cbreaking */ ! 93: savedest = savestr(savedest); ! 94: } ! 95: else { /* normal save */ ! 96: bool there, mailbox; ! 97: char *savename = getval("SAVENAME",SAVENAME); ! 98: ! 99: s = buf+1; /* skip s or S */ ! 100: if (*s == '-') { /* if they are confused, skip - also */ ! 101: #ifdef VERBOSE ! 102: IF(verbose) ! 103: fputs("Warning: '-' ignored. This isn't readnews.\n",stdout) ! 104: FLUSH; ! 105: ELSE ! 106: #endif ! 107: #ifdef TERSE ! 108: fputs("'-' ignored.\n",stdout) FLUSH; ! 109: #endif ! 110: s++; ! 111: } ! 112: for (; *s == ' '; s++); /* skip spaces */ ! 113: safecpy(altbuf,filexp(s),sizeof altbuf); ! 114: s = altbuf; ! 115: if (! index(s,'/')) { ! 116: interp(buf, (sizeof buf), getval("SAVEDIR",SAVEDIR)); ! 117: if (makedir(buf,MD_DIR)) /* ensure directory exists */ ! 118: strcpy(buf,cwd); ! 119: if (*s) { ! 120: for (c = buf; *c; c++) ; ! 121: *c++ = '/'; ! 122: strcpy(c,s); /* add filename */ ! 123: } ! 124: s = buf; ! 125: } ! 126: for (iter = 0; ! 127: (there = stat(s,&filestat) >= 0) && ! 128: (filestat.st_mode & S_IFDIR); ! 129: iter++) { /* is it a directory? */ ! 130: ! 131: c = (s+strlen(s)); ! 132: *c++ = '/'; /* put a slash before filename */ ! 133: interp(c, s==buf?(sizeof buf):(sizeof altbuf), ! 134: iter ? "News" : savename ); ! 135: /* generate a default name somehow or other */ ! 136: if (index(c,'/')) { /* yikes, a '/' in the filename */ ! 137: makedir(s,MD_FILE); ! 138: } ! 139: } ! 140: if (*s != '/') { /* relative path? */ ! 141: c = (s==buf ? altbuf : buf); ! 142: sprintf(c, "%s/%s", cwd, s); ! 143: s = c; /* absolutize it */ ! 144: } ! 145: s = savedest = savestr(s); /* doesn't move any more */ ! 146: /* make it handy for %b */ ! 147: if (!there) { ! 148: if (mbox_always) ! 149: mailbox = TRUE; ! 150: else if (norm_always) ! 151: mailbox = FALSE; ! 152: else { ! 153: char *dflt = (instr(savename,"%a") ? "nyq" : "ynq"); ! 154: ! 155: sprintf(cmd_buf, ! 156: "\nFile %s doesn't exist--\n use mailbox format? [%s] ", ! 157: s,dflt); ! 158: reask_save: ! 159: in_char(cmd_buf); ! 160: putchar('\n') FLUSH; ! 161: setdef(buf,dflt); ! 162: #ifdef VERIFY ! 163: printcmd(); ! 164: #endif ! 165: if (*buf == 'h') { ! 166: #ifdef VERBOSE ! 167: IF(verbose) ! 168: printf("\n\ ! 169: Type y to create %s as a mailbox.\n\ ! 170: Type n to create it as a normal file.\n\ ! 171: Type q to abort the save.\n\ ! 172: ",s) FLUSH; ! 173: ELSE ! 174: #endif ! 175: #ifdef TERSE ! 176: fputs("\n\ ! 177: y to create mailbox.\n\ ! 178: n to create normal file.\n\ ! 179: q to abort.\n\ ! 180: ",stdout) FLUSH; ! 181: #endif ! 182: goto reask_save; ! 183: } ! 184: else if (*buf == 'n') { ! 185: mailbox = FALSE; ! 186: } ! 187: else if (*buf == 'y') { ! 188: mailbox = TRUE; ! 189: } ! 190: else if (*buf == 'q') { ! 191: goto s_bomb; ! 192: } ! 193: else { ! 194: fputs(hforhelp,stdout) FLUSH; ! 195: settle_down(); ! 196: goto reask_save; ! 197: } ! 198: } ! 199: } ! 200: else if (filestat.st_mode & S_IFCHR) ! 201: mailbox = FALSE; ! 202: else { ! 203: int tmpfd; ! 204: ! 205: tmpfd = open(s,0); ! 206: if (tmpfd == -1) ! 207: mailbox = FALSE; ! 208: else { ! 209: read(tmpfd,buf,LBUFLEN); ! 210: c = buf; ! 211: if (!isspace(MBOXCHAR)) ! 212: while (isspace(*c)) ! 213: c++; ! 214: mailbox = (*c == MBOXCHAR); ! 215: close(tmpfd); ! 216: } ! 217: } ! 218: ! 219: safecpy(cmd_buf, filexp(mailbox ? ! 220: getval("MBOXSAVER",MBOXSAVER) : ! 221: getval("NORMSAVER",NORMSAVER) ), sizeof cmd_buf); ! 222: /* format the command */ ! 223: resetty(); /* make terminal behave */ ! 224: if (doshell(use_pref?Nullch:SH,cmd_buf)) ! 225: fputs("Not saved",stdout); ! 226: else ! 227: printf("%s to %s %s", ! 228: there?"Appended":"Saved", ! 229: mailbox?"mailbox":"file", ! 230: s); ! 231: if (interactive) ! 232: putchar('\n') FLUSH; ! 233: noecho(); /* make terminal do what we want */ ! 234: crmode(); ! 235: } ! 236: s_bomb: ! 237: #ifdef SERVER ! 238: if (chdir(spool)) { ! 239: #else ! 240: if (chdir(spool) || chdir(ngdir)) { ! 241: #endif ! 242: printf(nocd,ngdir) FLUSH; ! 243: sig_catcher(0); ! 244: } ! 245: return SAVE_DONE; ! 246: } ! 247: ! 248: int ! 249: cancel_article() ! 250: { ! 251: char *artid_buf; ! 252: char *ngs_buf; ! 253: char *from_buf; ! 254: char *reply_buf; ! 255: int myuid = getuid(); ! 256: int r = -1; ! 257: ! 258: if (artopen(art) == Nullfp) { ! 259: #ifdef VERBOSE ! 260: IF(verbose) ! 261: fputs("\n\ ! 262: Cancelling null articles is your idea of fun? :-)\n\ ! 263: ",stdout) FLUSH; ! 264: ELSE ! 265: #endif ! 266: #ifdef TERSE ! 267: fputs(nullart,stdout) FLUSH; ! 268: #endif ! 269: return r; ! 270: } ! 271: reply_buf = fetchlines(art,REPLY_LINE); ! 272: from_buf = fetchlines(art,FROM_LINE); ! 273: artid_buf = fetchlines(art,ARTID_LINE); ! 274: ngs_buf = fetchlines(art,NGS_LINE); ! 275: if (!instr(from_buf,sitename) || ! 276: (!instr(from_buf,logname) && ! 277: !instr(reply_buf,logname) && ! 278: #ifdef NEWSADMIN ! 279: myuid != newsuid && ! 280: #endif ! 281: myuid != ROOTID ) ) ! 282: #ifdef VERBOSE ! 283: IF(verbose) ! 284: fputs("You can't cancel someone else's article\n",stdout) ! 285: FLUSH; ! 286: ELSE ! 287: #endif ! 288: #ifdef TERSE ! 289: fputs("Not your article\n",stdout) FLUSH; ! 290: #endif ! 291: else { ! 292: tmpfp = fopen(headname,"w"); /* open header file */ ! 293: if (tmpfp == Nullfp) { ! 294: printf(cantcreate,headname) FLUSH; ! 295: goto no_cancel; ! 296: } ! 297: interp(buf, (sizeof buf), getval("CANCELHEADER",CANCELHEADER)); ! 298: fputs(buf,tmpfp); ! 299: fclose(tmpfp); ! 300: r = doshell(sh,filexp(getval("CANCEL",CANCEL))); ! 301: } ! 302: no_cancel: ! 303: free(artid_buf); ! 304: free(ngs_buf); ! 305: free(from_buf); ! 306: free(reply_buf); ! 307: return r; ! 308: } ! 309: ! 310: void ! 311: reply() ! 312: { ! 313: bool incl_body = (*buf == 'R'); ! 314: char *maildoer = savestr(filexp(getval("MAILPOSTER",MAILPOSTER))); ! 315: ! 316: artopen(art); ! 317: tmpfp = fopen(headname,"w"); /* open header file */ ! 318: if (tmpfp == Nullfp) { ! 319: printf(cantcreate,headname) FLUSH; ! 320: goto no_reply; ! 321: } ! 322: interp(buf, (sizeof buf), getval("MAILHEADER",MAILHEADER)); ! 323: fputs(buf,tmpfp); ! 324: if (!instr(maildoer,"%h")) ! 325: #ifdef VERBOSE ! 326: IF(verbose) ! 327: printf("\n%s\n(Above lines saved in file %s)\n",buf,headname) ! 328: FLUSH; ! 329: ELSE ! 330: #endif ! 331: #ifdef TERSE ! 332: printf("\n%s\n(Header in %s)\n",buf,headname) FLUSH; ! 333: #endif ! 334: if (incl_body && artfp != Nullfp) { ! 335: interp(buf, (sizeof buf), getval("YOUSAID",YOUSAID)); ! 336: fprintf(tmpfp,"%s\n",buf); ! 337: #ifdef ASYNC_PARSE ! 338: parse_maybe(art); ! 339: #endif ! 340: fseek(artfp,(long)htype[PAST_HEADER].ht_minpos,0); ! 341: while (fgets(buf,LBUFLEN,artfp) != Nullch) { ! 342: fprintf(tmpfp,"%s%s",indstr,buf); ! 343: } ! 344: fprintf(tmpfp,"\n"); ! 345: } ! 346: fclose(tmpfp); ! 347: interp(cmd_buf, (sizeof cmd_buf), maildoer); ! 348: invoke(cmd_buf,origdir); ! 349: UNLINK(headname); /* kill the header file */ ! 350: no_reply: ! 351: free(maildoer); ! 352: } ! 353: ! 354: void ! 355: followup() ! 356: { ! 357: bool incl_body = (*buf == 'F'); ! 358: ! 359: artopen(art); ! 360: tmpfp = fopen(headname,"w"); ! 361: if (tmpfp == Nullfp) { ! 362: printf(cantcreate,headname) FLUSH; ! 363: return; ! 364: } ! 365: interp(buf, (sizeof buf), getval("NEWSHEADER",NEWSHEADER)); ! 366: fprintf(tmpfp,"%s",buf); ! 367: if (incl_body && artfp != Nullfp) { ! 368: #ifdef VERBOSE ! 369: if (verbose) ! 370: fputs("\n\ ! 371: (Be sure to double-check the attribution against the signature, and\n\ ! 372: trim the quoted article down as much as possible.)\n\ ! 373: ",stdout) FLUSH; ! 374: #endif ! 375: interp(buf, (sizeof buf), getval("ATTRIBUTION",ATTRIBUTION)); ! 376: fprintf(tmpfp,"%s\n",buf); ! 377: #ifdef ASYNC_PARSE ! 378: parse_maybe(art); ! 379: #endif ! 380: fseek(artfp,(long)htype[PAST_HEADER].ht_minpos,0); ! 381: while (fgets(buf,LBUFLEN,artfp) != Nullch) { ! 382: fprintf(tmpfp,"%s%s",indstr,buf); ! 383: } ! 384: fprintf(tmpfp,"\n"); ! 385: } ! 386: fclose(tmpfp); ! 387: safecpy(cmd_buf,filexp(getval("NEWSPOSTER",NEWSPOSTER)),sizeof cmd_buf); ! 388: invoke(cmd_buf,origdir); ! 389: UNLINK(headname); ! 390: } ! 391: ! 392: void ! 393: invoke(cmd,dir) ! 394: char *cmd,*dir; ! 395: { ! 396: if (chdir(dir)) { ! 397: printf(nocd,dir) FLUSH; ! 398: return; ! 399: } ! 400: #ifdef VERBOSE ! 401: IF(verbose) ! 402: printf("\n(leaving cbreak mode; cwd=%s)\nInvoking command: %s\n\n", ! 403: dir,cmd) FLUSH; ! 404: ELSE ! 405: #endif ! 406: #ifdef TERSE ! 407: printf("\n(-cbreak; cwd=%s)\nInvoking: %s\n\n",dir,cmd) FLUSH; ! 408: #endif ! 409: resetty(); /* make terminal well-behaved */ ! 410: doshell(sh,cmd); /* do the command */ ! 411: noecho(); /* set no echo */ ! 412: crmode(); /* and cbreak mode */ ! 413: #ifdef VERBOSE ! 414: IF(verbose) ! 415: fputs("\n(re-entering cbreak mode)\n",stdout) FLUSH; ! 416: ELSE ! 417: #endif ! 418: #ifdef TERSE ! 419: fputs("\n(+cbreak)\n",stdout) FLUSH; ! 420: #endif ! 421: #ifdef SERVER ! 422: if (chdir(spool)) { ! 423: #else ! 424: if (chdir(spool) || chdir(ngdir)) { ! 425: #endif ! 426: printf(nocd,ngdir) FLUSH; ! 427: sig_catcher(0); ! 428: } ! 429: } ! 430:
This archive runs on limited infrastructure. Preserving old code on modern bandwidth. Automated agents are requested to crawl responsibly.