home *** CD-ROM | disk | FTP | other *** search
/ ftp.wwiv.com / ftp.wwiv.com.zip / ftp.wwiv.com / pub / PPPBCKP / SRC / SRC15B24.ZIP / EXP.C < prev    next >
Text File  |  1997-04-05  |  31KB  |  1,142 lines

  1. #include <stdio.h>
  2. #include <stdlib.h>
  3. #include <string.h>
  4. #include <dos.h>
  5. #include <fcntl.h>
  6. #include <sys/stat.h>
  7. #include <ctype.h>
  8. #include <mem.h>
  9. #include <conio.h>
  10. #include <io.h>
  11. #include <share.h>
  12. #include <errno.h>
  13. #include <dir.h>
  14. #include <time.h>
  15. #include <malloc.h>
  16. #include <process.h>
  17. #include <direct.h>
  18. #include "vardec.h"
  19. #include "net.h"
  20.  
  21. #include "version.h"
  22.  
  23. #define WAIT_TIME 10
  24. #define TRIES 100
  25. #define SHARE_LEVEL 10
  26. #define MT_DESQVIEW 0x01
  27. #define MT_WINDOWS  0x02
  28. #define MT_OS2      0x04
  29. #define MT_NB       0x40
  30.  
  31.  
  32. struct msghdr {
  33.   char fromUserName[205];
  34.   char toUserName[81];
  35.   char subject[81];
  36.   char dateTime[81];
  37. };
  38.  
  39. configrec syscfg;
  40. char *net_name, postmaster[31], net_data[MAXPATH], POPNAME[21], DOMAIN[81], tagfile[MAXPATH], maindir[MAXPATH];
  41. unsigned short net_sysnum, defuser, num_users, use_alias, instance, curuser, spam;
  42. int multitasker = 0;
  43.  
  44. void dv_pause(void)
  45. {
  46.   __emit__(0xb8, 0x1a, 0x10, 0xcd, 0x15);
  47.   __emit__(0xb8, 0x00, 0x10, 0xcd, 0x15);
  48.   __emit__(0xb8, 0x25, 0x10, 0xcd, 0x15);
  49. }
  50.  
  51. void win_pause(void)
  52. {
  53.   __emit__(0x55, 0xb8, 0x80, 0x16, 0xcd, 0x2f, 0x5d);
  54. }
  55.  
  56. int get_dos_version(void)
  57. {
  58.   _AX = 0x3000;
  59.   geninterrupt(0x21);
  60.   if (_AX % 256 >= 10) {
  61.     multitasker |= MT_OS2;
  62.   }
  63.   return (_AX);
  64. }
  65.  
  66. int get_dv_version(void)
  67. {
  68.   int v;
  69.  
  70.   if (multitasker & MT_OS2)
  71.     return 0;
  72.   _AX = 0x2b01;
  73.   _CX = 0x4445;
  74.   _DX = 0x5351;
  75.   geninterrupt(0x21);
  76.   if (_AL == 0xff) {
  77.     return 0;
  78.   } else {
  79.     v = _BX;
  80.     multitasker |= MT_DESQVIEW;
  81.     return v;
  82.   }
  83. }
  84.  
  85. int get_win_version(void)
  86. {
  87.   int v = 0;
  88.  
  89.   __emit__(0x55, 0x06, 0x53);
  90.   _AX = 0x352f;
  91.   geninterrupt(0x21);
  92.   _AX = _ES;
  93.   if (_AX | _BX) {
  94.     _AX = 0x1600;
  95.     geninterrupt(0x2f);
  96.     v = _AX;
  97.     if (v % 256 <= 1)
  98.       v = 0;
  99.   }
  100.   __emit__(0x5b, 0x07, 0x5d);
  101.   if (v != 0)
  102.     multitasker |= MT_WINDOWS;
  103.   return (v);
  104. }
  105.  
  106. int get_nb_version(void)
  107. {
  108.   _AX = 0;
  109.   geninterrupt(0x2A);
  110.   return (_AH);
  111. }
  112.  
  113. void detect_multitask(void)
  114. {
  115.   get_dos_version();
  116.   get_win_version();
  117.   get_dv_version();
  118. }
  119.  
  120. void giveup_timeslice(void)
  121. {
  122.   if (multitasker) {
  123.     switch (multitasker) {
  124.  case 1: 
  125.  case 3: 
  126.         dv_pause();
  127.         break;
  128.       case 2:
  129.       case 4:
  130.       case 5:
  131.       case 6:
  132.       case 7:
  133.         win_pause();
  134.         break;
  135.       default:
  136.         break;
  137.     }
  138.   }
  139. }
  140.  
  141. int sh_write(int handle, void *buffer, unsigned long len)
  142. {
  143.   if (handle == -1) {
  144.     return (-1);
  145.   }
  146.   return (write(handle, buffer, (unsigned) len));
  147. }
  148.  
  149. int sh_open(char *path, int file_access, unsigned fmode)
  150. {
  151.   int handle, count, share;
  152.   char drive[MAXDRIVE], dir[MAXDIR], file[MAXFILE], ext[MAXEXT];
  153.  
  154.   if ((file_access & O_RDWR) || (file_access & O_WRONLY) || (fmode & S_IWRITE)) {
  155.     share = SH_DENYRW;
  156.   } else {
  157.     share = SH_DENYWR;
  158.   }
  159.   handle = open(path, file_access | share, fmode);
  160.   if (handle < 0) {
  161.     count = 1;
  162.     fnsplit(path, drive, dir, file, ext);
  163.     if (access(path, 0) != -1) {
  164.       delay(WAIT_TIME);
  165.       handle = open(path, file_access | share, fmode);
  166.       while (((handle < 0) && (errno == EACCES)) && (count < TRIES)) {
  167.         if (count % 2)
  168.           delay(WAIT_TIME);
  169.         else
  170.           giveup_timeslice();
  171.         count++;
  172.         handle = open(path, file_access | share, fmode);
  173.       }
  174.     }
  175.   }
  176.   return (handle);
  177. }
  178.  
  179. int sh_open1(char *path, int access)
  180. {
  181.   unsigned fmode;
  182.  
  183.   fmode = 0;
  184.   if ((access & O_RDWR) || (access & O_WRONLY))
  185.     fmode |= S_IWRITE;
  186.   if ((access & O_RDWR) || (access & O_RDONLY))
  187.     fmode |= S_IREAD;
  188.   return (sh_open(path, access, fmode));
  189. }
  190.  
  191. int sh_close(int f)
  192. {
  193.   if (f != -1)
  194.     close(f);
  195.   return (-1);
  196. }
  197.  
  198. int sh_read(int handle, void *buf, unsigned len)
  199. {
  200.   if (handle == -1) {
  201.     return (-1);
  202.   }
  203.   return (read(handle, buf, len));
  204. }
  205.  
  206. long sh_lseek(int handle, long offset, int fromwhere)
  207. {
  208.   if (handle == -1) {
  209.     return (-1L);
  210.   }
  211.   return (lseek(handle, offset, fromwhere));
  212. }
  213.  
  214. FILE *fsh_open(char *path, char *fmode)
  215. {
  216.   FILE *f;
  217.   int count, share, md, fd;
  218.   char drive[MAXDRIVE], dir[MAXDIR], file[MAXFILE], ext[MAXEXT];
  219.  
  220.   share = SH_DENYWR;
  221.   md = 0;
  222.   if (((char *) _fstrchr(fmode, 'w')) != NULL) {
  223.     share = SH_DENYRD;
  224.     md = O_RDWR | O_CREAT | O_TRUNC;
  225.   } else
  226.     if (((char *) _fstrchr(fmode, 'a')) != NULL) {
  227.     share = SH_DENYRD;
  228.     md = O_RDWR | O_CREAT;
  229.   } else {
  230.     md = O_RDONLY;
  231.   }
  232.   if (((char *) _fstrchr(fmode, 'b')) != NULL) {
  233.     md |= O_BINARY;
  234.   }
  235.   if (((char *) _fstrchr(fmode, '+')) != NULL) {
  236.     md &= ~O_RDONLY;
  237.     md |= O_RDWR;
  238.     share = SH_DENYRD;
  239.   }
  240.   fd = open(path, md | share, S_IREAD | S_IWRITE);
  241.   if (fd < 0) {
  242.     count = 1;
  243.     fnsplit(path, drive, dir, file, ext);
  244.     if ((access(path, 0)) != -1) {
  245.       delay(WAIT_TIME);
  246.       fd = open(path, md | share, S_IREAD | S_IWRITE);
  247.       while (((fd < 0) && (errno == EACCES)) && (count < TRIES)) {
  248.         delay(WAIT_TIME);
  249.         count++;
  250.         fd = open(path, md | share, S_IREAD | S_IWRITE);
  251.       }
  252.     }
  253.   }
  254.   if (fd > 0) {
  255.     if (((char *) _fstrchr(fmode, 'a')) != NULL)
  256.       sh_lseek(fd, 0L, SEEK_END);
  257.     f = fdopen(fd, fmode);
  258.     if (!f) {
  259.       close(fd);
  260.     }
  261.   } else
  262.     f = 0;
  263.   return (f);
  264. }
  265.  
  266. size_t fsh_write(void *ptr, size_t size, size_t n, FILE *stream)
  267. {
  268.  
  269.   if (stream == NULL) {
  270.     return(0);
  271.   }
  272.   return(fwrite(ptr, size, n, stream));
  273. }
  274.  
  275.  
  276. int exist(char *s)
  277. {
  278.   int i;
  279.   struct ffblk ff;
  280.  
  281.   i = findfirst(s, &ff, 0);
  282.   if (i)
  283.     return (0);
  284.   else
  285.     return (1);
  286. }
  287.  
  288. char *stripspace(char *str)
  289. {
  290.   char *obuf, *nbuf;
  291.  
  292.   if (str) {
  293.     for (obuf = str, nbuf = str; *obuf; ++obuf) {
  294.       if (!isspace(*obuf))
  295.         *nbuf++ = *obuf;
  296.     }
  297.     *nbuf = NULL;
  298.   }
  299.   return (str);
  300. }
  301.  
  302. static unsigned char *trimstr1(unsigned char *s)
  303. {
  304.   int i;
  305.   static char *whitespace = " \r\n\t";
  306.  
  307.   i = (int) strlen(s);
  308.   while ((i > 0) && ((char *) _fstrchr(whitespace, s[i - 1]) != NULL))
  309.     --i;
  310.   while ((i > 0) && ((char *) _fstrchr(whitespace, *s) != NULL)) {
  311.     memmove(s, s + 1, --i);
  312.   }
  313.   s[i] = 0;
  314.   return (s);
  315. }
  316.  
  317.  
  318. int num_to_name(char *where, int whichuser, int alias);
  319.  
  320. void parse_net_ini(void)
  321. {
  322.  
  323.   char s[MAXPATH], line[121], *ss;
  324.   FILE *fp;
  325.  
  326.   defuser = 1;
  327.   use_alias = 1;
  328.   sprintf(s, "%sNET.INI", maindir);
  329.   fp = fsh_open(s, "rt");
  330.   if (!fp) {
  331.     fprintf(stderr, "\n ■ Unable to open %s.", s);
  332.     return;
  333.   }
  334.   while (fgets(line, 80, fp)) {
  335.     ss = NULL;
  336.     stripspace(line);
  337.     /* fprintf(stderr, "\nCurrent : %s\n", line); */
  338.     if ((line[0] == ';') || (line[0] == '\n') || (line[0] == '['))
  339.       continue;
  340.     if (strlen(line) == 0)
  341.       continue;
  342.     if (strnicmp(line, "POSTMASTER", 10) == 0) {
  343.       ss = strtok(line, "=");
  344.       if (ss) {
  345.         ss = strtok(NULL, "\n");
  346.         if (ss)
  347.           defuser = atoi(ss);
  348.       }
  349.     }
  350.     if (strnicmp(line, "SPAMCONTROL", 11) == 0) {
  351.       ss = strtok(line, "=");
  352.       if (ss) {
  353.         ss = strtok(NULL, "\n");
  354.         if ((ss[0] == 'y') || (ss[0] == 'Y'))
  355.           spam = 1;
  356.       }
  357.     }
  358.     if (strnicmp(line, "SIGNATURE", 9) == 0) {
  359.       ss = strtok(line, "=");
  360.       if (ss) {
  361.         ss = strtok(NULL, "\n");
  362.         trimstr1(ss);
  363.         strcpy(tagfile, ss);
  364.         if (!exist(tagfile)) {
  365.           fprintf(stderr, "\n ■ Default signature file %s not found!", tagfile);
  366.           tagfile[0] = 0;
  367.         }
  368.       }
  369.     }
  370.     if (strnicmp(line, "REALNAME", 8) == 0) {
  371.       ss = strtok(line, "=");
  372.       if (ss) {
  373.         ss = strtok(NULL, "\n");
  374.         if ((ss[0] == 'y') || (ss[0] == 'Y'))
  375.           use_alias = 0;
  376.       }
  377.     }
  378.   }
  379.   num_to_name(postmaster, defuser, 1);
  380.   fclose(fp);
  381.   return;
  382. }
  383.  
  384. int num_to_name(char *where, int whichuser, int alias)
  385. {
  386.   int userfile, num_users, found;
  387.   userrec ur;
  388.   long pos;
  389.   char fn[MAXPATH];
  390.  
  391.   found = 0;
  392.   sprintf(fn, "%sUSER.LST", syscfg.datadir);
  393.   userfile = sh_open1(fn, O_RDONLY | O_BINARY);
  394.   if (userfile < 0) {
  395.     fprintf(stderr, "\n ■ Cannot open %s.", fn);
  396.     return (found);
  397.   }
  398.   num_users = ((int) (filelength(userfile) / sizeof(userrec)));
  399.  
  400.   if (whichuser > num_users) {
  401.     fprintf(stderr, "\n ■ User #%d out of range.", whichuser);
  402.     return (found);
  403.   }
  404.   pos = ((long) sizeof(userrec) * ((long) whichuser));
  405.   lseek(userfile, pos, SEEK_SET);
  406.   sh_read(userfile, &ur, sizeof(userrec));
  407.   if (ur.realname[0] == 0)
  408.     fprintf(stderr, "\n ■ User #%d has blank real name field!", whichuser);
  409.   else {
  410.     if (ur.inact == inact_deleted)
  411.       fprintf(stderr, "\n ■ User #%d is marked as deleted!", whichuser);
  412.     else {
  413.       if (!alias)
  414.         strcpy(where, ur.realname);
  415.       else {
  416.         strlwr(ur.name);
  417.         strcpy(where, ur.name);
  418.       }
  419.       found = 1;
  420.     }
  421.   }
  422.   sh_close(userfile);
  423.   return (found);
  424. }
  425.  
  426. unsigned char *strrep(char *str, char old, char New)
  427. {
  428.   int i;
  429.  
  430.   for (i = 0; str[i]; i++)
  431.     if (str[i] == old)
  432.       str[i] = New;
  433.   return (str);
  434. }
  435.  
  436.  
  437. int name_to_num(char *name)
  438. {
  439.   int userfile, usernum;
  440.   userrec ur;
  441.   long pos;
  442.   char fn[MAXPATH], ur_name[60], ur_realname[60];
  443.  
  444.   sprintf(fn, "%sUSER.LST", syscfg.datadir);
  445.   userfile = sh_open1(fn, O_RDONLY | O_BINARY);
  446.   if (userfile < 0) {
  447.     fprintf(stderr, "\n ■ Cannot open %s", fn);
  448.     return (0);
  449.   } else
  450.     fprintf(stderr, "\n ■ Searching for user \"%s\"...", name);
  451.   num_users = ((int) (filelength(userfile) / sizeof(userrec)));
  452.  
  453.   for (usernum = 1; usernum < num_users; usernum++) {
  454.     pos = ((long) sizeof(userrec) * ((long) usernum));
  455.     lseek(userfile, pos, SEEK_SET);
  456.     sh_read(userfile, &ur, sizeof(userrec));
  457.     strcpy(ur_realname, ur.realname);
  458.     strrep(ur_realname, ' ', '_');
  459.     strcpy(ur_name, ur.name);
  460.     strrep(ur_name, ' ', '_');
  461.     if ((strcmpi(ur.realname, name) == 0) || (strcmpi(ur_realname, name) == 0) ||
  462.         (strcmpi(ur.name, name) == 0) || (strcmpi(ur_name, name) == 0)) {
  463.       if (ur.inact == inact_deleted) {
  464.         fprintf(stderr, " user #%d is deleted account.", usernum);
  465.         usernum = 0;
  466.         break;
  467.       } else {
  468.         fprintf(stderr, " matched user #%d.", usernum);
  469.         break;
  470.       }
  471.     }
  472.   }
  473.   userfile = sh_close(userfile);
  474.  
  475.   if (usernum >= num_users) {
  476.     fprintf(stderr, "... no match found.");
  477.     return (0);
  478.   }
  479.   return (usernum);
  480. }
  481.  
  482. char *find_name(char *name)
  483. {
  484.   char *ss;
  485.  
  486.   curuser = 0;
  487.   if (strcspn(name, "(") != strlen(name)) {
  488.     ss = strtok(name, "(");
  489.     ss = strtok(NULL, ")");
  490.     strcpy(name, ss);
  491.     curuser = name_to_num(name);
  492.   } else
  493.     if (strcspn(name, "\"") != strlen(name)) {
  494.     ss = strtok(name, "\"");
  495.     ss = strtok(NULL, "\"");
  496.     strcpy(name, ss);
  497.     curuser = name_to_num(name);
  498.   } else
  499.     if (strcspn(name, "<") != strlen(name)) {
  500.     if ((strcspn(name, " ")) < (strcspn(name, "<"))) {
  501.       ss = strtok(name, "<");
  502.       trimstr1(ss);
  503.       strcpy(name, ss);
  504.       curuser = name_to_num(name);
  505.     } else {
  506.       fprintf(stderr, "\nName is *after* host in \"%s\"", name);
  507.     }
  508.     }
  509.   if (curuser == 0)
  510.     return ('\0');
  511.   else
  512.     return (ss);
  513. }
  514.  
  515. void name_packet(char *pktname)
  516. {
  517.   int ok;
  518.   struct stat info;
  519.   unsigned i;
  520.  
  521.   ok = 0;
  522.   for (i = 0; ((i < 1000) && (!ok)); i++) {
  523.     sprintf(pktname, "%sP0-%u.%3.3hu", net_data, i, instance);
  524.     if (stat(pktname, &info) == -1)
  525.       ok = 1;
  526.   }
  527. }
  528.  
  529.  
  530. int import(char *fn)
  531. {
  532.   char s[513], pktname[MAXPATH], msgdate[31], *ss, *p;
  533.   int f, from, subj, intext, done;
  534.   long textlen, reallen;
  535.   struct msghdr mh;
  536.   net_header_rec nh;
  537.   struct date dt;
  538.   struct time tm;
  539.   FILE *fp;
  540.  
  541.   intext = 0;
  542.   f = sh_open1(fn, O_RDONLY | O_BINARY);
  543.   if (f < 0)
  544.     return (1);
  545.   textlen = filelength(f);
  546.   if (textlen > 32767L) {
  547.     fprintf(stderr, "\n ■ Skipping %s - greater than 32K.", fn);
  548.     return (1);
  549.   }
  550.   p = (char *) malloc(textlen + 1);
  551.   if (p == NULL) {
  552.     fprintf(stderr, "\n ■ Unable to allocate %ld bytes.", textlen);
  553.     return (1);
  554.   }
  555.   sh_read(f, (void *) p, textlen);
  556.   sh_close(f);
  557.  
  558.   nh.tosys = net_sysnum;
  559.   nh.fromsys = 32767L;
  560.   nh.fromuser = 0;
  561.   nh.touser = defuser;
  562.   nh.main_type = main_type_email;
  563.   nh.minor_type = 0;
  564.   nh.list_len = 0;
  565.   gettime(&tm);
  566.   getdate(&dt);
  567.   nh.daten = dostounix(&dt, &tm);
  568.   nh.method = 0;
  569.  
  570.   fp = fsh_open(fn, "rb");
  571.   if (!fp) {
  572.     free(p);
  573.     return (1);
  574.   }
  575.   from = subj = done = 0;
  576.   while ((fgets(s, 254, fp)) && !done) {
  577.     if ((s[0] == '\r') || (s[0] == '\n') || (s[0] == 0))
  578.       intext = 1;
  579.     if (s[0] == 4) {
  580.       ss = strtok(s, "R");
  581.       ss = strtok(NULL, "\r\n");
  582.       strcpy(s, ss);
  583.     }
  584.     if (!intext) {
  585.       if ((strncmpi(s, "reply-to:", 9) == 0)) {
  586.         from = 1;
  587.         ss = strtok(s, ": ");
  588.         ss = strtok(NULL, "\r\n");
  589.         trimstr1(ss);
  590.         /* strncpy(mh.fromUserName, ss, 46); */
  591.         strcpy(mh.fromUserName, ss);
  592.         if (strlen(mh.fromUserName) > 190)
  593.           mh.fromUserName[190] = '\0';
  594.         strcat(mh.fromUserName, "\r\n");
  595.       } else
  596.         if ((strncmpi(s, "from:", 5) == 0) && (!from)) {
  597.         from = 1;
  598.         ss = strtok(s, ": ");
  599.         ss = strtok(NULL, "\r\n");
  600.         trimstr1(ss);
  601.         /* strncpy(mh.fromUserName, ss, 46); */
  602.         strcpy(mh.fromUserName, ss);
  603.         if (strlen(mh.fromUserName) > 190)
  604.           mh.fromUserName[190] = '\0';
  605.         strcat(mh.fromUserName, "\r\n");
  606.       } else
  607.         if ((strncmpi(s, "return-path:", 12) == 0) && (!from)) {
  608.         ss = strtok(s, ": ");
  609.         ss = strtok(NULL, "\r\n");
  610.         trimstr1(ss);
  611.         /* strncpy(mh.fromUserName, ss, 46); */
  612.         strcpy(mh.fromUserName, ss);
  613.         if (strlen(mh.fromUserName) > 190)
  614.           mh.fromUserName[190] = '\0';
  615.         strcat(mh.fromUserName, "\r\n");
  616.       } else
  617.         if ((strncmpi(s, "subject:", 8) == 0) && (!subj)) {
  618.         ss = strtok(s, ": ");
  619.         ss = strtok(NULL, "\r\n");
  620.         trimstr1(ss);
  621.         strcpy(mh.subject, ss);
  622.         if (strlen(mh.subject) > 72)
  623.           mh.subject[72] = '\0';
  624.         else
  625.           mh.subject[strlen(mh.subject)] = '\0';
  626.       } else
  627.         if ((strncmpi(s, "to:", 3) == 0) || (strncmpi(s, "cc:", 3) == 0)) {
  628.         ss = strtok(s, ": ");
  629.         ss = strtok(NULL, "\r\n");
  630.         strcpy(mh.toUserName, ss);
  631.         trimstr1(mh.toUserName);
  632.         if (_fstrstr(mh.toUserName, " "))
  633.           find_name(mh.toUserName);
  634.         else
  635.           mh.toUserName[0] = '\0';
  636.         if ((mh.toUserName[0] == 0) || (curuser == 0)) {
  637.           nh.touser = defuser;
  638.           strcpy(mh.toUserName, postmaster);
  639.         } else
  640.           nh.touser = curuser;
  641.         }
  642.     } else
  643.       done = 1;
  644.   }
  645.   fclose(fp);
  646.   fprintf(stderr, "\n ■ From    : %s", mh.fromUserName);
  647.   fprintf(stderr, " ■ Sent to : %s #%hd", strupr(mh.toUserName), nh.touser);
  648.   fprintf(stderr, "\n ■ Subject : %s", mh.subject);
  649.   name_packet(pktname);
  650.   fp = fsh_open(pktname, "wb");
  651.   if (fp < 0) {
  652.     fprintf(stderr, "\n ■ Unable to create packet %s", pktname);
  653.     free(p);
  654.     return (1);
  655.   }
  656.   strncpy(msgdate, ctime(&(time_t) nh.daten), 24);
  657.   msgdate[24] = '\0';
  658.   strcat(msgdate, "\r\n");
  659.   nh.length = textlen + strlen(mh.fromUserName) + strlen(mh.subject) + strlen(msgdate) + 1;
  660.   fsh_write(&nh, sizeof(net_header_rec), 1, fp);
  661.   fsh_write(mh.subject, sizeof(char), strlen(mh.subject) +1, fp);
  662.   fsh_write(mh.fromUserName, sizeof(char), strlen(mh.fromUserName), fp);
  663.   fsh_write(msgdate, sizeof(char), strlen(msgdate), fp);
  664.   reallen = fsh_write(p, sizeof(char), textlen, fp);
  665.   if (reallen != textlen)
  666.     fprintf(stderr, "\n ■ Expected %ld bytes, wrote %ld bytes.", textlen, reallen);
  667.   fclose(fp);
  668.   free(p);
  669.   return (0);
  670. }
  671.  
  672. unsigned char *stripcolors(unsigned char *text)
  673. {
  674.   static unsigned char s[161];
  675.   int i, i1;
  676.  
  677.   if (strlen(text) == 0)
  678.     return ("");
  679.  
  680.   i = 0;
  681.   i1 = 0;
  682.   do {
  683.     if (text[i] == 3)
  684.       i++;
  685.     else {
  686.       s[i1] = text[i];
  687.       i1++;
  688.     }
  689.     i++;
  690.   } while (i < strlen(text));
  691.   s[i1] = 0;
  692.   return (s);
  693. }
  694.  
  695. int export(char *fn)
  696. {
  697.   char fn1[121], tagfn[121], groupname[81], outfn[121], _temp_buffer[256];
  698.   char *ss, *buffer, *text;
  699.   unsigned stype, ttype;
  700.   int infile, outfile, inloc, outloc, term, ok, i, j;
  701.   net_header_rec nhr;
  702.   struct msghdr mh;
  703.   struct tm *time_msg;
  704.   FILE *fp;
  705.   time_t some;
  706.   char *main_type[] =
  707.   {
  708.     "Network Update", "email by usernum", "post from sub host", "file",
  709.     "post to sub host", "external message", "email by name",
  710.     "NetEdit message", "SUBS.LST", "Extra Data", "BBSLIST from GC",
  711.     "CONNECT from GC", "Unused_1", "Info from GC", "SSM", "Sub Add Request",
  712.     "Sub Drop Request", "Sub Add Response", "Sub Drop Response", "Sub Info"
  713.   };
  714.  
  715.   if ((infile = sh_open1(fn, O_RDONLY | O_BINARY)) == -1)
  716.     return (1);
  717.  
  718.   if ((buffer = (char *) malloc(32 * 1024)) == NULL) {
  719.     fprintf(stderr, "\n ■ Out of memory allocating input buffer!");
  720.     return (1);
  721.   }
  722.   if ((text = (char *) malloc(32 * 1024)) == NULL) {
  723.     fprintf(stderr, "\n ■ Out of memory allocating output buffer!");
  724.     if (buffer)
  725.       free(buffer);
  726.     buffer = NULL;
  727.     return (1);
  728.   }
  729.   while (sh_read(infile, &nhr, sizeof(nhr))) {
  730.     sh_read(infile, buffer, nhr.length);
  731.     if (nhr.tosys != 32767) {
  732.       fprintf(stderr, "\n ■ Non-Internet system routing via @32767... aborting export.");
  733.       return (1);
  734.     }
  735.     if ((nhr.main_type == main_type_post) ||
  736.         (nhr.main_type == main_type_new_post) ||
  737.         (nhr.main_type == main_type_email_name) ||
  738.         (nhr.main_type == main_type_ssm)) {
  739.       inloc = 0;
  740.       if ((nhr.main_type == main_type_email_name) ||
  741.            (nhr.main_type == main_type_ssm)) {
  742.         stype = nhr.minor_type;
  743.         inloc = strlen(buffer) + 1;
  744.         strcpy(mh.toUserName, buffer);
  745.         if (nhr.fromsys != net_sysnum) {
  746.           fprintf(stderr, "\n ■ Gate from #%hd@%hd to %s not yet supported",
  747.                   nhr.fromuser, nhr.fromsys, mh.toUserName);
  748.           continue;
  749.         }
  750.       } else
  751.         if (nhr.main_type == main_type_post)
  752.         stype = nhr.minor_type;
  753.       else {
  754.         stype = atoi(&buffer[inloc]);
  755.         sprintf(_temp_buffer, "%u", stype);
  756.         inloc += strlen(_temp_buffer) + 1;
  757.       }
  758.       strncpy(mh.subject, &buffer[inloc], sizeof(mh.subject));
  759.       stripcolors(mh.subject);
  760.       inloc += strlen(&buffer[inloc]) + 1;
  761.  
  762.       for (term = inloc; buffer[term] != '\r'; term++);
  763.       buffer[term] = '\0';
  764.  
  765.       if ((nhr.fromsys == net_sysnum) && (nhr.fromuser)) {
  766.         if (nhr.main_type != main_type_post) {
  767.           if (!num_to_name(mh.fromUserName, nhr.fromuser, use_alias)) {
  768.             fprintf(stderr, "\n ■ No match for user #%hd... skipping message!",
  769.                     nhr.fromuser);
  770.             continue;
  771.           }
  772.         } else {
  773.           if (!num_to_name(mh.fromUserName, nhr.fromuser, 1)) {
  774.             fprintf(stderr, "\n ■ No match for user #%hd... skipping message!",
  775.                     nhr.fromuser);
  776.             continue;
  777.           }
  778.         }
  779.       } else {
  780.         strncpy(mh.fromUserName, &buffer[inloc], sizeof(mh.fromUserName));
  781.         stripcolors(mh.fromUserName);
  782.         strtok(mh.fromUserName, "#");
  783.         if ((nhr.main_type == main_type_post) &&
  784.             (nhr.fromsys != net_sysnum)) {
  785.           sprintf(_temp_buffer, " #%hd @%hu", nhr.fromuser, nhr.fromsys);
  786.           strcat(mh.fromUserName, _temp_buffer);
  787.         }
  788.       }
  789.  
  790.       inloc = term + 2;
  791.  
  792.       while (buffer[inloc] != '\n')
  793.         inloc++;
  794.       inloc++;
  795.  
  796.       if (strncmp(&buffer[inloc], "0R", 3) == 0) {
  797.         while (buffer[inloc] != '\n')
  798.           ++inloc;
  799.         inloc++;
  800.       }
  801.       if (strnicmp(&buffer[inloc], "RE: ", 4) == 0) {
  802.         for (term = inloc; buffer[term] != '\r'; term++);
  803.         buffer[term] = '\0';
  804.         strncpy(mh.subject, &buffer[inloc], sizeof(mh.subject));
  805.         inloc = term + 2;
  806.       }
  807.       if ((strncmp(&buffer[inloc], "BY: ", 4) == 0) ||
  808.           (strncmp(&buffer[inloc], "TO: ", 4) == 0)) {
  809.         for (term = inloc; buffer[term] != '\r'; term++);
  810.         buffer[term] = '\0';
  811.         strncpy(mh.toUserName, &buffer[inloc + 4], sizeof(mh.toUserName));
  812.         stripcolors(mh.toUserName);
  813.         inloc = term + 2;
  814.       } else {
  815.         if (nhr.main_type != main_type_email_name) {
  816.           strcpy(mh.toUserName, "ALL\n");
  817.         }
  818.       }
  819.  
  820.       outloc = 0;
  821.       do {
  822.         if (buffer[inloc] == 2) {
  823.           i = inloc + 1;
  824.           for (j = 1; j < 80; j++) {
  825.             if ((buffer[i] == '\r') ||
  826.                 (i > nhr.length))
  827.               break;
  828.             i++;
  829.           }
  830.           if (j < 80) {
  831.             i = (80 - j) / 2;
  832.             for (j = 1; j <= i; j++)
  833.               text[outloc++] = ' ';
  834.           }
  835.           inloc++;
  836.         } else
  837.           if (buffer[inloc] == 3)
  838.           inloc += 2;
  839.         else
  840.           if ((buffer[inloc] == 4) && (buffer[inloc + 1] == '0')) {
  841.           i = inloc;
  842.           for (j = 1; j < 80; j++) {
  843.             if ((buffer[i] == '\r') ||
  844.                 (i > nhr.length))
  845.               break;
  846.             i++;
  847.             inloc++;
  848.           }
  849.           inloc++;
  850.           }
  851.         else
  852.           if (buffer[inloc] >= 127) {
  853.           inloc++;
  854.         } else
  855.           if (buffer[inloc] == 1)
  856.           inloc++;
  857.         else
  858.           text[outloc++] = buffer[inloc++];
  859.       } while (inloc < nhr.length);
  860.  
  861.       text[outloc] = '\0';
  862.  
  863.       switch (nhr.main_type) {
  864.         case main_type_email:
  865.         case main_type_email_name:
  866.         case main_type_ssm:
  867.           i = 1;
  868.           sprintf(outfn, "%sMQUEUE\\MSG.%d", net_data, i);
  869.           while (exist(outfn))
  870.             sprintf(outfn, "%sMQUEUE\\MSG.%d", net_data, ++i);
  871.           break;
  872.         case main_type_post:
  873.         case main_type_pre_post:
  874.           i = 1;
  875.           sprintf(outfn, "%sOUTBOUND\\%d.%d", net_data, stype, i);
  876.           while (exist(outfn))
  877.             sprintf(outfn, "%sOUTBOUND\\%d.%d", net_data, stype, ++i);
  878.           break;
  879.         default:
  880.           continue;
  881.       }
  882.  
  883.       fprintf(stderr, "\n ■ Creating: %s", outfn);
  884.       fprintf(stderr, "\n ■ From    : %s", mh.fromUserName);
  885.       if ((nhr.main_type == main_type_post) ||
  886.           (nhr.main_type == main_type_pre_post)) {
  887.         sprintf(fn1, "%sNEWS.RC", net_data);
  888.         fp = fsh_open(fn1, "rt");
  889.         if (!fp)
  890.           fprintf(stderr, "\n ■ %s not found!", fn1);
  891.         else {
  892.           ok = 0;
  893.           while ((fgets(_temp_buffer, 80, fp) != NULL) && (!ok)) {
  894.             groupname[0] = 0;
  895.             ss = strtok(_temp_buffer, " ");
  896.             if (ss) {
  897.               strcpy(groupname, ss);
  898.               ss = strtok(NULL, " ");
  899.               ss = strtok(NULL, "\r");
  900.               ttype = atoi(ss);
  901.               if (ttype == stype)
  902.                 ok = 1;
  903.             }
  904.           }
  905.           *ss = NULL;
  906.           fclose(fp);
  907.         }
  908.       }
  909.       if ((nhr.main_type == main_type_email) ||
  910.           (nhr.main_type == main_type_email_name) ||
  911.           (nhr.main_type == main_type_ssm)) {
  912.         fprintf(stderr, "\n ■ To      : %s", strlwr(mh.toUserName));
  913.       } else {
  914.         if (groupname[0] == 0)
  915.           fprintf(stderr, "\n ■ No match for subtype %u in NEWS.RC", stype);
  916.         else
  917.           fprintf(stderr, "\n ■ Post to : %s", groupname);
  918.       }
  919.  
  920.       fprintf(stderr, "\n ■ Subject : %s", mh.subject);
  921.  
  922.       outfile = sh_open(outfn, O_WRONLY | O_BINARY | O_CREAT | O_TRUNC | O_EXCL, S_IWRITE);
  923.       if (outfile == -1) {
  924.         if (buffer)
  925.           free(buffer);
  926.         if (text)
  927.           free(text);
  928.         fprintf(stderr, "\n ■ Unable to open output file %s", outfn);
  929.         return (1);
  930.       }
  931.       time(&some);
  932.       time_msg = localtime(&some);
  933.       strftime(mh.dateTime, 80, "%a, %d %b %y %H:%M:%S (%Z)", time_msg);
  934.       for (j = 0; j < strlen(mh.fromUserName); j++)
  935.         if (mh.fromUserName[j] == ' ')
  936.           mh.fromUserName[j] = '_';
  937.       if ((spam) && ((nhr.main_type == main_type_post) || (nhr.main_type == main_type_new_post)))
  938.         sprintf(_temp_buffer, "From: nowhere@no.net (%s)\n",
  939.                 mh.fromUserName);
  940.       else
  941.         sprintf(_temp_buffer, "From: %s@%s (%s)\n",
  942.                 POPNAME, DOMAIN, mh.fromUserName);
  943.       sh_write(outfile, _temp_buffer, strlen(_temp_buffer));
  944.       delay(2000);
  945.       sprintf(_temp_buffer, "Message-ID: <%lx-%s@%s>\n",
  946.               time(NULL), POPNAME, DOMAIN);
  947.       sh_write(outfile, _temp_buffer, strlen(_temp_buffer));
  948.       if ((nhr.main_type == main_type_email) ||
  949.           (nhr.main_type == main_type_email_name) ||
  950.           (nhr.main_type == main_type_ssm)) {
  951.         sprintf(_temp_buffer, "To: %s\n",
  952.                 mh.toUserName);
  953.         sh_write(outfile, _temp_buffer, strlen(_temp_buffer));
  954.       } else {
  955.         sprintf(_temp_buffer, "Newsgroups: %s\n", groupname);
  956.         sh_write(outfile, _temp_buffer, strlen(_temp_buffer));
  957.       }
  958.       sprintf(_temp_buffer, "Subject: %s\n", mh.subject);
  959.       sh_write(outfile, _temp_buffer, strlen(_temp_buffer));
  960.       sprintf(_temp_buffer, "Date: %s\n", mh.dateTime);
  961.       sh_write(outfile, _temp_buffer, strlen(_temp_buffer));
  962.       sprintf(_temp_buffer, "Organization: %s * @%hu.%s * %s\n",
  963.               syscfg.systemname, net_sysnum, net_name, syscfg.systemphone);
  964.       sh_write(outfile, _temp_buffer, strlen(_temp_buffer));
  965.       if ((!spam) && ((nhr.main_type != main_type_post) || (nhr.main_type != main_type_new_post))) {
  966.         sprintf(_temp_buffer, "Reply-To: %s@%s (%s)\n",
  967.                 POPNAME, DOMAIN, mh.fromUserName);
  968.         sh_write(outfile, _temp_buffer, strlen(_temp_buffer));
  969.       }
  970.       sprintf(_temp_buffer, "Version: WWIV PPP Project %s\n\n", VERSION);
  971.       sh_write(outfile, _temp_buffer, strlen(_temp_buffer));
  972.  
  973.       if ((spam) && ((nhr.main_type == main_type_post) || (nhr.main_type == main_type_new_post))) {
  974.         sprintf(_temp_buffer, "Reply to: %s@%s (%s)\n\n",
  975.                 POPNAME, DOMAIN, mh.fromUserName);
  976.         sh_write(outfile, _temp_buffer, strlen(_temp_buffer));
  977.       }
  978.       if ((nhr.main_type != main_type_email) &&
  979.           (nhr.main_type != main_type_email_name) &&
  980.           (strncmp(mh.toUserName, "ALL", 3) != 0)) {
  981.         sprintf(_temp_buffer, "Responding to: %s\n", mh.toUserName);
  982.         sh_write(outfile, _temp_buffer, strlen(_temp_buffer));
  983.       }
  984.       sh_write(outfile, text, strlen(text));
  985.  
  986.       sprintf(tagfn, "%sI%u.TAG", syscfg.datadir, stype);
  987.       if (exist(tagfn))
  988.         strcpy(tagfile, tagfn);
  989.       if (tagfile[0] == 0) {
  990.         sprintf(_temp_buffer, "\n\nOrigin: %s * %s * @%hu.FILEnet\n\n",
  991.                 syscfg.systemname, syscfg.systemphone, net_sysnum);
  992.         sh_write(outfile, _temp_buffer, strlen(_temp_buffer));
  993.       } else {
  994.         fp = fsh_open(tagfile, "rt");
  995.         if (!fp)
  996.           fprintf(stderr, "\n ■ Error reading %s.", tagfile);
  997.         else {
  998.           sprintf(_temp_buffer, "\n\n");
  999.           sh_write(outfile, _temp_buffer, strlen(_temp_buffer));
  1000.           while (fgets(_temp_buffer, 120, fp)) {
  1001.             for (i = 0; ((i < strlen(_temp_buffer)) &&
  1002.                (_temp_buffer[i] != '\r') && (_temp_buffer[i] != '\n')); i++)
  1003.               if ((_temp_buffer[i] < 32) || (_temp_buffer[i] > 126))
  1004.                 _temp_buffer[i] = 32;
  1005.             sh_write(outfile, _temp_buffer, strlen(_temp_buffer));
  1006.           }
  1007.           fclose(fp);
  1008.           sprintf(_temp_buffer, "\n\n");
  1009.           sh_write(outfile, _temp_buffer, strlen(_temp_buffer));
  1010.         }
  1011.       }
  1012.       sh_close(outfile);
  1013.     } else {
  1014.       if ((nhr.main_type >= 0x01) && (nhr.main_type <= 0x14))
  1015.         fprintf(stderr, "\n ■ %s message skipped",
  1016.                 main_type[nhr.main_type - 1]);
  1017.       else
  1018.         fprintf(stderr, "\n ■ Unknown Main_type %hd skipped", nhr.main_type);
  1019.     }
  1020.   }
  1021.   sh_close(infile);
  1022.   unlink(fn);
  1023.   if (text)
  1024.     free(text);
  1025.   if (buffer)
  1026.     free(buffer);
  1027.   return (0);
  1028. }
  1029.  
  1030. void get_dir(char *s, int be)
  1031. {
  1032.   strcpy(s, "X:\\");
  1033.   s[0] = 'A' + getdisk();
  1034.   getcurdir(0, s + 3);
  1035.   if (be) {
  1036.     if (s[strlen(s) - 1] != '\\')
  1037.       strcat(s, "\\");
  1038.   }
  1039. }
  1040.  
  1041. int main(int argc, char *argv[])
  1042. {
  1043.   char fn[MAXPATH], *ss;
  1044.   int f, f1, maxmail, i;
  1045.   struct ffblk ff;
  1046.  
  1047.   /* 0      1               2          3          4       5        6       */
  1048.   /* exp s32767.net,      net_data, net_sysnum, popname, domain, net_name  */
  1049.   /* exp netlog/contact,  net_data,   sysnum,     sent    recd   totaltime */
  1050.  
  1051.   fprintf(stderr, "\n ■ PPP Import/Export %s", VERSION);
  1052.   if (argc != 7) {
  1053.     fprintf(stderr, "\n ■ EXP <filename> <net_data> <net_sysnum> <POPNAME> <DOMAIN> <net_name>\n\n");
  1054.     if (argc > 1) {
  1055.       fprintf(stderr, "Command line was: ");
  1056.       for (i = 0; i < argc; i++)
  1057.         fprintf(stderr, "%s ", argv[i]);
  1058.       fprintf(stderr, "\n\n");
  1059.     }
  1060.     return (1);
  1061.   }
  1062.   if (get_nb_version())
  1063.     multitasker = 8;
  1064.   else
  1065.     detect_multitask();
  1066.   switch (multitasker) {
  1067.     case 1:
  1068.       get_dv_version();
  1069.       break;
  1070.     case 2:
  1071.       get_win_version();
  1072.       break;
  1073.     case 3:
  1074.       get_dv_version();
  1075.       break;
  1076.     case 4:
  1077.     case 5:
  1078.     case 6:
  1079.     case 7:
  1080.       break;
  1081.     case 8:
  1082.       multitasker = 1;
  1083.       break;
  1084.     default:
  1085.       break;
  1086.   }
  1087.   get_dir(maindir, 1);
  1088.   strcpy(net_data, argv[2]);
  1089.   sprintf(fn, "%s%s", net_data, argv[1]);
  1090.   net_name = argv[6];
  1091.   strcpy(POPNAME, argv[4]);
  1092.   strcpy(DOMAIN, argv[5]);
  1093.   net_sysnum = atoi(argv[3]);
  1094.   tagfile[0] = 0;
  1095.   spam = 0;
  1096.  
  1097.   f = sh_open1("CONFIG.DAT", O_RDONLY | O_BINARY);
  1098.   if (f < 0) {
  1099.     fprintf(stderr, "Could not open CONFIG.DAT!\n\n");
  1100.     return (1);
  1101.   }
  1102.   sh_read(f, (void *) &syscfg, sizeof(configrec));
  1103.   sh_close(f);
  1104.  
  1105.   ss = getenv("WWIV_INSTANCE");
  1106.   if (ss) {
  1107.     instance = atoi(ss);
  1108.     if (instance >= 1000) {
  1109.       fprintf(stderr, "\n ■ WWIV_INSTANCE set to %hd.  Can only be 1..999!",
  1110.               instance);
  1111.       instance = 1;
  1112.     }
  1113.   } else
  1114.     instance = 1;
  1115.  
  1116.   parse_net_ini();
  1117.  
  1118.   fprintf(stderr, "\n ■ Postmaster default account set to %s #%hd.",
  1119.           strupr(postmaster), defuser);
  1120.   fprintf(stderr, "\n ■ Using user %s on outbound Internet mail.",
  1121.           use_alias ? "aliases" : "real names");
  1122.   if (spam)
  1123.     fprintf(stderr, "\n ■ Using bogus originating address on newsgroup posts.");
  1124.   if (tagfile[0] != 0)
  1125.     fprintf(stderr, "\n ■ Using signature file : %s", tagfile);
  1126.  
  1127.   export(fn);
  1128.  
  1129.   sprintf(fn, "%sSPOOL\\UNK*.*", net_data);
  1130.   f1 = findfirst(fn, &ff, 0);
  1131.   maxmail = 14;
  1132.   while ((f1 == 0) && maxmail) {
  1133.     sprintf(fn, "%sSPOOL\\%s", net_data, ff.ff_name);
  1134.     if (!import(fn)) {
  1135.       unlink(fn);
  1136.       --maxmail;
  1137.     }
  1138.     f1 = findnext(&ff);
  1139.   }
  1140.   return 0;
  1141. }
  1142.