|
|
1.1 ! root 1: #ifndef lint ! 2: static char *sccsid = "@(#)inews.c 1.12 (Berkeley) 7/13/87"; ! 3: #endif ! 4: ! 5: /* ! 6: * Itty-bitty inews for talking to remote server. ! 7: * Simply accept input on stdin (or via a named file) and dump this ! 8: * to the server; add a From: and Path: line if missing in the original. ! 9: * Print meaningful errors from the server. ! 10: * Limit .signature files to MAX_SIGNATURE lines. ! 11: * ! 12: * Original by Steven Grady <[email protected]>, with thanks from ! 13: * Phil Lapsley <[email protected]>, who is now responsible for it. ! 14: */ ! 15: ! 16: #include <stdio.h> ! 17: #include <pwd.h> ! 18: #include <ctype.h> ! 19: #include <strings.h> ! 20: #include "../common/conf.h" ! 21: #include "../common/response_codes.h" ! 22: ! 23: #define MAX_SIGNATURE 4 ! 24: ! 25: extern FILE *ser_wr_fp; ! 26: ! 27: char host_name[256]; ! 28: ! 29: main(argc, argv) ! 30: int argc; ! 31: char *argv[]; ! 32: { ! 33: char line[256], s[256]; ! 34: int seen_fromline, in_header; ! 35: int response; ! 36: char *server; ! 37: char *getserverbyfile(); ! 38: register char *cp; ! 39: ! 40: ++argv; ! 41: while (argc > 1) ! 42: if (*argv[0] == '-') { ! 43: ++argv; ! 44: --argc; ! 45: } else ! 46: break; ! 47: ! 48: if (argc > 1) { ! 49: if (freopen(*argv, "r", stdin) == NULL) { ! 50: perror(*argv); ! 51: exit(1); ! 52: } ! 53: } ! 54: ! 55: uname(host_name); ! 56: ! 57: server = getserverbyfile(SERVER_FILE); ! 58: if (server == NULL) { ! 59: fprintf(stderr, ! 60: "Can't get the name of the news server from %s.\n", ! 61: SERVER_FILE); ! 62: fprintf(stderr, ! 63: "Either fix this file, or put NNTPSERVER in your enviroment.\n"); ! 64: exit(1); ! 65: } ! 66: ! 67: response = server_init(server); ! 68: if (response < 0) { ! 69: printf("Couldn't connect to %s news server, try again later.\n", ! 70: server); ! 71: exit(1); ! 72: } ! 73: ! 74: if (handle_server_response(response, server) < 0 ! 75: || response == OK_NOPOST) { ! 76: close_server(); ! 77: exit(1); ! 78: } ! 79: ! 80: put_server("POST"); ! 81: (void) get_server(line, sizeof(line)); ! 82: if (*line != CHAR_CONT) { ! 83: if (atoi(line) == ERR_NOPOST) { ! 84: close_server(); ! 85: fprintf(stderr, ! 86: "Sorry, you can't post from this machine.\n"); ! 87: exit(1); ! 88: } else { ! 89: close_server(); ! 90: fprintf(stderr, "Remote error: %s\n", line); ! 91: exit(1); ! 92: } ! 93: } ! 94: ! 95: in_header = 1; ! 96: seen_fromline = 0; ! 97: ! 98: while (gets(s) != NULL) { ! 99: if (s[0] == '.') /* Single . is eof, so put in extra one */ ! 100: (void) fputc('.', ser_wr_fp); ! 101: if (in_header && strneql(s, "From:", sizeof("From:")-1)) ! 102: seen_fromline = 1; ! 103: if (in_header && s[0] == '\0') { ! 104: in_header = 0; ! 105: if (!seen_fromline) ! 106: gen_frompath(); ! 107: } ! 108: fprintf(ser_wr_fp, "%s\r\n", s); ! 109: } ! 110: ! 111: append_signature(); ! 112: ! 113: fprintf(ser_wr_fp, ".\r\n"); ! 114: (void) fflush(ser_wr_fp); ! 115: (void) get_server(line, sizeof(line)); ! 116: if (*line != CHAR_OK) { ! 117: if (atoi(line) == ERR_POSTFAIL) { ! 118: close_server(); ! 119: printf("Article not accepted by server; not posted.\n"); ! 120: for (cp = line + 4; *cp && *cp != '\r'; cp++) ! 121: if (*cp == '\\') ! 122: putchar('\n'); ! 123: else ! 124: putchar(*cp); ! 125: exit(1); ! 126: } else { ! 127: close_server(); ! 128: fprintf(stderr, "Remote error: %s\n", line); ! 129: exit(1); ! 130: } ! 131: } ! 132: ! 133: /* ! 134: * Close server sends the server a ! 135: * "quit" command for us, which is why we don't send it. ! 136: */ ! 137: ! 138: close_server(); ! 139: ! 140: exit(0); ! 141: } ! 142: ! 143: /* ! 144: * append_signature -- append the person's .signature file if ! 145: * they have one. Limit .signature to MAX_SIGNATURE lines. ! 146: */ ! 147: ! 148: append_signature() ! 149: { ! 150: char line[256], sigfile[256]; ! 151: char *cp; ! 152: struct passwd *passwd; ! 153: FILE *fp; ! 154: char *index(); ! 155: int count = 0; ! 156: ! 157: passwd = getpwuid(getuid()); ! 158: if (passwd == NULL) ! 159: return; ! 160: ! 161: (void) strcpy(sigfile, passwd->pw_dir); ! 162: (void) strcat(sigfile, "/"); ! 163: (void) strcat(sigfile, ".signature"); ! 164: ! 165: fp = fopen(sigfile, "r"); ! 166: if (fp == NULL) ! 167: return; ! 168: ! 169: while (fgets(line, sizeof (line), fp)) { ! 170: count++; ! 171: if (count > MAX_SIGNATURE) { ! 172: fprintf(stderr, ! 173: "Warning: .signature files should be no longer than %d lines.\n", ! 174: MAX_SIGNATURE); ! 175: fprintf(stderr, ! 176: "(Only %d lines of your .signature were posted.)\n", ! 177: MAX_SIGNATURE); ! 178: break; ! 179: } ! 180: if (cp = index(line, '\n')) ! 181: *cp = '\0'; ! 182: fprintf(ser_wr_fp, "%s\r\n", line); ! 183: } ! 184: (void) fclose(fp); ! 185: } ! 186: ! 187: ! 188: /* ! 189: * gen_frompath -- generate From: and Path: lines, in the form ! 190: * ! 191: * From: [email protected] (full_name) ! 192: * Path: host!user ! 193: * ! 194: * This routine should only be called if the message doesn't have ! 195: * a From: line in it. ! 196: */ ! 197: ! 198: gen_frompath() ! 199: { ! 200: char *full_name; ! 201: char *cp; ! 202: struct passwd *passwd; ! 203: char *index(), *getenv(); ! 204: ! 205: passwd = getpwuid(getuid()); ! 206: ! 207: full_name = getenv("NAME"); ! 208: if (full_name == NULL) { ! 209: full_name = passwd->pw_gecos; ! 210: if ((cp = index(full_name, ','))) ! 211: *cp = '\0'; ! 212: } ! 213: ! 214: #ifdef DOMAIN ! 215: ! 216: /* A heuristic to see if we should tack on a domain */ ! 217: ! 218: cp = index(host_name, '.'); ! 219: if (cp) ! 220: fprintf(ser_wr_fp, "From: %s@%s (", ! 221: passwd->pw_name, ! 222: host_name); ! 223: else ! 224: fprintf(ser_wr_fp, "From: %s@%s.%s (", ! 225: passwd->pw_name, ! 226: host_name, ! 227: DOMAIN); ! 228: #else ! 229: fprintf(ser_wr_fp, "From: %s@%s (", ! 230: passwd->pw_name, ! 231: host_name); ! 232: #endif ! 233: ! 234: for (cp = full_name; *cp != '\0'; ++cp) ! 235: if (*cp != '&') ! 236: putc(*cp, ser_wr_fp); ! 237: else { /* Stupid & hack. God damn it. */ ! 238: putc(toupper(passwd->pw_name[0]), ser_wr_fp); ! 239: fprintf(ser_wr_fp, passwd->pw_name+1); ! 240: } ! 241: ! 242: fprintf(ser_wr_fp, ")\r\n"); ! 243: ! 244: fprintf(ser_wr_fp, "Path: %s!%s\r\n", host_name, passwd->pw_name); ! 245: } ! 246: ! 247: ! 248: /* ! 249: * strneql -- determine if two strings are equal in the first n ! 250: * characters, ignoring case. ! 251: * ! 252: * Parameters: "a" and "b" are the pointers ! 253: * to characters to be compared. ! 254: * "n" is the number of characters to compare. ! 255: * ! 256: * Returns: 1 if the strings are equal, 0 otherwise. ! 257: * ! 258: * Side effects: None. ! 259: */ ! 260: ! 261: strneql(a, b, n) ! 262: register char *a, *b; ! 263: int n; ! 264: { ! 265: char lower(); ! 266: ! 267: while (n && lower(*a) == lower(*b)) { ! 268: if (*a == '\0') ! 269: return (1); ! 270: a++; ! 271: b++; ! 272: n--; ! 273: } ! 274: if (n) ! 275: return (0); ! 276: else ! 277: return (1); ! 278: } ! 279: ! 280: /* ! 281: * lower -- convert a character to lower case, if it's ! 282: * upper case. ! 283: * ! 284: * Parameters: "c" is the character to be ! 285: * converted. ! 286: * ! 287: * Returns: "c" if the character is not ! 288: * upper case, otherwise the lower ! 289: * case eqivalent of "c". ! 290: * ! 291: * Side effects: None. ! 292: */ ! 293: ! 294: char lower(c) ! 295: register char c; ! 296: { ! 297: if (isascii(c) && isupper(c)) ! 298: c = c - 'A' + 'a'; ! 299: return(c); ! 300: }
This archive runs on limited infrastructure. Preserving old code on modern bandwidth. Automated agents are requested to crawl responsibly.