home *** CD-ROM | disk | FTP | other *** search
/ Usenet 1994 January / usenetsourcesnewsgroupsinfomagicjanuary1994.iso / sources / unix / volume13 / vn.jan.88 / part03 / svart.c < prev    next >
Encoding:
C/C++ Source or Header  |  1988-01-30  |  4.1 KB  |  237 lines

  1. /*
  2. ** vn news reader.
  3. **
  4. ** svart.c - article save routine
  5. **
  6. ** see copyright disclaimer / history in vn.c source file
  7. */
  8. #include <stdio.h>
  9. #include <pwd.h>
  10. #include <sys/types.h>
  11. #include <sys/stat.h>
  12. #include "config.h"
  13. #include "tty.h"
  14. #include "tune.h"
  15. #include "node.h"
  16. #include "page.h"
  17.  
  18. extern PAGE Page;
  19. extern int Digest;
  20. extern char *List_sep;
  21. extern char *Home;
  22. extern char *Savedir;
  23.  
  24. /*
  25. ** save article in file.  Called from reader and session both.
  26. ** handles "|" pipe convention.  Caller passes in return message buffer.
  27. */
  28. save_art(art,idest,msg)
  29. char *art;
  30. char *idest;
  31. char *msg;
  32. {
  33.     char fn[L_tmpnam+1];
  34.     char cmd[RECLEN];
  35.     char *mode;
  36.     char *dest, dstore[RECLEN];
  37.     struct stat sbuf;
  38.     int rstat;
  39.     char *colon;
  40.     char *pcnt;
  41.     char *index();
  42.  
  43.     /* temporary copy so we don't overwrite saved string */
  44.     strcpy((dest = dstore),idest);
  45.  
  46.     if (*dest == '|')
  47.     {
  48.         tmpnam(fn);
  49.         if (art_xfer(fn,art,"w") != 0)
  50.         {
  51.             strcpy(msg,"Can't open temporary file");
  52.             return (-1);
  53.         }
  54.         sprintf(cmd,"cat %s %s",fn,dest);
  55.         tty_set (SAVEMODE);
  56.         rstat = system (cmd);
  57.         tty_set (RESTORE);
  58.         sprintf(msg,"Command returns %d",rstat);
  59.         return (rstat);
  60.     }
  61.  
  62.     if ((colon = index(dest,':')) != NULL)
  63.     {
  64.         mode = dest;
  65.         *colon = '\0';
  66.         dest = colon+1;
  67.     }
  68.     else
  69.         mode = "a";
  70.  
  71.     if (*dest == '~')
  72.     {
  73.         if (twiddle(dest,msg) < 0)
  74.             return (-1);
  75.     }
  76.  
  77.     if (*dest == '\0')
  78.         strcpy(dest,"%d");
  79.  
  80.     if (*dest != '/')
  81.     {
  82.         if (noslash(dest,msg) < 0)
  83.             return (-1);
  84.     }
  85.  
  86.     if ((pcnt = index(dest,'%')) != NULL && pcnt[1] == 'd')
  87.     {
  88.         if (Digest)
  89.             sprintf(cmd,dest,Digest);
  90.         else
  91.             sprintf(cmd,dest,atoi(art));
  92.         dest = cmd;
  93.     }
  94.  
  95.     rstat = stat(dest,&sbuf);
  96.  
  97.     if (art_xfer(dest,art,mode) != 0)
  98.     {
  99.         sprintf(msg,"Can't open %s with mode %s",dest,mode);
  100.         return(-1);
  101.     }
  102.  
  103.     if (rstat != 0)
  104.     {
  105.         sprintf(msg,"Created %s",dest);
  106.         return(0);
  107.     }
  108.  
  109.     if (strcmp(mode,"a") == 0)
  110.     {
  111.         sprintf(msg,"Appended %s",dest);
  112.         return(0);
  113.     }
  114.  
  115.     sprintf(msg,"Wrote (mode %s) %s",mode,dest);
  116.     return(0);
  117. }
  118.  
  119. static
  120. noslash(dest,msg)
  121. char *dest;
  122. char *msg;
  123. {
  124.     char *pcnt;
  125.     char buf[RECLEN];
  126.     char dir[RECLEN];
  127.     struct stat sbuf;
  128.  
  129.     strcpy(buf,Page.h.name);
  130. #ifdef SYSV
  131.     buf[14] = '\0';
  132. #endif
  133.     if ((pcnt = index(Savedir,'%')) != NULL && pcnt[1] == 's')
  134.         sprintf(dir,Savedir,buf);
  135.     else
  136.         strcpy(dir,Savedir);
  137.     if (dir[0] == '~')
  138.     {
  139.         if (twiddle(dir,msg) < 0)
  140.             return (-1);
  141.     }
  142.     if (stat(dir,&sbuf) != 0)
  143.     {
  144. #ifdef SYSV
  145.         /*
  146.         ** late enough releases of SYSV may have a mkdir() call, but
  147.         ** this is an obscure feature anyway.  We'll accept the fork.
  148.         */
  149.         sprintf(buf,"mkdir %s",dir);
  150.         if (system(buf) != 0)
  151. #else
  152.         if (mkdir(dir,0755) != 0)
  153. #endif
  154.         {
  155.             sprintf(msg,"Cannot make directory %s",dir);
  156.             return (-1);
  157.         }
  158.     }
  159.     sprintf(buf,"%s/%s",dir,dest);
  160.     strcpy(dest,buf);
  161.     return (0);
  162. }
  163.  
  164. static
  165. twiddle(dest,msg)
  166. char *dest, *msg;
  167. {
  168.     char *tail;
  169.     char *name;
  170.     char tmp;
  171.     char buf[RECLEN];
  172.     struct passwd *ptr, *getpwnam();
  173.  
  174.     for (tail=name=dest+1; *tail != '/' && *tail != '\0'; ++tail)
  175.         ;
  176.  
  177.     if (*name == '\0' || *name == '/')
  178.         sprintf(buf,"%s%s",Home,tail);
  179.     else
  180.     {
  181.         tmp = *tail;
  182.         *tail = '\0';
  183.         ptr = getpwnam(name);
  184.         *tail = tmp;
  185.         if (ptr == NULL)
  186.         {
  187.             sprintf(msg,"Can't interpret ~%s",name);
  188.             return(-1);
  189.         }
  190.         sprintf(buf,"%s%s",ptr->pw_dir,tail);
  191.     }
  192.  
  193.     strcpy(dest,buf);
  194.     return (0);
  195. }
  196.  
  197. /*
  198. ** transfer contents of a list of articles to a file.  If Digest, this
  199. ** is simply a list of files.  If not, it is a list of articles to be
  200. ** saved with vns_asave.  Parses list destructively with
  201. ** strtok().  Return 0 for success, -1 for failure to open file.
  202. **
  203. ** Called directly to copy a list of articles to a temp. file to
  204. ** direct to printer.
  205. */
  206. art_xfer(fn,list,mode)
  207. char *fn, *list, *mode;
  208. {
  209.     char *p;
  210.     FILE *fout, *fin;
  211.     int count;
  212.     char buf[RECLEN];
  213.     char *strtok();
  214.  
  215.     if ((fout = fopen(fn,mode)) == NULL)
  216.         return (-1);
  217.  
  218.     count = 0;
  219.     for (p = strtok(list,List_sep); p != NULL; p = strtok(NULL,List_sep))
  220.     {
  221.         if (Digest)
  222.         {
  223.             fin = fopen(p,"r");
  224.             if (fin == NULL)
  225.                 continue;
  226.             while (fgets(buf,RECLEN-1,fin) != NULL)
  227.                 fputs(buf,fout);
  228.             fclose(fin);
  229.             continue;
  230.         }
  231.         vns_asave(atoi(p),fout,count,fn,mode);
  232.         ++count;
  233.     }
  234.     fclose(fout);
  235.     return(0);
  236. }
  237.