home *** CD-ROM | disk | FTP | other *** search
/ GEMini Atari / GEMini_Atari_CD-ROM_Walnut_Creek_December_1993.iso / zip / gnu / gawk213s.lzh / GAWK213S / VMS_POPE.C < prev    next >
C/C++ Source or Header  |  1993-07-29  |  4KB  |  169 lines

  1. /*
  2.  * [.vms]vms_popen.c -- substitute routines for missing pipe calls.
  3.  */
  4.  
  5. /*
  6.  * Copyright (C) 1991 the Free Software Foundation, Inc.
  7.  *
  8.  * This file is part of GAWK, the GNU implementation of the
  9.  * AWK Progamming Language.
  10.  *
  11.  * GAWK is free software; you can redistribute it and/or modify
  12.  * it under the terms of the GNU General Public License as published by
  13.  * the Free Software Foundation; either version 1, or (at your option)
  14.  * any later version.
  15.  *
  16.  * GAWK is distributed in the hope that it will be useful,
  17.  * but WITHOUT ANY WARRANTY; without even the implied warranty of
  18.  * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
  19.  * GNU General Public License for more details.
  20.  *
  21.  * You should have received a copy of the GNU General Public License
  22.  * along with GAWK; see the file COPYING.  If not, write to
  23.  * the Free Software Foundation, 675 Mass Ave, Cambridge, MA 02139, USA.
  24.  */
  25.  
  26. #ifndef NO_VMS_PIPES
  27.  
  28. #include "awk.h"    /* really "../awk.h" */
  29. #include <stdio.h>
  30.  
  31. #ifndef PIPES_SIMULATED
  32.  
  33. FILE *
  34. popen( const char *command, const char *mode )
  35. {
  36.     fatal(" Cannot open pipe `%s' (not implemented)", command);
  37.     /* NOT REACHED */
  38.     return 0;
  39. }
  40.  
  41. int
  42. pclose( FILE *current )
  43. {
  44.     fatal(" Internal error ('pclose' not implemented)");
  45.     /* NOT REACHED */
  46.     return -1;
  47. }
  48.  
  49. int
  50. fork()
  51. {
  52.     fatal(" Internal error ('fork' not implemented)");
  53.     /* NOT REACHED */
  54.     return -1;
  55. }
  56.  
  57. #else    PIPES_SIMULATED
  58.     /*
  59.      * Simulate pipes using temporary files; hope that the user
  60.      * doesn't expect pipe i/o to be interleaved with other i/o ;-}.
  61.      *
  62.      * This is essentially the same as the MSDOS version.  The
  63.      * difference is that redirection is handled using LIB$SPAWN
  64.      * rather than constructing a command for system() which uses
  65.      * '<' or '>'.
  66.      */
  67. #include "vms.h"
  68. #include <errno.h>
  69.  
  70. typedef enum { unopened = 0, reading, writing } pipemode;
  71. static
  72. struct {
  73.     char *command;
  74.     char *name;
  75.     pipemode pmode;
  76. } pipes[_NFILE];
  77.  
  78. FILE *
  79. popen( const char *command, const char *mode )
  80. {
  81.     FILE *current;
  82.     char *name, *mktemp();
  83.     int   cur, strcmp();
  84.     pipemode curmode;
  85.  
  86.     if (strcmp(mode, "r") == 0)
  87.     curmode = reading;
  88.     else if (strcmp(mode, "w") == 0)
  89.     curmode = writing;
  90.     else
  91.     return NULL;
  92.  
  93.     /* make a name for the temporary file */
  94.     if ((name = mktemp(strdup("sys$scratch:pipe_XXXX.tmp"))) == 0)
  95.     return NULL;
  96.  
  97.     if (curmode == reading) {
  98.     /* an input pipe reads a temporary file created by the command */
  99.     vms_execute(command, (char *)0, name);    /* 'command >tempfile' */
  100.     }
  101.     if ((current = fopen(name, mode)) == NULL) {
  102.     free(name);
  103.     return NULL;
  104.     }
  105.     cur = fileno(current);
  106.     pipes[cur].name = name;
  107.     pipes[cur].pmode = curmode;
  108.     pipes[cur].command = strdup(command);
  109.     return current;
  110. }
  111.  
  112. int
  113. pclose( FILE *current )
  114. {
  115.     int rval, cur = fileno(current);
  116.  
  117.     if (pipes[cur].pmode == unopened)
  118.     return -1;    /* should never happen */
  119.  
  120.     rval = fclose(current);    /* close temp file; if reading, we're done */
  121.     if (pipes[cur].pmode == writing) {
  122.     /* an output pipe feeds the temporary file to the other program */
  123.     rval = vms_execute(pipes[cur].command, pipes[cur].name, (char *)0);
  124.     }
  125.     /* clean up */
  126.     unlink(pipes[cur].name);    /* get rid of the temporary file */
  127.     pipes[cur].pmode = unopened;
  128.     free(pipes[cur].name),  pipes[cur].name = 0;
  129.     free(pipes[cur].command),  pipes[cur].command = 0;
  130.     return rval;
  131. }
  132.  
  133.     /*
  134.      * Create a process and execute a command in it.  This is essentially
  135.      * the same as system() but allows us to specify SYS$INPUT (stdin)
  136.      * and/or SYS$OUTPUT (stdout) for the process.
  137.      * [With more work it could truly simulate a pipe using mailboxes.]
  138.      */
  139. int
  140. vms_execute( const char *command, const char *input, const char *output )
  141. {
  142.     Dsc cmd, in, out, *in_p, *out_p;
  143.     u_long sts, cmpltn_sts, LIB$SPAWN();
  144.  
  145.     cmd.len = strlen(cmd.adr = (char *)command);
  146.     if (input)
  147.     in.len = strlen(in.adr = (char *)input),  in_p = ∈
  148.     else
  149.     in_p = 0;
  150.     if (output)
  151.     out.len = strlen(out.adr = (char *)output),  out_p = &out;
  152.     else
  153.     out_p = 0;
  154.  
  155.     sts = LIB$SPAWN(&cmd, in_p, out_p, (long *)0,
  156.             (Dsc *)0, (u_long *)0, &cmpltn_sts);
  157.  
  158.     if (vmswork(sts) && vmsfail(cmpltn_sts))  sts = cmpltn_sts;
  159.     if (vmsfail(sts)) {
  160.     errno = EVMSERR,  vaxc$errno = sts;
  161.     return -1;
  162.     } else
  163.     return 0;
  164. }
  165.  
  166. #endif    /* PIPES_SIMULATED */
  167.  
  168. #endif    /*!NO_VMS_PIPES*/
  169.