1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19 20 21 22 23 24 25 26 27 28 29 30 31 32 33 34 35 36 37 38 39 40 41 42 43 44 45 46 47 48 49 50 51 52 53 54 55 56 57 58 59 60 61 62 63 64 65 66 67 68 69 70 71 72 73 74 75 76 77 78 79 80 81 82 83 84 85 86 87 88 89 90 91 92 93 94 95 96 97 98 99 100 101 102 103 104 105 106 107 108 109 110 111 112 113 114 115 116 117 118 119 120 121 122 123 124 125 126 127 128 129 130 131 132 133 134 135 136 137 138 139 140 141 142 143 144 145 146 147 148 149 150 151 152 153 154 155 156 157 158 159 160 161 162 163 164 165 166 167 168 169 170 171 172 173 174 175 176 177 178 179 180 181 182 183 184
|
#ifndef lint
static char SccsId[] = "%W% %G%";
#endif
/* Module: ctrlmbox.c (ControlMailbox)
* Purpose: Handle a VMS mailbox for IO
* Subroutine: open_mailbox() returns: int
* Subroutine: close_mailbox() returns: void
* Subroutine: flush_mailbox() returns: void
* Copyright: 1989, 1990 Smithsonian Astrophysical Observatory
* You may do anything you like with this file except remove
* this copyright. The Smithsonian Astrophysical Observatory
* makes no representations about the suitability of this
* software for any purpose. It is provided "as is" without
* express or implied warranty.
* Modified: {0} Jay Travisano (STScI) initial version 10 Nov 1989
* {1} MVH simplified for new connect module 10 March 1990
* {n} <who> -- <does what> -- <when>
*/
#ifdef VMS
/*
* VMS -- Use VMS/IRAF Imtool driver (ZFIOVI)
*/
#include <stdio.h> /* define stderr, FILE, NULL, etc */
#include <sys/file.h> /* define open */
#include <X11/Xlib.h> /* X window stuff */
#include "hfiles/control.h" /* declare control structure types */
#define READ_ONLY 1 /* IRAF SPP definitions */
#define READ_WRITE 2
#define WRITE_ONLY 3
/*
* Subroutine: open_mailbox
* Purpose: Open a VMS mailbox I/O
* Returns: Channel number on success else -1.
*/
int open_mailbox ( device_name, direction, flush_flag )
char *device_name; /* i: name of mailbox device */
int direction; /* i: IOP_Write, IOP_Read, IOP_ReadWrite */
int flush_flag; /* i: 1=flush, 0=don't flush */
{
int ipc; /* o: channel of new pipe connection */
int mode;
if( direction == IOP_Write )
mode = WRITE_ONLY;
else if( direction == IOP_Read )
mode = READ_ONLY;
else if( direction == IOP_ReadWrite )
mode = READ_WRITE;
else
return( -1 );
zopnvi(device_name, &mode, &ipc);
if( ipc == -1 ) {
(void)fprintf(stderr,"Warning: cannot open %s\n", device_name);
return( -1 );
}
#ifdef VMS_FLUSH_INPUT
/* Don't think we want to do this. Mailboxes are pretty well-behaved,
* and we should be able to pick up pending input if we are (re)started
* after IRAF has sent data.
*/
if( flush_flag && (mode != WRITE_ONLY) )
/* if reading, flush old input, if any */
flush_mailbox(ipc, 0, device_name);
#endif
return( ipc );
}
/*
* Subroutine: close_mailbox
* Purpose: Close a mailbox connection
* Returns: 0 on success else -1.
*/
int close_mailbox ( ipc, device_name )
int ipc; /* i: mailbox channel number */
char *device_name; /* i: name of mailbox device */
{
int chan, status;
chan = ipc;
zclsvi(&chan, &status);
if( status == -1 ) {
(void)fprintf(stderr,"Warning: cannot close mailbox %s\n", device_name);
return( -1 );
} else {
return( 0 );
}
}
/*
* Subroutine: flush_mailbox
* Purpose: Suck all bytes out of a pipe open for reading
*/
void flush_mailbox ( ipc, device_name )
int ipc; /* i: mailbox channel number */
char *device_name; /* [i]: name of mailbox device */
{
int bytes, total;
char buf[8192];
int read_mailbox();
total = 0;
while( ZPending(ipc) ) {
bytes = read_mailbox(ipc, buf, sizeof(buf), 0, device_name, "junk");
total += bytes;
}
#ifdef DEBUG
if( total > 0 )
(void)fprintf(stderr, "Flushed %d bytes from pipe\n", total);
#endif
}
/*
* Subroutine: read_mailbox
* Purpose: Read VMS mailbox
* Returns: Byte count, 0 on EOF, -1 on error
*/
int read_mailbox ( ipc, buf, bytes, report_error, device_name, detail )
int ipc; /* i: mailbox channel number */
char *buf; /* i: address of buffer to receive data */
int bytes; /* i: maximum number of bytes to read */
int report_error; /* i: report under-count read */
char *device_name; /* [i]: name of mailbox device */
char *detail; /* [i]: details of operation */
{
int chan = ipc;
int maxbytes = bytes;
int offset = 0;
int status;
zardvi(&chan, buf, &maxbytes, &offset);
zawtvi(&chan, &status);
if( report_error ) {
if( status <= 0 ) {
(void)fprintf(stderr, "Error in reading");
if( detail != NULL )
(void)fprintf(stderr, " %s", detail);
if( device_name != NULL )
(void)fprintf(stderr, " from %s", device_name);
(void)fprintf(stderr, "\n");
(void)fflush(stderr);
} else {
if (status < maxbytes) {
(void)fprintf(stderr, "Expected %d bytes, read %d\n",
maxbytes, status);
(void)fflush(stderr);
}
}
}
return( status );
}
/*
* Subroutine: write_mailbox
* Purpose: Write to VMS mailbox
* Returns: Byte count, 0 on EOF, -1 on error
*/
int write_mailbox ( ipc, buf, bytes, device_name )
int ipc; /* i: mailbox channel number */
char *buf; /* i: address of buffer to write */
int bytes; /* i: number of bytes to write */
char *device_name; /* i: name of mailbox device */
{
int chan = ipc;
int nbytes = bytes;
int offset = 0;
int status;
zawrvi(&chan, buf, &nbytes, &offset);
zawtvi(&chan, &status);
if( status < bytes )
(void)fprintf(stderr, "Write error on %s; wrote %d of %d bytes\n",
device_name, status, bytes);
return( status );
}
#endif
|