1 /* Interfaces to system-dependent kernel and library entries.
2 Copyright (C) 1985, 1986, 1987, 1988, 1993, 1994, 1995, 1999, 2000, 2001,
3 2002, 2003, 2004, 2005, 2006, 2007, 2008
4 Free Software Foundation, Inc.
6 This file is part of GNU Emacs.
8 GNU Emacs is free software; you can redistribute it and/or modify
9 it under the terms of the GNU General Public License as published by
10 the Free Software Foundation; either version 3, or (at your option)
13 GNU Emacs is distributed in the hope that it will be useful,
14 but WITHOUT ANY WARRANTY; without even the implied warranty of
15 MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
16 GNU General Public License for more details.
18 You should have received a copy of the GNU General Public License
19 along with GNU Emacs; see the file COPYING. If not, write to
20 the Free Software Foundation, Inc., 51 Franklin Street, Fifth Floor,
21 Boston, MA 02110-1301, USA. */
34 /* Including stdlib.h isn't necessarily enough to get srandom
35 declared, e.g. without __USE_XOPEN_EXTENDED with glibc 2. */
37 #if 0 /* Don't prototype srandom; it takes an unsigned argument on
38 some systems, and an unsigned long on others, like FreeBSD
40 extern void srandom
P_ ((unsigned int));
44 /* The w32 build defines select stuff in w32.h, which is included by
45 sys/select.h (included below). */
47 #include "sysselect.h"
50 #include "blockinput.h"
54 #define write sys_write
59 #endif /* not WINDOWSNT */
61 /* Does anyone other than VMS need this? */
63 #define sys_fwrite fwrite
68 #include <sys/types.h>
73 #if !defined (USG) || defined (BSD_PGRPS)
75 #define setpgrp setpgid
79 /* Get SI_SRPC_DOMAIN, if it is available. */
80 #ifdef HAVE_SYS_SYSTEMINFO_H
81 #include <sys/systeminfo.h>
84 #ifdef MSDOS /* Demacs 1.1.2 91/10/20 Manabu Higashida, MW Aug 1993 */
88 #include <sys/param.h>
92 extern unsigned start
__asm__ ("start");
114 #include <sys/file.h>
122 #define MAXIOSIZE (32 * PAGESIZE) /* Don't I/O more than 32 blocks at a time */
126 #include <sys/file.h>
134 #include <sys/ioctl.h>
140 #ifdef BROKEN_TIOCGWINSZ
146 #include <sys/utsname.h>
147 #ifndef MEMORY_IN_STRING_H
150 #if defined (TIOCGWINSZ)
152 #include <sys/sioctl.h>
155 #include <sys/stream.h>
156 #include <sys/ptem.h>
158 #endif /* TIOCGWINSZ */
161 extern int quit_char
;
163 #include "keyboard.h"
166 #include "termhooks.h"
167 #include "termchar.h"
168 #include "termopts.h"
169 #include "dispextern.h"
171 #include "cm.h" /* for reset_sys_modes */
175 /* In process.h which conflicts with the local copy. */
177 int _CRTAPI1
_spawnlp (int, const char *, const char *, ...);
178 int _CRTAPI1
_getpid (void);
179 extern char *getwd (char *);
182 #ifdef NONSYSTEM_DIR_LIBRARY
184 #endif /* NONSYSTEM_DIR_LIBRARY */
186 #include "syssignal.h"
193 #ifndef HAVE_STRUCT_UTIMBUF
194 /* We want to use utime rather than utimes, but we couldn't find the
195 structure declaration. We'll use the traditional one. */
203 /* LPASS8 is new in 4.3, and makes cbreak mode provide all 8 bits. */
209 #define LNOFLSH 0100000
212 static int baud_convert
[] =
217 0, 50, 75, 110, 135, 150, 200, 300, 600, 1200,
218 1800, 2400, 4800, 9600, 19200, 38400
225 #if defined (HAVE_LIBNCURSES) && ! defined (NCURSES_OSPEED_T)
227 #if defined (HAVE_TERMIOS_H) && defined (GNU_LINUX)
235 void croak
P_ ((char *)) NO_RETURN
;
238 void hft_init
P_ ((struct tty_display_info
*));
239 void hft_reset
P_ ((struct tty_display_info
*));
242 /* Temporary used by `sigblock' when defined in terms of signprocmask. */
244 SIGMASKTYPE sigprocmask_set
;
247 #if !defined (HAVE_GET_CURRENT_DIR_NAME) || defined (BROKEN_GET_CURRENT_DIR_NAME)
249 /* Return the current working directory. Returns NULL on errors.
250 Any other returned value must be freed with free. This is used
251 only when get_current_dir_name is not defined on the system. */
253 get_current_dir_name ()
257 struct stat dotstat
, pwdstat
;
258 /* If PWD is accurate, use it instead of calling getwd. PWD is
259 sometimes a nicer name, and using it may avoid a fatal error if a
260 parent directory is searchable but not readable. */
261 if ((pwd
= getenv ("PWD")) != 0
262 && (IS_DIRECTORY_SEP (*pwd
) || (*pwd
&& IS_DEVICE_SEP (pwd
[1])))
263 && stat (pwd
, &pwdstat
) == 0
264 && stat (".", &dotstat
) == 0
265 && dotstat
.st_ino
== pwdstat
.st_ino
266 && dotstat
.st_dev
== pwdstat
.st_dev
268 && strlen (pwd
) < MAXPATHLEN
272 buf
= (char *) malloc (strlen (pwd
) + 1);
280 size_t buf_size
= 1024;
281 buf
= (char *) malloc (buf_size
);
286 if (getcwd (buf
, buf_size
) == buf
)
290 int tmp_errno
= errno
;
296 buf
= (char *) realloc (buf
, buf_size
);
304 /* We need MAXPATHLEN here. */
305 buf
= (char *) malloc (MAXPATHLEN
+ 1);
308 if (getwd (buf
) == NULL
)
310 int tmp_errno
= errno
;
322 /* Discard pending input on all input descriptors. */
328 struct emacs_tty buf
;
335 SYS$
QIOW (0, fileno (CURTTY()->input
), IO$_READVBLK
|IO$M_PURGE
, input_iosb
, 0, 0,
336 &buf
.main
, 0, 0, terminator_mask
, 0, 0);
339 #ifdef MSDOS /* Demacs 1.1.1 91/10/16 HIRANO Satoshi */
340 while (dos_keyread () != -1)
342 #else /* not MSDOS */
344 struct tty_display_info
*tty
;
345 for (tty
= tty_list
; tty
; tty
= tty
->next
)
347 if (tty
->input
) /* Is the device suspended? */
349 EMACS_GET_TTY (fileno (tty
->input
), &buf
);
350 EMACS_SET_TTY (fileno (tty
->input
), &buf
, 0);
354 #endif /* not MSDOS */
356 #endif /* not WINDOWSNT */
362 /* Arrange for character C to be read as the next input from
364 XXX What if we have multiple ttys?
370 if (! FRAME_TERMCAP_P (SELECTED_FRAME ()))
373 /* Should perhaps error if in batch mode */
375 ioctl (fileno (CURTTY()->input
), TIOCSTI
, &c
);
376 #else /* no TIOCSTI */
377 error ("Cannot stuff terminal input characters in this version of Unix");
378 #endif /* no TIOCSTI */
384 init_baud_rate (int fd
)
390 #ifdef INIT_BAUD_RATE
395 #else /* not DOS_NT */
399 SYS$
QIOW (0, fd
, IO$_SENSEMODE
, &sg
, 0, 0,
400 &sg
.class, 12, 0, 0, 0, 0 );
401 emacs_ospeed
= sg
.xmit_baud
;
408 emacs_ospeed
= cfgetospeed (&sg
);
409 #if defined (USE_GETOBAUD) && defined (getobaud)
410 /* m88k-motorola-sysv3 needs this (ghazi@noc.rutgers.edu) 9/1/94. */
411 if (emacs_ospeed
== 0)
412 emacs_ospeed
= getobaud (sg
.c_cflag
);
414 #else /* neither VMS nor TERMIOS */
422 ioctl (fd
, TCGETA
, &sg
);
424 emacs_ospeed
= sg
.c_cflag
& CBAUD
;
425 #else /* neither VMS nor TERMIOS nor TERMIO */
428 sg
.sg_ospeed
= B9600
;
429 if (ioctl (fd
, TIOCGETP
, &sg
) < 0)
431 emacs_ospeed
= sg
.sg_ospeed
;
432 #endif /* not HAVE_TERMIO */
433 #endif /* not HAVE_TERMIOS */
435 #endif /* not DOS_NT */
436 #endif /* not INIT_BAUD_RATE */
439 baud_rate
= (emacs_ospeed
< sizeof baud_convert
/ sizeof baud_convert
[0]
440 ? baud_convert
[emacs_ospeed
] : 9600);
448 set_exclusive_use (fd
)
452 ioctl (fd
, FIOCLEX
, 0);
454 /* Ok to do nothing if this feature does not exist */
459 wait_without_blocking ()
462 wait3 (0, WNOHANG
| WUNTRACED
, 0);
464 croak ("wait_without_blocking");
466 synch_process_alive
= 0;
469 #endif /* not subprocesses */
471 int wait_debugging
; /* Set nonzero to make following function work under dbx
472 (at least for bsd). */
475 wait_for_termination_signal ()
478 /* Wait for subprocess with process id `pid' to terminate and
479 make sure it will get eliminated (not remain forever as a zombie) */
482 wait_for_termination (pid
)
491 status
= SYS$
FORCEX (&pid
, 0, 0);
494 #if defined (BSD_SYSTEM) || (defined (HPUX) && !defined (HPUX_5))
495 /* Note that kill returns -1 even if the process is just a zombie now.
496 But inevitably a SIGCHLD interrupt should be generated
497 and child_sig will do wait3 and make the process go away. */
498 /* There is some indication that there is a bug involved with
499 termination of subprocesses, perhaps involving a kernel bug too,
500 but no idea what it is. Just as a hunch we signal SIGCHLD to see
501 if that causes the problem to go away or get worse. */
502 sigsetmask (sigmask (SIGCHLD
));
503 if (0 > kill (pid
, 0))
505 sigsetmask (SIGEMPTYMASK
);
506 kill (getpid (), SIGCHLD
);
512 sigpause (SIGEMPTYMASK
);
513 #else /* not BSD_SYSTEM, and not HPUX version >= 6 */
514 #ifdef POSIX_SIGNALS /* would this work for GNU/Linux as well? */
515 sigblock (sigmask (SIGCHLD
));
517 if (kill (pid
, 0) == -1 && errno
== ESRCH
)
519 sigunblock (sigmask (SIGCHLD
));
523 sigsuspend (&empty_mask
);
524 #else /* not POSIX_SIGNALS */
525 #ifdef HAVE_SYSV_SIGPAUSE
527 if (0 > kill (pid
, 0))
533 #else /* not HAVE_SYSV_SIGPAUSE */
537 #else /* not WINDOWSNT */
538 if (0 > kill (pid
, 0))
540 /* Using sleep instead of pause avoids timing error.
541 If the inferior dies just before the sleep,
542 we lose just one second. */
544 #endif /* not WINDOWSNT */
545 #endif /* not HAVE_SYSV_SIGPAUSE */
546 #endif /* not POSIX_SIGNALS */
547 #endif /* not BSD_SYSTEM, and not HPUX version >= 6 */
549 #else /* not subprocesses */
552 #else /* not __DJGPP__ > 1 */
554 if (kill (pid
, 0) < 0)
560 if (status
== pid
|| status
== -1)
563 #endif /* not __DJGPP__ > 1*/
564 #endif /* not subprocesses */
571 * flush any pending output
572 * (may flush input as well; it does not matter the way we use it)
576 flush_pending_output (channel
)
580 /* If we try this, we get hit with SIGTTIN, because
581 the child's tty belongs to the child's pgrp. */
584 ioctl (channel
, TCFLSH
, 1);
588 /* 3rd arg should be ignored
589 but some 4.2 kernels actually want the address of an int
590 and nonzero means something different. */
591 ioctl (channel
, TIOCFLUSH
, &zero
);
598 /* Set up the terminal at the other end of a pseudo-terminal that
599 we will be controlling an inferior through.
600 It should not echo or do line-editing, since that is done
601 in Emacs. No padding needed for insertion into an Emacs buffer. */
604 child_setup_tty (out
)
610 EMACS_GET_TTY (out
, &s
);
612 #if defined (HAVE_TERMIO) || defined (HAVE_TERMIOS)
613 s
.main
.c_oflag
|= OPOST
; /* Enable output postprocessing */
614 s
.main
.c_oflag
&= ~ONLCR
; /* Disable map of NL to CR-NL on output */
616 s
.main
.c_oflag
&= ~(NLDLY
|CRDLY
|TABDLY
|BSDLY
|VTDLY
|FFDLY
);
617 /* No output delays */
619 s
.main
.c_lflag
&= ~ECHO
; /* Disable echo */
620 s
.main
.c_lflag
|= ISIG
; /* Enable signals */
621 #if 0 /* This causes bugs in (for instance) telnet to certain sites. */
622 s
.main
.c_iflag
&= ~ICRNL
; /* Disable map of CR to NL on input */
623 #ifdef INLCR /* Just being cautious, since I can't check how
624 widespread INLCR is--rms. */
625 s
.main
.c_iflag
&= ~INLCR
; /* Disable map of NL to CR on input */
629 s
.main
.c_iflag
&= ~IUCLC
; /* Disable downcasing on input. */
632 s
.main
.c_iflag
&= ~ISTRIP
; /* don't strip 8th bit on input */
635 s
.main
.c_oflag
&= ~OLCUC
; /* Disable upcasing on output. */
637 s
.main
.c_oflag
&= ~TAB3
; /* Disable tab expansion */
638 s
.main
.c_cflag
= (s
.main
.c_cflag
& ~CSIZE
) | CS8
; /* Don't strip 8th bit */
640 /* Said to be unnecessary: */
641 s
.main
.c_cc
[VMIN
] = 1; /* minimum number of characters to accept */
642 s
.main
.c_cc
[VTIME
] = 0; /* wait forever for at least 1 character */
645 s
.main
.c_lflag
|= ICANON
; /* Enable erase/kill and eof processing */
646 s
.main
.c_cc
[VEOF
] = 04; /* insure that EOF is Control-D */
647 s
.main
.c_cc
[VERASE
] = CDISABLE
; /* disable erase processing */
648 s
.main
.c_cc
[VKILL
] = CDISABLE
; /* disable kill processing */
651 s
.main
.c_cflag
= (s
.main
.c_cflag
& ~CBAUD
) | B9600
; /* baud rate sanity */
654 #ifdef SIGNALS_VIA_CHARACTERS
655 /* the QUIT and INTR character are used in process_send_signal
656 so set them here to something useful. */
657 if (s
.main
.c_cc
[VQUIT
] == CDISABLE
)
658 s
.main
.c_cc
[VQUIT
] = '\\'&037; /* Control-\ */
659 if (s
.main
.c_cc
[VINTR
] == CDISABLE
)
660 s
.main
.c_cc
[VINTR
] = 'C'&037; /* Control-C */
661 #endif /* not SIGNALS_VIA_CHARACTERS */
664 /* AIX enhanced edit loses NULs, so disable it */
667 s
.main
.c_iflag
&= ~ASCEDIT
;
669 /* Also, PTY overloads NUL and BREAK.
670 don't ignore break, but don't signal either, so it looks like NUL. */
671 s
.main
.c_iflag
&= ~IGNBRK
;
672 s
.main
.c_iflag
&= ~BRKINT
;
673 /* rms: Formerly it set s.main.c_cc[VINTR] to 0377 here
674 unconditionally. Then a SIGNALS_VIA_CHARACTERS conditional
675 would force it to 0377. That looks like duplicated code. */
676 #ifndef SIGNALS_VIA_CHARACTERS
677 /* QUIT and INTR work better as signals, so disable character forms */
678 s
.main
.c_cc
[VQUIT
] = CDISABLE
;
679 s
.main
.c_cc
[VINTR
] = CDISABLE
;
680 s
.main
.c_lflag
&= ~ISIG
;
681 #endif /* no TIOCGPGRP or no TIOCGLTC or no TIOCGETC */
682 s
.main
.c_cc
[VEOL
] = CDISABLE
;
683 s
.main
.c_cflag
= (s
.main
.c_cflag
& ~CBAUD
) | B9600
; /* baud rate sanity */
686 #else /* not HAVE_TERMIO */
688 s
.main
.sg_flags
&= ~(ECHO
| CRMOD
| ANYP
| ALLDELAY
| RAW
| LCASE
690 s
.main
.sg_flags
|= LPASS8
;
691 s
.main
.sg_erase
= 0377;
692 s
.main
.sg_kill
= 0377;
693 s
.lmode
= LLITOUT
| s
.lmode
; /* Don't strip 8th bit */
695 #endif /* not HAVE_TERMIO */
697 EMACS_SET_TTY (out
, &s
, 0);
703 #endif /* not DOS_NT */
707 #endif /* subprocesses */
709 /* Record a signal code and the handler for it. */
713 SIGTYPE (*handler
) P_ ((int));
716 static void save_signal_handlers
P_ ((struct save_signal
*));
717 static void restore_signal_handlers
P_ ((struct save_signal
*));
719 /* Suspend the Emacs process; give terminal to its superior. */
725 /* "Foster" parentage allows emacs to return to a subprocess that attached
726 to the current emacs as a cheaper than starting a whole new process. This
727 is set up by KEPTEDITOR.COM. */
728 unsigned long parent_id
, foster_parent_id
;
731 fpid_string
= getenv ("EMACS_PARENT_PID");
732 if (fpid_string
!= NULL
)
734 sscanf (fpid_string
, "%x", &foster_parent_id
);
735 if (foster_parent_id
!= 0)
736 parent_id
= foster_parent_id
;
738 parent_id
= getppid ();
741 parent_id
= getppid ();
743 xfree (fpid_string
); /* On VMS, this was malloc'd */
745 if (parent_id
&& parent_id
!= 0xffffffff)
747 SIGTYPE (*oldsig
)() = (int) signal (SIGINT
, SIG_IGN
);
748 int status
= LIB$
ATTACH (&parent_id
) & 1;
749 signal (SIGINT
, oldsig
);
758 d_prompt
.l
= sizeof ("Emacs: "); /* Our special prompt */
759 d_prompt
.a
= "Emacs: "; /* Just a reminder */
760 LIB$
SPAWN (0, 0, 0, 0, 0, 0, 0, 0, 0, 0, &d_prompt
, 0);
765 #if defined (SIGTSTP) && !defined (MSDOS)
768 int pgrp
= EMACS_GETPGRP (0);
769 EMACS_KILLPG (pgrp
, SIGTSTP
);
772 #else /* No SIGTSTP */
773 #ifdef USG_JOBCTRL /* If you don't know what this is don't mess with it */
774 ptrace (0, 0, 0, 0); /* set for ptrace - caught by csh */
775 kill (getpid (), SIGQUIT
);
777 #else /* No SIGTSTP or USG_JOBCTRL */
779 /* On a system where suspending is not implemented,
780 instead fork a subshell and let it talk directly to the terminal
784 #endif /* no USG_JOBCTRL */
785 #endif /* no SIGTSTP */
789 /* Fork a subshell. */
795 #ifdef DOS_NT /* Demacs 1.1.2 91/10/20 Manabu Higashida */
797 char oldwd
[MAXPATHLEN
+1]; /* Fixed length is safe on MSDOS. */
800 struct save_signal saved_handlers
[5];
802 unsigned char *str
= 0;
805 saved_handlers
[0].code
= SIGINT
;
806 saved_handlers
[1].code
= SIGQUIT
;
807 saved_handlers
[2].code
= SIGTERM
;
809 saved_handlers
[3].code
= SIGIO
;
810 saved_handlers
[4].code
= 0;
812 saved_handlers
[3].code
= 0;
815 /* Mentioning current_buffer->buffer would mean including buffer.h,
816 which somehow wedges the hp compiler. So instead... */
818 dir
= intern ("default-directory");
819 if (NILP (Fboundp (dir
)))
821 dir
= Fsymbol_value (dir
);
825 dir
= expand_and_dir_to_file (Funhandled_file_name_directory (dir
), Qnil
);
826 str
= (unsigned char *) alloca (SCHARS (dir
) + 2);
828 bcopy (SDATA (dir
), str
, len
);
829 if (str
[len
- 1] != '/') str
[len
++] = '/';
836 save_signal_handlers (saved_handlers
);
837 synch_process_alive
= 1;
838 #endif /* __DJGPP__ > 1 */
842 error ("Can't spawn subshell");
849 #ifdef DOS_NT /* MW, Aug 1993 */
852 sh
= (char *) egetenv ("SUSPEND"); /* KFS, 1994-12-14 */
855 sh
= (char *) egetenv ("SHELL");
859 /* Use our buffer's default directory for the subshell. */
861 chdir ((char *) str
);
864 close_process_descs (); /* Close Emacs's pipes/ptys */
867 #ifdef SET_EMACS_PRIORITY
869 extern EMACS_INT emacs_priority
;
871 if (emacs_priority
< 0)
872 nice (-emacs_priority
);
876 #ifdef MSDOS /* Demacs 1.1.2 91/10/20 Manabu Higashida */
878 char *epwd
= getenv ("PWD");
879 char old_pwd
[MAXPATHLEN
+1+4];
881 /* If PWD is set, pass it with corrected value. */
884 strcpy (old_pwd
, epwd
);
885 if (str
[len
- 1] == '/')
887 setenv ("PWD", str
, 1);
892 putenv (old_pwd
); /* restore previous value */
894 #if 0 /* This is also reported if last command executed in subshell failed, KFS */
896 report_file_error ("Can't execute subshell", Fcons (build_string (sh
), Qnil
));
898 #else /* not MSDOS */
900 /* Waits for process completion */
901 pid
= _spawnlp (_P_WAIT
, sh
, sh
, NULL
);
904 write (1, "Can't execute subshell", 22);
905 #else /* not WINDOWSNT */
906 execlp (sh
, sh
, (char *) 0);
907 write (1, "Can't execute subshell", 22);
909 #endif /* not WINDOWSNT */
910 #endif /* not MSDOS */
913 /* Do this now if we did not do it before. */
914 #if !defined (MSDOS) || __DJGPP__ == 1
915 save_signal_handlers (saved_handlers
);
916 synch_process_alive
= 1;
920 wait_for_termination (pid
);
922 restore_signal_handlers (saved_handlers
);
923 synch_process_alive
= 0;
928 save_signal_handlers (saved_handlers
)
929 struct save_signal
*saved_handlers
;
931 while (saved_handlers
->code
)
933 saved_handlers
->handler
934 = (SIGTYPE (*) P_ ((int))) signal (saved_handlers
->code
, SIG_IGN
);
940 restore_signal_handlers (saved_handlers
)
941 struct save_signal
*saved_handlers
;
943 while (saved_handlers
->code
)
945 signal (saved_handlers
->code
, saved_handlers
->handler
);
951 /* If SIGIO is broken, don't do anything. */
968 unrequest_sigio (void)
975 int old_fcntl_flags
[MAXDESC
];
982 old_fcntl_flags
[fd
] = fcntl (fd
, F_GETFL
, 0) & ~FASYNC
;
983 fcntl (fd
, F_SETFL
, old_fcntl_flags
[fd
] | FASYNC
);
985 interrupts_deferred
= 0;
993 fcntl (fd
, F_SETFL
, old_fcntl_flags
[fd
]);
997 #ifdef FASYNC /* F_SETFL does not imply existence of FASYNC */
998 /* XXX Uhm, FASYNC is not used anymore here. */
999 /* XXX Yeah, but you need it for SIGIO, don't you? */
1008 sigunblock (sigmask (SIGWINCH
));
1010 sigunblock (sigmask (SIGIO
));
1012 interrupts_deferred
= 0;
1016 unrequest_sigio (void)
1021 #if 0 /* XXX What's wrong with blocking SIGIO under X? */
1027 sigblock (sigmask (SIGWINCH
));
1029 sigblock (sigmask (SIGIO
));
1030 interrupts_deferred
= 1;
1033 #else /* no FASYNC */
1039 if (noninteractive
|| read_socket_hook
)
1042 croak ("request_sigio");
1048 if (noninteractive
|| read_socket_hook
)
1051 croak ("unrequest_sigio");
1056 #endif /* F_SETFL */
1059 /* Saving and restoring the process group of Emacs's terminal. */
1063 /* The process group of which Emacs was a member when it initially
1066 If Emacs was in its own process group (i.e. inherited_pgroup ==
1067 getpid ()), then we know we're running under a shell with job
1068 control (Emacs would never be run as part of a pipeline).
1071 If Emacs was not in its own process group, then we know we're
1072 running under a shell (or a caller) that doesn't know how to
1073 separate itself from Emacs (like sh). Emacs must be in its own
1074 process group in order to receive SIGIO correctly. In this
1075 situation, we put ourselves in our own pgroup, forcibly set the
1076 tty's pgroup to our pgroup, and make sure to restore and reinstate
1077 the tty's pgroup just like any other terminal setting. If
1078 inherited_group was not the tty's pgroup, then we'll get a
1079 SIGTTmumble when we try to change the tty's pgroup, and a CONT if
1080 it goes foreground in the future, which is what should happen.
1082 This variable is initialized in emacs.c. */
1083 int inherited_pgroup
;
1085 /* Split off the foreground process group to Emacs alone. When we are
1086 in the foreground, but not started in our own process group,
1087 redirect the tty device handle FD to point to our own process
1088 group. We need to be in our own process group to receive SIGIO
1091 narrow_foreground_group (int fd
)
1095 setpgrp (0, inherited_pgroup
);
1097 /* XXX inherited_pgroup should not be zero here, but GTK seems to
1099 if (! inherited_pgroup
)
1100 abort (); /* Should not happen. */
1102 if (inherited_pgroup
!= me
)
1103 EMACS_SET_TTY_PGRP (fd
, &me
); /* XXX This only works on the controlling tty. */
1107 /* Set the tty to our original foreground group. */
1109 widen_foreground_group (int fd
)
1111 if (inherited_pgroup
!= getpid ())
1112 EMACS_SET_TTY_PGRP (fd
, &inherited_pgroup
);
1113 setpgrp (0, inherited_pgroup
);
1116 #endif /* BSD_PGRPS */
1118 /* Getting and setting emacs_tty structures. */
1120 /* Set *TC to the parameters associated with the terminal FD.
1121 Return zero if all's well, or -1 if we ran into an error we
1122 couldn't deal with. */
1124 emacs_get_tty (fd
, settings
)
1126 struct emacs_tty
*settings
;
1128 /* Retrieve the primary parameters - baud rate, character size, etcetera. */
1130 /* We have those nifty POSIX tcmumbleattr functions. */
1131 bzero (&settings
->main
, sizeof (settings
->main
));
1132 if (tcgetattr (fd
, &settings
->main
) < 0)
1137 /* The SYSV-style interface? */
1138 if (ioctl (fd
, TCGETA
, &settings
->main
) < 0)
1143 /* Vehemently Monstrous System? :-) */
1144 if (! (SYS$
QIOW (0, fd
, IO$_SENSEMODE
, settings
, 0, 0,
1145 &settings
->main
.class, 12, 0, 0, 0, 0)
1151 /* I give up - I hope you have the BSD ioctls. */
1152 if (ioctl (fd
, TIOCGETP
, &settings
->main
) < 0)
1154 #endif /* not DOS_NT */
1159 /* Suivant - Do we have to get struct ltchars data? */
1161 if (ioctl (fd
, TIOCGLTC
, &settings
->ltchars
) < 0)
1165 /* How about a struct tchars and a wordful of lmode bits? */
1167 if (ioctl (fd
, TIOCGETC
, &settings
->tchars
) < 0
1168 || ioctl (fd
, TIOCLGET
, &settings
->lmode
) < 0)
1172 /* We have survived the tempest. */
1177 /* Set the parameters of the tty on FD according to the contents of
1178 *SETTINGS. If FLUSHP is non-zero, we discard input.
1179 Return 0 if all went well, and -1 if anything failed. */
1182 emacs_set_tty (fd
, settings
, flushp
)
1184 struct emacs_tty
*settings
;
1187 /* Set the primary parameters - baud rate, character size, etcetera. */
1190 /* We have those nifty POSIX tcmumbleattr functions.
1191 William J. Smith <wjs@wiis.wang.com> writes:
1192 "POSIX 1003.1 defines tcsetattr to return success if it was
1193 able to perform any of the requested actions, even if some
1194 of the requested actions could not be performed.
1195 We must read settings back to ensure tty setup properly.
1196 AIX requires this to keep tty from hanging occasionally." */
1197 /* This make sure that we don't loop indefinitely in here. */
1198 for (i
= 0 ; i
< 10 ; i
++)
1199 if (tcsetattr (fd
, flushp
? TCSAFLUSH
: TCSADRAIN
, &settings
->main
) < 0)
1210 bzero (&new, sizeof (new));
1211 /* Get the current settings, and see if they're what we asked for. */
1212 tcgetattr (fd
, &new);
1213 /* We cannot use memcmp on the whole structure here because under
1214 * aix386 the termios structure has some reserved field that may
1217 if ( new.c_iflag
== settings
->main
.c_iflag
1218 && new.c_oflag
== settings
->main
.c_oflag
1219 && new.c_cflag
== settings
->main
.c_cflag
1220 && new.c_lflag
== settings
->main
.c_lflag
1221 && memcmp (new.c_cc
, settings
->main
.c_cc
, NCCS
) == 0)
1229 /* The SYSV-style interface? */
1230 if (ioctl (fd
, flushp
? TCSETAF
: TCSETAW
, &settings
->main
) < 0)
1235 /* Vehemently Monstrous System? :-) */
1236 if (! (SYS$
QIOW (0, fd
, IO$_SETMODE
, &input_iosb
, 0, 0,
1237 &settings
->main
.class, 12, 0, 0, 0, 0)
1243 /* I give up - I hope you have the BSD ioctls. */
1244 if (ioctl (fd
, (flushp
) ? TIOCSETP
: TIOCSETN
, &settings
->main
) < 0)
1246 #endif /* not DOS_NT */
1252 /* Suivant - Do we have to get struct ltchars data? */
1254 if (ioctl (fd
, TIOCSLTC
, &settings
->ltchars
) < 0)
1258 /* How about a struct tchars and a wordful of lmode bits? */
1260 if (ioctl (fd
, TIOCSETC
, &settings
->tchars
) < 0
1261 || ioctl (fd
, TIOCLSET
, &settings
->lmode
) < 0)
1265 /* We have survived the tempest. */
1272 /* BSD 4.1 needs to keep track of the lmode bits in order to start
1277 #ifndef F_SETOWN_BUG
1279 int old_fcntl_owner
[MAXDESC
];
1280 #endif /* F_SETOWN */
1281 #endif /* F_SETOWN_BUG */
1283 /* This may also be defined in stdio,
1284 but if so, this does no harm,
1285 and using the same name avoids wasting the other one's space. */
1288 extern char *_sobuf
;
1290 #if defined (USG) || defined (DGUX)
1291 unsigned char _sobuf
[BUFSIZ
+8];
1293 char _sobuf
[BUFSIZ
];
1298 static struct ltchars new_ltchars
= {-1,-1,-1,-1,-1,-1};
1301 static struct tchars new_tchars
= {-1,-1,-1,-1,-1,-1};
1304 /* Initialize the terminal mode on all tty devices that are currently
1308 init_all_sys_modes (void)
1310 struct tty_display_info
*tty
;
1311 for (tty
= tty_list
; tty
; tty
= tty
->next
)
1312 init_sys_modes (tty
);
1315 /* Initialize the terminal mode on the given tty device. */
1318 init_sys_modes (tty_out
)
1319 struct tty_display_info
*tty_out
;
1321 struct emacs_tty tty
;
1325 static int oob_chars
[2] = {0, 1 << 7}; /* catch C-g's */
1326 extern int (*interrupt_signal
) ();
1330 Vtty_erase_char
= Qnil
;
1335 if (!tty_out
->output
)
1336 return; /* The tty is suspended. */
1340 input_ef
= get_kbd_event_flag ();
1341 /* LIB$GET_EF (&input_ef); */
1342 SYS$
CLREF (input_ef
);
1343 waiting_for_ast
= 0;
1345 timer_ef
= get_timer_event_flag ();
1346 /* LIB$GET_EF (&timer_ef); */
1347 SYS$
CLREF (timer_ef
);
1351 LIB$
GET_EF (&process_ef
);
1352 SYS$
CLREF (process_ef
);
1354 if (input_ef
/ 32 != process_ef
/ 32)
1355 croak ("Input and process event flags in different clusters.");
1357 if (input_ef
/ 32 != timer_ef
/ 32)
1358 croak ("Input and timer event flags in different clusters.");
1360 input_eflist
= ((unsigned) 1 << (input_ef
% 32)) |
1361 ((unsigned) 1 << (process_ef
% 32));
1363 timer_eflist
= ((unsigned) 1 << (input_ef
% 32)) |
1364 ((unsigned) 1 << (timer_ef
% 32));
1366 sys_access_reinit ();
1372 /* read_socket_hook is not global anymore. I think doing this
1373 unconditionally will not cause any problems. */
1374 if (! read_socket_hook
&& EQ (Vinitial_window_system
, Qnil
))
1376 narrow_foreground_group (fileno (tty_out
->input
));
1379 if (! tty_out
->old_tty
)
1380 tty_out
->old_tty
= (struct emacs_tty
*) xmalloc (sizeof (struct emacs_tty
));
1382 EMACS_GET_TTY (fileno (tty_out
->input
), tty_out
->old_tty
);
1384 tty
= *tty_out
->old_tty
;
1386 #if defined (HAVE_TERMIO) || defined (HAVE_TERMIOS)
1387 XSETINT (Vtty_erase_char
, tty
.main
.c_cc
[VERASE
]);
1389 tty
.main
.c_iflag
|= (IGNBRK
); /* Ignore break condition */
1390 tty
.main
.c_iflag
&= ~ICRNL
; /* Disable map of CR to NL on input */
1391 #ifdef INLCR /* I'm just being cautious,
1392 since I can't check how widespread INLCR is--rms. */
1393 tty
.main
.c_iflag
&= ~INLCR
; /* Disable map of NL to CR on input */
1396 tty
.main
.c_iflag
&= ~ISTRIP
; /* don't strip 8th bit on input */
1398 tty
.main
.c_lflag
&= ~ECHO
; /* Disable echo */
1399 tty
.main
.c_lflag
&= ~ICANON
; /* Disable erase/kill processing */
1401 tty
.main
.c_lflag
&= ~IEXTEN
; /* Disable other editing characters. */
1403 tty
.main
.c_lflag
|= ISIG
; /* Enable signals */
1404 if (tty_out
->flow_control
)
1406 tty
.main
.c_iflag
|= IXON
; /* Enable start/stop output control */
1408 tty
.main
.c_iflag
&= ~IXANY
;
1412 tty
.main
.c_iflag
&= ~IXON
; /* Disable start/stop output control */
1413 tty
.main
.c_oflag
&= ~ONLCR
; /* Disable map of NL to CR-NL
1415 tty
.main
.c_oflag
&= ~TAB3
; /* Disable tab expansion */
1417 if (tty_out
->meta_key
)
1419 tty
.main
.c_cflag
|= CS8
; /* allow 8th bit on input */
1420 tty
.main
.c_cflag
&= ~PARENB
;/* Don't check parity */
1423 if (tty_out
->input
== stdin
)
1425 tty
.main
.c_cc
[VINTR
] = quit_char
; /* C-g (usually) gives SIGINT */
1426 /* Set up C-g for both SIGQUIT and SIGINT.
1427 We don't know which we will get, but we handle both alike
1428 so which one it really gives us does not matter. */
1429 tty
.main
.c_cc
[VQUIT
] = quit_char
;
1433 /* We normally don't get interrupt or quit signals from tty
1434 devices other than our controlling terminal; therefore,
1435 we must handle C-g as normal input. Unfortunately, this
1436 means that the interrupt and quit feature must be
1437 disabled on secondary ttys, or we would not even see the
1440 Note that even though emacsclient could have special code
1441 to pass SIGINT to Emacs, we should _not_ enable
1442 interrupt/quit keys for emacsclient frames. This means
1443 that we can't break out of loops in C code from a
1444 secondary tty frame, but we can always decide what
1445 display the C-g came from, which is more important from a
1446 usability point of view. (Consider the case when two
1447 people work together using the same Emacs instance.) */
1448 tty
.main
.c_cc
[VINTR
] = CDISABLE
;
1449 tty
.main
.c_cc
[VQUIT
] = CDISABLE
;
1451 tty
.main
.c_cc
[VMIN
] = 1; /* Input should wait for at least 1 char */
1452 tty
.main
.c_cc
[VTIME
] = 0; /* no matter how long that takes. */
1454 tty
.main
.c_cc
[VSWTCH
] = CDISABLE
; /* Turn off shell layering use
1458 #if defined (mips) || defined (HAVE_TCATTR)
1460 tty
.main
.c_cc
[VSUSP
] = CDISABLE
; /* Turn off mips handling of C-z. */
1463 tty
.main
.c_cc
[V_DSUSP
] = CDISABLE
; /* Turn off mips handling of C-y. */
1464 #endif /* V_DSUSP */
1465 #ifdef VDSUSP /* Some systems have VDSUSP, some have V_DSUSP. */
1466 tty
.main
.c_cc
[VDSUSP
] = CDISABLE
;
1469 tty
.main
.c_cc
[VLNEXT
] = CDISABLE
;
1472 tty
.main
.c_cc
[VREPRINT
] = CDISABLE
;
1473 #endif /* VREPRINT */
1475 tty
.main
.c_cc
[VWERASE
] = CDISABLE
;
1476 #endif /* VWERASE */
1478 tty
.main
.c_cc
[VDISCARD
] = CDISABLE
;
1479 #endif /* VDISCARD */
1481 if (tty_out
->flow_control
)
1484 tty
.main
.c_cc
[VSTART
] = '\021';
1487 tty
.main
.c_cc
[VSTOP
] = '\023';
1493 tty
.main
.c_cc
[VSTART
] = CDISABLE
;
1496 tty
.main
.c_cc
[VSTOP
] = CDISABLE
;
1499 #endif /* mips or HAVE_TCATTR */
1501 #ifdef SET_LINE_DISCIPLINE
1502 /* Need to explicitly request TERMIODISC line discipline or
1503 Ultrix's termios does not work correctly. */
1504 tty
.main
.c_line
= SET_LINE_DISCIPLINE
;
1508 /* AIX enhanced edit loses NULs, so disable it. */
1509 tty
.main
.c_line
= 0;
1510 tty
.main
.c_iflag
&= ~ASCEDIT
;
1512 tty
.main
.c_cc
[VSTRT
] = CDISABLE
;
1513 tty
.main
.c_cc
[VSTOP
] = CDISABLE
;
1514 tty
.main
.c_cc
[VSUSP
] = CDISABLE
;
1515 tty
.main
.c_cc
[VDSUSP
] = CDISABLE
;
1516 #endif /* IBMR2AIX */
1517 if (tty_out
->flow_control
)
1520 tty
.main
.c_cc
[VSTART
] = '\021';
1523 tty
.main
.c_cc
[VSTOP
] = '\023';
1526 /* Also, PTY overloads NUL and BREAK.
1527 don't ignore break, but don't signal either, so it looks like NUL.
1528 This really serves a purpose only if running in an XTERM window
1529 or via TELNET or the like, but does no harm elsewhere. */
1530 tty
.main
.c_iflag
&= ~IGNBRK
;
1531 tty
.main
.c_iflag
&= ~BRKINT
;
1533 #else /* if not HAVE_TERMIO */
1535 tty
.main
.tt_char
|= TT$M_NOECHO
;
1537 tty
.main
.tt_char
|= TT$M_EIGHTBIT
;
1538 if (tty_out
->flow_control
)
1539 tty
.main
.tt_char
|= TT$M_TTSYNC
;
1541 tty
.main
.tt_char
&= ~TT$M_TTSYNC
;
1542 tty
.main
.tt2_char
|= TT2$M_PASTHRU
| TT2$M_XON
;
1543 #else /* not VMS (BSD, that is) */
1545 XSETINT (Vtty_erase_char
, tty
.main
.sg_erase
);
1546 tty
.main
.sg_flags
&= ~(ECHO
| CRMOD
| XTABS
);
1548 tty
.main
.sg_flags
|= ANYP
;
1549 tty
.main
.sg_flags
|= interrupt_input
? RAW
: CBREAK
;
1550 #endif /* not DOS_NT */
1551 #endif /* not VMS (BSD, that is) */
1552 #endif /* not HAVE_TERMIO */
1554 /* If going to use CBREAK mode, we must request C-g to interrupt
1555 and turn off start and stop chars, etc. If not going to use
1556 CBREAK mode, do this anyway so as to turn off local flow
1557 control for user coming over network on 4.2; in this case,
1558 only t_stopc and t_startc really matter. */
1561 /* Note: if not using CBREAK mode, it makes no difference how we
1563 tty
.tchars
= new_tchars
;
1564 tty
.tchars
.t_intrc
= quit_char
;
1565 if (tty_out
->flow_control
)
1567 tty
.tchars
.t_startc
= '\021';
1568 tty
.tchars
.t_stopc
= '\023';
1571 tty
.lmode
= LDECCTQ
| LLITOUT
| LPASS8
| LNOFLSH
| tty_out
->old_tty
.lmode
;
1573 /* Under Ultrix 4.2a, leaving this out doesn't seem to hurt
1574 anything, and leaving it in breaks the meta key. Go figure. */
1575 tty
.lmode
&= ~LLITOUT
;
1582 #endif /* HAVE_TCHARS */
1583 #endif /* not HAVE_TERMIO */
1586 tty
.ltchars
= new_ltchars
;
1587 #endif /* HAVE_LTCHARS */
1588 #ifdef MSDOS /* Demacs 1.1.2 91/10/20 Manabu Higashida, MW Aug 1993 */
1589 if (!tty_out
->term_initted
)
1590 internal_terminal_init ();
1594 EMACS_SET_TTY (fileno (tty_out
->input
), &tty
, 0);
1596 /* This code added to insure that, if flow-control is not to be used,
1597 we have an unlocked terminal at the start. */
1600 if (!tty_out
->flow_control
) ioctl (fileno (tty_out
->input
), TCXONC
, 1);
1603 if (!tty_out
->flow_control
) ioctl (fileno (tty_out
->input
), TIOCSTART
, 0);
1606 #if defined (HAVE_TERMIOS) || defined (HPUX9)
1608 if (!tty_out
->flow_control
) tcflow (fileno (tty_out
->input
), TCOON
);
1616 /* IBM's HFT device usually thinks a ^J should be LF/CR. We need it
1617 to be only LF. This is the way that is done. */
1620 if (ioctl (1, HFTGETID
, &tty
) != -1)
1621 write (1, "\033[20l", 5);
1627 /* Appears to do nothing when in PASTHRU mode.
1628 SYS$QIOW (0, fileno (tty_out->input), IO$_SETMODE|IO$M_OUTBAND, 0, 0, 0,
1629 interrupt_signal, oob_chars, 0, 0, 0, 0);
1631 queue_kbd_input (0);
1635 #ifndef F_SETOWN_BUG
1636 #ifdef F_GETOWN /* F_SETFL does not imply existence of F_GETOWN */
1637 if (interrupt_input
)
1639 old_fcntl_owner
[fileno (tty_out
->input
)] =
1640 fcntl (fileno (tty_out
->input
), F_GETOWN
, 0);
1641 fcntl (fileno (tty_out
->input
), F_SETOWN
, getpid ());
1642 init_sigio (fileno (tty_out
->input
));
1644 if (gpm_tty
== tty_out
)
1646 /* Arrange for mouse events to give us SIGIO signals. */
1647 fcntl (gpm_fd
, F_SETOWN
, getpid ());
1648 fcntl (gpm_fd
, F_SETFL
, fcntl (gpm_fd
, F_GETFL
, 0) | O_NONBLOCK
);
1649 init_sigio (gpm_fd
);
1651 #endif /* HAVE_GPM */
1653 #endif /* F_GETOWN */
1654 #endif /* F_SETOWN_BUG */
1655 #endif /* F_SETFL */
1658 if (interrupt_input
)
1659 init_sigio (fileno (tty_out
->input
));
1662 #ifdef VMS /* VMS sometimes has this symbol but lacks setvbuf. */
1666 /* This symbol is defined on recent USG systems.
1667 Someone says without this call USG won't really buffer the file
1668 even with a call to setbuf. */
1669 setvbuf (tty_out
->output
, (char *) _sobuf
, _IOFBF
, sizeof _sobuf
);
1671 setbuf (tty_out
->output
, (char *) _sobuf
);
1674 if (tty_out
->terminal
->set_terminal_modes_hook
)
1675 tty_out
->terminal
->set_terminal_modes_hook (tty_out
->terminal
);
1677 if (!tty_out
->term_initted
)
1679 Lisp_Object tail
, frame
;
1680 FOR_EACH_FRAME (tail
, frame
)
1682 /* XXX This needs to be revised. */
1683 if (FRAME_TERMCAP_P (XFRAME (frame
))
1684 && FRAME_TTY (XFRAME (frame
)) == tty_out
)
1685 init_frame_faces (XFRAME (frame
));
1689 if (tty_out
->term_initted
&& no_redraw_on_reenter
)
1691 /* XXX This seems wrong on multi-tty. */
1692 if (display_completed
)
1693 direct_output_forward_char (0);
1697 Lisp_Object tail
, frame
;
1699 FOR_EACH_FRAME (tail
, frame
)
1701 if (FRAME_TERMCAP_P (XFRAME (frame
))
1702 && FRAME_TTY (XFRAME (frame
)) == tty_out
)
1703 FRAME_GARBAGED_P (XFRAME (frame
)) = 1;
1707 tty_out
->term_initted
= 1;
1710 /* Return nonzero if safe to use tabs in output.
1711 At the time this is called, init_sys_modes has not been done yet. */
1714 tabs_safe_p (int fd
)
1716 struct emacs_tty etty
;
1718 EMACS_GET_TTY (fd
, &etty
);
1719 return EMACS_TTY_TABS_OK (&etty
);
1722 /* Get terminal size from system.
1723 Store number of lines into *HEIGHTP and width into *WIDTHP.
1724 We store 0 if there's no valid information. */
1727 get_tty_size (int fd
, int *widthp
, int *heightp
)
1733 struct winsize size
;
1735 if (ioctl (fd
, TIOCGWINSZ
, &size
) == -1)
1736 *widthp
= *heightp
= 0;
1739 *widthp
= size
.ws_col
;
1740 *heightp
= size
.ws_row
;
1746 /* SunOS - style. */
1747 struct ttysize size
;
1749 if (ioctl (fd
, TIOCGSIZE
, &size
) == -1)
1750 *widthp
= *heightp
= 0;
1753 *widthp
= size
.ts_cols
;
1754 *heightp
= size
.ts_lines
;
1760 /* Use a fresh channel since the current one may have stale info
1761 (for example, from prior to a suspend); and to avoid a dependency
1762 in the init sequence. */
1764 struct sensemode tty
;
1766 SYS$
ASSIGN (&input_dsc
, &chan
, 0, 0);
1767 SYS$
QIOW (0, chan
, IO$_SENSEMODE
, &tty
, 0, 0,
1768 &tty
.class, 12, 0, 0, 0, 0);
1770 *widthp
= tty
.scr_wid
;
1771 *heightp
= tty
.scr_len
;
1775 *widthp
= ScreenCols ();
1776 *heightp
= ScreenRows ();
1777 #else /* system doesn't know size */
1781 #endif /* not VMS */
1782 #endif /* not SunOS-style */
1783 #endif /* not BSD-style */
1786 /* Set the logical window size associated with descriptor FD
1787 to HEIGHT and WIDTH. This is used mainly with ptys. */
1790 set_window_size (fd
, height
, width
)
1791 int fd
, height
, width
;
1796 struct winsize size
;
1797 size
.ws_row
= height
;
1798 size
.ws_col
= width
;
1800 if (ioctl (fd
, TIOCSWINSZ
, &size
) == -1)
1801 return 0; /* error */
1808 /* SunOS - style. */
1809 struct ttysize size
;
1810 size
.ts_lines
= height
;
1811 size
.ts_cols
= width
;
1813 if (ioctl (fd
, TIOCGSIZE
, &size
) == -1)
1819 #endif /* not SunOS-style */
1820 #endif /* not BSD-style */
1825 /* Prepare all terminal devices for exiting Emacs. */
1828 reset_all_sys_modes (void)
1830 struct tty_display_info
*tty
;
1831 for (tty
= tty_list
; tty
; tty
= tty
->next
)
1832 reset_sys_modes (tty
);
1835 /* Prepare the terminal for closing it; move the cursor to the
1836 bottom of the frame, turn off interrupt-driven I/O, etc. */
1839 reset_sys_modes (tty_out
)
1840 struct tty_display_info
*tty_out
;
1847 if (!tty_out
->term_initted
)
1850 if (!tty_out
->output
)
1851 return; /* The tty is suspended. */
1853 /* Go to and clear the last line of the terminal. */
1855 cmgoto (tty_out
, FrameRows (tty_out
) - 1, 0);
1857 /* Code adapted from tty_clear_end_of_line. */
1858 if (tty_out
->TS_clr_line
)
1860 emacs_tputs (tty_out
, tty_out
->TS_clr_line
, 1, cmputc
);
1863 { /* have to do it the hard way */
1865 tty_turn_off_insert (tty_out
);
1867 for (i
= curX (tty_out
); i
< FrameCols (tty_out
) - 1; i
++)
1869 fputc (' ', tty_out
->output
);
1873 cmgoto (tty_out
, FrameRows (tty_out
) - 1, 0);
1874 fflush (tty_out
->output
);
1876 #if defined (IBMR2AIX) && defined (AIXHFT)
1878 /* HFT devices normally use ^J as a LF/CR. We forced it to
1879 do the LF only. Now, we need to reset it. */
1882 if (ioctl (1, HFTGETID
, &tty
) != -1)
1883 write (1, "\033[20h", 5);
1887 if (tty_out
->terminal
->reset_terminal_modes_hook
)
1888 tty_out
->terminal
->reset_terminal_modes_hook (tty_out
->terminal
);
1892 /* Avoid possible loss of output when changing terminal modes. */
1893 fsync (fileno (tty_out
->output
));
1898 #ifndef F_SETOWN_BUG
1899 #ifdef F_SETOWN /* F_SETFL does not imply existence of F_SETOWN */
1900 if (interrupt_input
)
1902 reset_sigio (fileno (tty_out
->input
));
1903 fcntl (fileno (tty_out
->input
), F_SETOWN
,
1904 old_fcntl_owner
[fileno (tty_out
->input
)]);
1906 #endif /* F_SETOWN */
1907 #endif /* F_SETOWN_BUG */
1909 fcntl (fileno (tty_out
->input
), F_SETFL
,
1910 fcntl (fileno (tty_out
->input
), F_GETFL
, 0) & ~O_NDELAY
);
1912 #endif /* F_SETFL */
1914 if (interrupt_input
)
1915 reset_sigio (fileno (tty_out
->input
));
1918 if (tty_out
->old_tty
)
1919 while (EMACS_SET_TTY (fileno (tty_out
->input
),
1920 tty_out
->old_tty
, 0) < 0 && errno
== EINTR
)
1923 #ifdef MSDOS /* Demacs 1.1.2 91/10/20 Manabu Higashida */
1927 #ifdef SET_LINE_DISCIPLINE
1928 /* Ultrix's termios *ignores* any line discipline except TERMIODISC.
1929 A different old line discipline is therefore not restored, yet.
1930 Restore the old line discipline by hand. */
1931 ioctl (0, TIOCSETD
, &tty_out
->old_tty
.main
.c_line
);
1939 widen_foreground_group (fileno (tty_out
->input
));
1945 /* Set up the proper status flags for use of a pty. */
1951 /* I'm told that TOICREMOTE does not mean control chars
1952 "can't be sent" but rather that they don't have
1953 input-editing or signaling effects.
1954 That should be good, because we have other ways
1955 to do those things in Emacs.
1956 However, telnet mode seems not to work on 4.2.
1957 So TIOCREMOTE is turned off now. */
1959 /* Under hp-ux, if TIOCREMOTE is turned on, some calls
1960 will hang. In particular, the "timeout" feature (which
1961 causes a read to return if there is no data available)
1962 does this. Also it is known that telnet mode will hang
1963 in such a way that Emacs must be stopped (perhaps this
1964 is the same problem).
1966 If TIOCREMOTE is turned off, then there is a bug in
1967 hp-ux which sometimes loses data. Apparently the
1968 code which blocks the master process when the internal
1969 buffer fills up does not work. Other than this,
1970 though, everything else seems to work fine.
1972 Since the latter lossage is more benign, we may as well
1973 lose that way. -- cph */
1975 #if defined(SYSV_PTYS) || defined(UNIX98_PTYS)
1978 ioctl (fd
, FIONBIO
, &on
);
1983 #endif /* HAVE_PTYS */
1987 /* Assigning an input channel is done at the start of Emacs execution.
1988 This is called each time Emacs is resumed, also, but does nothing
1989 because input_chain is no longer zero. */
1996 if (fileno (CURTTY ()->input
)) == 0)
1998 status
= SYS$
ASSIGN (&input_dsc
, &fileno (CURTTY ()->input
)), 0, 0);
2004 /* Deassigning the input channel is done before exiting. */
2009 return SYS$
DASSGN (fileno (CURTTY ()->input
)));
2014 /* Request reading one character into the keyboard buffer.
2015 This is done as soon as the buffer becomes empty. */
2021 extern kbd_input_ast ();
2023 waiting_for_ast
= 0;
2025 status
= SYS$
QIO (0, fileno (CURTTY()->input
), IO$_READVBLK
,
2026 &input_iosb
, kbd_input_ast
, 1,
2027 &input_buffer
, 1, 0, terminator_mask
, 0, 0);
2032 /* Ast routine that is called when keyboard input comes in
2033 in accord with the SYS$QIO above. */
2038 register int c
= -1;
2039 int old_errno
= errno
;
2040 extern EMACS_TIME
*input_available_clear_time
;
2042 if (waiting_for_ast
)
2043 SYS$
SETEF (input_ef
);
2044 waiting_for_ast
= 0;
2047 if (input_count
== 25)
2049 printf ("Ast # %d,", input_count
);
2050 printf (" iosb = %x, %x, %x, %x",
2051 input_iosb
.offset
, input_iosb
.status
, input_iosb
.termlen
,
2054 if (input_iosb
.offset
)
2058 printf (", char = 0%o", c
);
2070 struct input_event e
;
2073 e
.kind
= ASCII_KEYSTROKE_EVENT
;
2074 XSETINT (e
.code
, c
);
2075 e
.frame_or_window
= selected_frame
;
2076 kbd_buffer_store_event (&e
);
2078 if (input_available_clear_time
)
2079 EMACS_SET_SECS_USECS (*input_available_clear_time
, 0, 0);
2083 /* Wait until there is something in kbd_buffer. */
2086 wait_for_kbd_input ()
2088 extern int have_process_input
, process_exited
;
2090 /* If already something, avoid doing system calls. */
2091 if (detect_input_pending ())
2095 /* Clear a flag, and tell ast routine above to set it. */
2096 SYS$
CLREF (input_ef
);
2097 waiting_for_ast
= 1;
2098 /* Check for timing error: ast happened while we were doing that. */
2099 if (!detect_input_pending ())
2101 /* No timing error: wait for flag to be set. */
2102 set_waiting_for_input (0);
2103 SYS$
WFLOR (input_ef
, input_eflist
);
2104 clear_waiting_for_input ();
2105 if (!detect_input_pending ())
2106 /* Check for subprocess input availability */
2108 int dsp
= have_process_input
|| process_exited
;
2110 SYS$
CLREF (process_ef
);
2111 if (have_process_input
)
2112 process_command_input ();
2117 update_mode_lines
++;
2118 prepare_menu_bars ();
2119 redisplay_preserve_echo_area (18);
2123 waiting_for_ast
= 0;
2126 /* Get rid of any pending QIO, when we are about to suspend
2127 or when we want to throw away pending input.
2128 We wait for a positive sign that the AST routine has run
2129 and therefore there is no I/O request queued when we return.
2130 SYS$SETAST is used to avoid a timing error. */
2136 printf ("At end_kbd_input.\n");
2140 if (LIB$
AST_IN_PROG ()) /* Don't wait if suspending from kbd_buffer_store_event! */
2142 SYS$
CANCEL (fileno (CURTTY()->input
));
2147 /* Clear a flag, and tell ast routine above to set it. */
2148 SYS$
CLREF (input_ef
);
2149 waiting_for_ast
= 1;
2151 SYS$
CANCEL (fileno (CURTTY()->input
));
2153 SYS$
WAITFR (input_ef
);
2154 waiting_for_ast
= 0;
2157 /* Wait for either input available or time interval expiry. */
2160 input_wait_timeout (timeval
)
2161 int timeval
; /* Time to wait, in seconds */
2164 static int zero
= 0;
2165 static int large
= -10000000;
2167 LIB$
EMUL (&timeval
, &large
, &zero
, time
); /* Convert to VMS format */
2169 /* If already something, avoid doing system calls. */
2170 if (detect_input_pending ())
2174 /* Clear a flag, and tell ast routine above to set it. */
2175 SYS$
CLREF (input_ef
);
2176 waiting_for_ast
= 1;
2177 /* Check for timing error: ast happened while we were doing that. */
2178 if (!detect_input_pending ())
2180 /* No timing error: wait for flag to be set. */
2182 if (SYS$
SETIMR (timer_ef
, time
, 0, 1) & 1) /* Set timer */
2183 SYS$
WFLOR (timer_ef
, timer_eflist
); /* Wait for timer expiry or input */
2185 waiting_for_ast
= 0;
2188 /* The standard `sleep' routine works some other way
2189 and it stops working if you have ever quit out of it.
2190 This one continues to work. */
2196 static int zero
= 0;
2197 static int large
= -10000000;
2199 LIB$
EMUL (&timeval
, &large
, &zero
, time
); /* Convert to VMS format */
2202 if (SYS$
SETIMR (timer_ef
, time
, 0, 1) & 1) /* Set timer */
2203 SYS$
WAITFR (timer_ef
); /* Wait for timer expiry only */
2224 croak ("request sigio");
2232 croak ("unrequest sigio");
2237 /* Note that VMS compiler won't accept defined (CANNOT_DUMP). */
2242 #ifndef SYSTEM_MALLOC
2249 /* Some systems that cannot dump also cannot implement these. */
2252 * Return the address of the start of the text segment prior to
2253 * doing an unexec. After unexec the return value is undefined.
2254 * See crt0.c for further explanation and _start.
2258 #if !(defined (__NetBSD__) && defined (__ELF__))
2259 #ifndef HAVE_TEXT_START
2264 return ((char *) TEXT_START
);
2266 extern int _start ();
2267 return ((char *) _start
);
2268 #endif /* TEXT_START */
2270 #endif /* not HAVE_TEXT_START */
2274 * Return the address of the start of the data segment prior to
2275 * doing an unexec. After unexec the return value is undefined.
2276 * See crt0.c for further information and definition of data_start.
2278 * Apparently, on BSD systems this is etext at startup. On
2279 * USG systems (swapping) this is highly mmu dependent and
2280 * is also dependent on whether or not the program is running
2281 * with shared text. Generally there is a (possibly large)
2282 * gap between end of text and start of data with shared text.
2284 * On Uniplus+ systems with shared text, data starts at a
2285 * fixed address. Each port (from a given oem) is generally
2286 * different, and the specific value of the start of data can
2287 * be obtained via the UniPlus+ specific "uvar" system call,
2288 * however the method outlined in crt0.c seems to be more portable.
2290 * Probably what will have to happen when a USG unexec is available,
2291 * at least on UniPlus, is temacs will have to be made unshared so
2292 * that text and data are contiguous. Then once loadup is complete,
2293 * unexec will produce a shared executable where the data can be
2294 * at the normal shared text boundary and the startofdata variable
2295 * will be patched by unexec to the correct value.
2299 #ifndef start_of_data
2304 return ((char *) DATA_START
);
2306 #ifdef ORDINARY_LINK
2308 * This is a hack. Since we're not linking crt0.c or pre_crt0.c,
2309 * data_start isn't defined. We take the address of environ, which
2310 * is known to live at or near the start of the system crt0.c, and
2311 * we don't sweat the handful of bytes that might lose.
2313 extern char **environ
;
2315 return ((char *) &environ
);
2317 extern int data_start
;
2318 return ((char *) &data_start
);
2319 #endif /* ORDINARY_LINK */
2320 #endif /* DATA_START */
2322 #endif /* start_of_data */
2323 #endif /* NEED_STARTS (not CANNOT_DUMP or not SYSTEM_MALLOC) */
2325 /* init_system_name sets up the string for the Lisp function
2326 system-name to return. */
2332 extern Lisp_Object Vsystem_name
;
2337 #include <sys/socket.h>
2339 #endif /* HAVE_SOCKETS */
2340 #endif /* not VMS */
2341 #endif /* not BSD4_1 */
2344 #ifndef HAVE_H_ERRNO
2347 #endif /* TRY_AGAIN */
2353 Vsystem_name
= build_string (sysname
);
2357 if ((sp
= egetenv ("SYS$NODE")) == 0)
2358 Vsystem_name
= build_string ("vax-vms");
2359 else if ((end
= index (sp
, ':')) == 0)
2360 Vsystem_name
= build_string (sp
);
2362 Vsystem_name
= make_string (sp
, end
- sp
);
2364 #ifndef HAVE_GETHOSTNAME
2367 Vsystem_name
= build_string (uts
.nodename
);
2368 #else /* HAVE_GETHOSTNAME */
2369 unsigned int hostname_size
= 256;
2370 char *hostname
= (char *) alloca (hostname_size
);
2372 /* Try to get the host name; if the buffer is too short, try
2373 again. Apparently, the only indication gethostname gives of
2374 whether the buffer was large enough is the presence or absence
2375 of a '\0' in the string. Eech. */
2378 gethostname (hostname
, hostname_size
- 1);
2379 hostname
[hostname_size
- 1] = '\0';
2381 /* Was the buffer large enough for the '\0'? */
2382 if (strlen (hostname
) < hostname_size
- 1)
2385 hostname_size
<<= 1;
2386 hostname
= (char *) alloca (hostname_size
);
2389 /* Turn the hostname into the official, fully-qualified hostname.
2390 Don't do this if we're going to dump; this can confuse system
2391 libraries on some machines and make the dumped emacs core dump. */
2394 #endif /* not CANNOT_DUMP */
2395 if (! index (hostname
, '.'))
2398 #ifdef HAVE_GETADDRINFO
2399 struct addrinfo
*res
;
2400 struct addrinfo hints
;
2403 memset (&hints
, 0, sizeof(hints
));
2404 hints
.ai_socktype
= SOCK_STREAM
;
2405 hints
.ai_flags
= AI_CANONNAME
;
2407 for (count
= 0;; count
++)
2409 if ((ret
= getaddrinfo (hostname
, NULL
, &hints
, &res
)) == 0
2410 || ret
!= EAI_AGAIN
)
2415 Fsleep_for (make_number (1), Qnil
);
2420 struct addrinfo
*it
= res
;
2423 char *fqdn
= it
->ai_canonname
;
2424 if (fqdn
&& index (fqdn
, '.')
2425 && strcmp (fqdn
, "localhost.localdomain") != 0)
2431 hostname
= alloca (strlen (it
->ai_canonname
) + 1);
2432 strcpy (hostname
, it
->ai_canonname
);
2436 #else /* !HAVE_GETADDRINFO */
2438 for (count
= 0;; count
++)
2444 hp
= gethostbyname (hostname
);
2446 if (! (hp
== 0 && h_errno
== TRY_AGAIN
))
2453 Fsleep_for (make_number (1), Qnil
);
2458 char *fqdn
= (char *) hp
->h_name
;
2463 if (!index (fqdn
, '.'))
2465 /* We still don't have a fully qualified domain name.
2466 Try to find one in the list of alternate names */
2467 char **alias
= hp
->h_aliases
;
2469 && (!index (*alias
, '.')
2470 || !strcmp (*alias
, "localhost.localdomain")))
2477 /* Convert the host name to lower case. */
2478 /* Using ctype.h here would introduce a possible locale
2479 dependence that is probably wrong for hostnames. */
2483 if (*p
>= 'A' && *p
<= 'Z')
2489 #endif /* !HAVE_GETADDRINFO */
2491 #endif /* HAVE_SOCKETS */
2492 /* We used to try using getdomainname here,
2493 but NIIBE Yutaka <gniibe@etl.go.jp> says that
2494 getdomainname gets the NIS/YP domain which often is not the same
2495 as in Internet domain name. */
2496 #if 0 /* Turned off because sysinfo is not really likely to return the
2497 correct Internet domain. */
2498 #if (HAVE_SYSINFO && defined (SI_SRPC_DOMAIN))
2499 if (! index (hostname
, '.'))
2501 /* The hostname is not fully qualified. Append the domain name. */
2503 int hostlen
= strlen (hostname
);
2504 int domain_size
= 256;
2508 char *domain
= (char *) alloca (domain_size
+ 1);
2509 char *fqdn
= (char *) alloca (hostlen
+ 1 + domain_size
+ 1);
2510 int sys_domain_size
= sysinfo (SI_SRPC_DOMAIN
, domain
, domain_size
);
2511 if (sys_domain_size
<= 0)
2513 if (domain_size
< sys_domain_size
)
2515 domain_size
= sys_domain_size
;
2518 strcpy (fqdn
, hostname
);
2519 if (domain
[0] == '.')
2520 strcpy (fqdn
+ hostlen
, domain
);
2521 else if (domain
[0] != 0)
2523 fqdn
[hostlen
] = '.';
2524 strcpy (fqdn
+ hostlen
+ 1, domain
);
2530 #endif /* HAVE_SYSINFO && defined (SI_SRPC_DOMAIN) */
2532 Vsystem_name
= build_string (hostname
);
2533 #endif /* HAVE_GETHOSTNAME */
2538 for (p
= SDATA (Vsystem_name
); *p
; p
++)
2539 if (*p
== ' ' || *p
== '\t')
2546 #if !defined (HAVE_SELECT) || defined (BROKEN_SELECT_NON_X)
2548 #include "sysselect.h"
2551 #if defined (HAVE_X_WINDOWS) && !defined (HAVE_SELECT)
2552 /* Cause explanatory error message at compile time,
2553 since the select emulation is not good enough for X. */
2554 int *x
= &x_windows_lose_if_no_select_system_call
;
2557 /* Emulate as much as select as is possible under 4.1 and needed by Gnu Emacs
2558 * Only checks read descriptors.
2560 /* How long to wait between checking fds in select */
2561 #define SELECT_PAUSE 1
2564 /* For longjmp'ing back to read_input_waiting. */
2566 jmp_buf read_alarm_throw
;
2568 /* Nonzero if the alarm signal should throw back to read_input_waiting.
2569 The read_socket_hook function sets this to 1 while it is waiting. */
2571 int read_alarm_should_throw
;
2579 #else /* not BSD4_1 */
2580 signal (SIGALRM
, SIG_IGN
);
2581 #endif /* not BSD4_1 */
2582 SIGNAL_THREAD_CHECK (SIGALRM
);
2583 if (read_alarm_should_throw
)
2584 longjmp (read_alarm_throw
, 1);
2588 /* Only rfds are checked. */
2590 sys_select (nfds
, rfds
, wfds
, efds
, timeout
)
2592 SELECT_TYPE
*rfds
, *wfds
, *efds
;
2593 EMACS_TIME
*timeout
;
2595 /* XXX This needs to be updated for multi-tty support. Is there
2596 anybody who needs to emulate select these days? */
2601 extern int proc_buffered_char
[];
2602 #ifndef subprocesses
2603 int process_tick
= 0, update_tick
= 0;
2605 extern int process_tick
, update_tick
;
2609 #if defined (HAVE_SELECT) && defined (HAVE_X_WINDOWS)
2610 /* If we're using X, then the native select will work; we only need the
2611 emulation for non-X usage. */
2612 if (!NILP (Vinitial_window_system
))
2613 return select (nfds
, rfds
, wfds
, efds
, timeout
);
2615 timeoutval
= timeout
? EMACS_SECS (*timeout
) : 100000;
2616 local_timeout
= &timeoutval
;
2628 /* If we are looking only for the terminal, with no timeout,
2629 just read it and wait -- that's more efficient. */
2630 if (*local_timeout
== 100000 && process_tick
== update_tick
2631 && FD_ISSET (0, &orfds
))
2634 for (fd
= 1; fd
< nfds
; ++fd
)
2635 if (FD_ISSET (fd
, &orfds
))
2637 if (! detect_input_pending ())
2638 read_input_waiting ();
2644 /* Once a second, till the timer expires, check all the flagged read
2645 * descriptors to see if any input is available. If there is some then
2646 * set the corresponding bit in the return copy of rfds.
2650 register int to_check
, fd
;
2654 for (to_check
= nfds
, fd
= 0; --to_check
>= 0; fd
++)
2656 if (FD_ISSET (fd
, &orfds
))
2658 int avail
= 0, status
= 0;
2661 avail
= detect_input_pending (); /* Special keyboard handler */
2665 status
= ioctl (fd
, FIONREAD
, &avail
);
2666 #else /* no FIONREAD */
2667 /* Hoping it will return -1 if nothing available
2668 or 0 if all 0 chars requested are read. */
2669 if (proc_buffered_char
[fd
] >= 0)
2673 avail
= read (fd
, &buf
, 1);
2675 proc_buffered_char
[fd
] = buf
;
2677 #endif /* no FIONREAD */
2679 if (status
>= 0 && avail
> 0)
2687 if (*local_timeout
== 0 || ravail
!= 0 || process_tick
!= update_tick
)
2690 turn_on_atimers (0);
2691 signal (SIGALRM
, select_alarm
);
2693 alarm (SELECT_PAUSE
);
2695 /* Wait for a SIGALRM (or maybe a SIGTINT) */
2696 while (select_alarmed
== 0 && *local_timeout
!= 0
2697 && process_tick
== update_tick
)
2699 /* If we are interested in terminal input,
2700 wait by reading the terminal.
2701 That makes instant wakeup for terminal input at least. */
2702 if (FD_ISSET (0, &orfds
))
2704 read_input_waiting ();
2705 if (detect_input_pending ())
2711 (*local_timeout
) -= SELECT_PAUSE
;
2713 /* Reset the old alarm if there was one. */
2714 turn_on_atimers (1);
2716 if (*local_timeout
== 0) /* Stop on timer being cleared */
2721 #endif /* not WINDOWSNT */
2723 /* Read keyboard input into the standard buffer,
2724 waiting for at least one character. */
2727 read_input_waiting ()
2729 /* XXX This needs to be updated for multi-tty support. Is there
2730 anybody who needs to emulate select these days? */
2732 extern int quit_char
;
2734 if (read_socket_hook
)
2736 struct input_event hold_quit
;
2738 EVENT_INIT (hold_quit
);
2739 hold_quit
.kind
= NO_EVENT
;
2741 read_alarm_should_throw
= 0;
2742 if (! setjmp (read_alarm_throw
))
2743 nread
= (*read_socket_hook
) (0, 1, &hold_quit
);
2747 if (hold_quit
.kind
!= NO_EVENT
)
2748 kbd_buffer_store_event (&hold_quit
);
2752 struct input_event e
;
2754 nread
= read (fileno (stdin
), buf
, 1);
2757 /* Scan the chars for C-g and store them in kbd_buffer. */
2758 e
.kind
= ASCII_KEYSTROKE_EVENT
;
2759 e
.frame_or_window
= selected_frame
;
2761 for (i
= 0; i
< nread
; i
++)
2763 /* Convert chars > 0177 to meta events if desired.
2764 We do this under the same conditions that read_avail_input does. */
2765 if (read_socket_hook
== 0)
2767 /* If the user says she has a meta key, then believe her. */
2768 if (meta_key
== 1 && (buf
[i
] & 0x80))
2769 e
.modifiers
= meta_modifier
;
2774 XSETINT (e
.code
, buf
[i
]);
2775 kbd_buffer_store_event (&e
);
2776 /* Don't look at input that follows a C-g too closely.
2777 This reduces lossage due to autorepeat on C-g. */
2778 if (buf
[i
] == quit_char
)
2784 #if !defined (HAVE_SELECT) || defined (BROKEN_SELECT_NON_X)
2785 #define select sys_select
2788 #endif /* not HAVE_SELECT */
2789 #endif /* not VMS */
2790 #endif /* not MSDOS */
2799 lmode
= LINTRUP
| lmode
;
2800 ioctl (fd
, TIOCLSET
, &lmode
);
2809 lmode
= ~LINTRUP
& lmode
;
2810 ioctl (fd
, TIOCLSET
, &lmode
);
2820 interrupts_deferred
= 0;
2830 interrupts_deferred
= 1;
2833 /* still inside #ifdef BSD4_1 */
2836 int sigheld
; /* Mask of held signals */
2842 sigheld
|= sigbit (signum
);
2850 sigheld
|= sigbit (signum
);
2857 sigheld
&= ~sigbit (signum
);
2862 sigfree () /* Free all held signals */
2865 for (i
= 0; i
< NSIG
; i
++)
2866 if (sigheld
& sigbit (i
))
2874 return 1 << (i
- 1);
2876 #endif /* subprocesses */
2879 /* POSIX signals support - DJB */
2880 /* Anyone with POSIX signals should have ANSI C declarations */
2882 #ifdef POSIX_SIGNALS
2884 sigset_t empty_mask
, full_mask
;
2887 sys_signal (int signal_number
, signal_handler_t action
)
2889 struct sigaction new_action
, old_action
;
2890 sigemptyset (&new_action
.sa_mask
);
2891 new_action
.sa_handler
= action
;
2892 #if defined (SA_RESTART) && ! defined (BROKEN_SA_RESTART) && !defined(SYNC_INPUT)
2893 /* Emacs mostly works better with restartable system services. If this
2894 flag exists, we probably want to turn it on here.
2895 However, on some systems this resets the timeout of `select'
2896 which means that `select' never finishes if it keeps getting signals.
2897 BROKEN_SA_RESTART is defined on those systems. */
2898 /* It's not clear why the comment above says "mostly works better". --Stef
2899 When SYNC_INPUT is set, we don't want SA_RESTART because we need to poll
2900 for pending input so we need long-running syscalls to be interrupted
2901 after a signal that sets the interrupt_input_pending flag. */
2902 new_action
.sa_flags
= SA_RESTART
;
2904 new_action
.sa_flags
= 0;
2906 sigaction (signal_number
, &new_action
, &old_action
);
2907 return (old_action
.sa_handler
);
2911 /* If we're compiling with GCC, we don't need this function, since it
2912 can be written as a macro. */
2914 sys_sigmask (int sig
)
2917 sigemptyset (&mask
);
2918 sigaddset (&mask
, sig
);
2923 /* I'd like to have these guys return pointers to the mask storage in here,
2924 but there'd be trouble if the code was saving multiple masks. I'll be
2925 safe and pass the structure. It normally won't be more than 2 bytes
2929 sys_sigblock (sigset_t new_mask
)
2932 sigprocmask (SIG_BLOCK
, &new_mask
, &old_mask
);
2937 sys_sigunblock (sigset_t new_mask
)
2940 sigprocmask (SIG_UNBLOCK
, &new_mask
, &old_mask
);
2945 sys_sigsetmask (sigset_t new_mask
)
2948 sigprocmask (SIG_SETMASK
, &new_mask
, &old_mask
);
2952 #endif /* POSIX_SIGNALS */
2954 #if !defined HAVE_STRSIGNAL && !HAVE_DECL_SYS_SIGLIST
2955 static char *my_sys_siglist
[NSIG
];
2959 # define sys_siglist my_sys_siglist
2965 #ifdef POSIX_SIGNALS
2966 sigemptyset (&empty_mask
);
2967 sigfillset (&full_mask
);
2970 #if !defined HAVE_STRSIGNAL && !HAVE_DECL_SYS_SIGLIST
2974 sys_siglist
[SIGABRT
] = "Aborted";
2977 sys_siglist
[SIGAIO
] = "LAN I/O interrupt";
2980 sys_siglist
[SIGALRM
] = "Alarm clock";
2983 sys_siglist
[SIGBUS
] = "Bus error";
2986 sys_siglist
[SIGCLD
] = "Child status changed";
2989 sys_siglist
[SIGCHLD
] = "Child status changed";
2992 sys_siglist
[SIGCONT
] = "Continued";
2995 sys_siglist
[SIGDANGER
] = "Swap space dangerously low";
2998 sys_siglist
[SIGDGNOTIFY
] = "Notification message in queue";
3001 sys_siglist
[SIGEMT
] = "Emulation trap";
3004 sys_siglist
[SIGFPE
] = "Arithmetic exception";
3007 sys_siglist
[SIGFREEZE
] = "SIGFREEZE";
3010 sys_siglist
[SIGGRANT
] = "Monitor mode granted";
3013 sys_siglist
[SIGHUP
] = "Hangup";
3016 sys_siglist
[SIGILL
] = "Illegal instruction";
3019 sys_siglist
[SIGINT
] = "Interrupt";
3022 sys_siglist
[SIGIO
] = "I/O possible";
3025 sys_siglist
[SIGIOINT
] = "I/O intervention required";
3028 sys_siglist
[SIGIOT
] = "IOT trap";
3031 sys_siglist
[SIGKILL
] = "Killed";
3034 sys_siglist
[SIGLOST
] = "Resource lost";
3037 sys_siglist
[SIGLWP
] = "SIGLWP";
3040 sys_siglist
[SIGMSG
] = "Monitor mode data available";
3043 sys_siglist
[SIGWIND
] = "SIGPHONE";
3046 sys_siglist
[SIGPIPE
] = "Broken pipe";
3049 sys_siglist
[SIGPOLL
] = "Pollable event occurred";
3052 sys_siglist
[SIGPROF
] = "Profiling timer expired";
3055 sys_siglist
[SIGPTY
] = "PTY I/O interrupt";
3058 sys_siglist
[SIGPWR
] = "Power-fail restart";
3061 sys_siglist
[SIGQUIT
] = "Quit";
3064 sys_siglist
[SIGRETRACT
] = "Need to relinguish monitor mode";
3067 sys_siglist
[SIGSAK
] = "Secure attention";
3070 sys_siglist
[SIGSEGV
] = "Segmentation violation";
3073 sys_siglist
[SIGSOUND
] = "Sound completed";
3076 sys_siglist
[SIGSTOP
] = "Stopped (signal)";
3079 sys_siglist
[SIGSTP
] = "Stopped (user)";
3082 sys_siglist
[SIGSYS
] = "Bad argument to system call";
3085 sys_siglist
[SIGTERM
] = "Terminated";
3088 sys_siglist
[SIGTHAW
] = "SIGTHAW";
3091 sys_siglist
[SIGTRAP
] = "Trace/breakpoint trap";
3094 sys_siglist
[SIGTSTP
] = "Stopped (user)";
3097 sys_siglist
[SIGTTIN
] = "Stopped (tty input)";
3100 sys_siglist
[SIGTTOU
] = "Stopped (tty output)";
3103 sys_siglist
[SIGURG
] = "Urgent I/O condition";
3106 sys_siglist
[SIGUSR1
] = "User defined signal 1";
3109 sys_siglist
[SIGUSR2
] = "User defined signal 2";
3112 sys_siglist
[SIGVTALRM
] = "Virtual timer expired";
3115 sys_siglist
[SIGWAITING
] = "Process's LWPs are blocked";
3118 sys_siglist
[SIGWINCH
] = "Window size changed";
3121 sys_siglist
[SIGWIND
] = "SIGWIND";
3124 sys_siglist
[SIGXCPU
] = "CPU time limit exceeded";
3127 sys_siglist
[SIGXFSZ
] = "File size limit exceeded";
3130 #endif /* !defined HAVE_STRSIGNAL && !defined HAVE_DECL_SYS_SIGLIST */
3139 /* Figure out how many bits the system's random number generator uses.
3140 `random' and `lrand48' are assumed to return 31 usable bits.
3141 BSD `rand' returns a 31 bit value but the low order bits are unusable;
3142 so we'll shift it and treat it like the 15-bit USG `rand'. */
3146 # define RAND_BITS 31
3147 # else /* !HAVE_RANDOM */
3148 # ifdef HAVE_LRAND48
3149 # define RAND_BITS 31
3150 # define random lrand48
3151 # else /* !HAVE_LRAND48 */
3152 # define RAND_BITS 15
3153 # if RAND_MAX == 32767
3154 # define random rand
3155 # else /* RAND_MAX != 32767 */
3156 # if RAND_MAX == 2147483647
3157 # define random() (rand () >> 16)
3158 # else /* RAND_MAX != 2147483647 */
3160 # define random rand
3162 # define random() (rand () >> 16)
3164 # endif /* RAND_MAX != 2147483647 */
3165 # endif /* RAND_MAX != 32767 */
3166 # endif /* !HAVE_LRAND48 */
3167 # endif /* !HAVE_RANDOM */
3168 #endif /* !RAND_BITS */
3175 srandom ((unsigned int)arg
);
3177 # ifdef HAVE_LRAND48
3180 srand ((unsigned int)arg
);
3186 * Build a full Emacs-sized word out of whatever we've got.
3187 * This suffices even for a 64-bit architecture with a 15-bit rand.
3192 long val
= random ();
3193 #if VALBITS > RAND_BITS
3194 val
= (val
<< RAND_BITS
) ^ random ();
3195 #if VALBITS > 2*RAND_BITS
3196 val
= (val
<< RAND_BITS
) ^ random ();
3197 #if VALBITS > 3*RAND_BITS
3198 val
= (val
<< RAND_BITS
) ^ random ();
3199 #if VALBITS > 4*RAND_BITS
3200 val
= (val
<< RAND_BITS
) ^ random ();
3201 #endif /* need at least 5 */
3202 #endif /* need at least 4 */
3203 #endif /* need at least 3 */
3204 #endif /* need at least 2 */
3205 return val
& ((1L << VALBITS
) - 1);
3211 /* If any place else asks for the TERM variable,
3212 allow it to be overridden with the EMACS_TERM variable
3213 before attempting to translate the logical name TERM. As a last
3214 resort, ask for VAX C's special idea of the TERM variable. */
3221 static char buf
[256];
3222 static struct dsc$descriptor_s equiv
3223 = {sizeof (buf
), DSC$K_DTYPE_T
, DSC$K_CLASS_S
, buf
};
3224 static struct dsc$descriptor_s d_name
3225 = {0, DSC$K_DTYPE_T
, DSC$K_CLASS_S
, 0};
3228 if (!strcmp (name
, "TERM"))
3230 val
= (char *) getenv ("EMACS_TERM");
3235 d_name
.dsc$w_length
= strlen (name
);
3236 d_name
.dsc$a_pointer
= name
;
3237 if (LIB$
SYS_TRNLOG (&d_name
, &eqlen
, &equiv
) == 1)
3239 char *str
= (char *) xmalloc (eqlen
+ 1);
3240 bcopy (buf
, str
, eqlen
);
3242 /* This is a storage leak, but a pain to fix. With luck,
3243 no one will ever notice. */
3246 return (char *) getenv (name
);
3251 /* Since VMS doesn't believe in core dumps, the only way to debug this beast is
3252 to force a call on the debugger from within the image. */
3256 reset_all_sys_modes ();
3257 LIB$
SIGNAL (SS$_DEBUG
);
3263 #ifdef LINK_CRTL_SHARE
3264 #ifdef SHARABLE_LIB_BUG
3265 /* Variables declared noshare and initialized in sharable libraries
3266 cannot be shared. The VMS linker incorrectly forces you to use a private
3267 version which is uninitialized... If not for this "feature", we
3268 could use the C library definition of sys_nerr and sys_errlist. */
3270 char *sys_errlist
[] =
3274 "no such file or directory",
3276 "interrupted system call",
3278 "no such device or address",
3279 "argument list too long",
3280 "exec format error",
3283 "no more processes",
3284 "not enough memory",
3285 "permission denied",
3287 "block device required",
3288 "mount devices busy",
3290 "cross-device link",
3295 "file table overflow",
3296 "too many open files",
3300 "no space left on device",
3302 "read-only file system",
3308 "vax/vms specific error code nontranslatable error"
3310 #endif /* SHARABLE_LIB_BUG */
3311 #endif /* LINK_CRTL_SHARE */
3314 #ifndef HAVE_STRERROR
3320 extern char *sys_errlist
[];
3321 extern int sys_nerr
;
3323 if (errnum
>= 0 && errnum
< sys_nerr
)
3324 return sys_errlist
[errnum
];
3325 return (char *) "Unknown error";
3327 #endif /* not WINDOWSNT */
3328 #endif /* ! HAVE_STRERROR */
3331 emacs_open (path
, oflag
, mode
)
3335 register int rtnval
;
3338 if (oflag
& O_CREAT
)
3339 return creat (path
, mode
);
3342 while ((rtnval
= open (path
, oflag
, mode
)) == -1
3343 && (errno
== EINTR
))
3353 register int rtnval
;
3355 #if defined (MAC_OSX) && defined (HAVE_CARBON)
3357 extern int mac_try_close_socket
P_ ((int));
3359 if (mac_try_close_socket (fd
))
3364 while ((rtnval
= close (fd
)) == -1
3365 && (errno
== EINTR
))
3368 /* If close is interrupted SunOS 4.1 may or may not have closed the
3369 file descriptor. If it did the second close will fail with
3370 errno = EBADF. That means we have succeeded. */
3371 if (rtnval
== -1 && did_retry
&& errno
== EBADF
)
3378 emacs_read (fildes
, buf
, nbyte
)
3383 register int rtnval
;
3385 while ((rtnval
= read (fildes
, buf
, nbyte
)) == -1
3386 && (errno
== EINTR
))
3392 emacs_write (fildes
, buf
, nbyte
)
3397 register int rtnval
, bytes_written
;
3403 rtnval
= write (fildes
, buf
, nbyte
);
3410 /* I originally used `QUIT' but that might causes files to
3411 be truncated if you hit C-g in the middle of it. --Stef */
3412 if (interrupt_input_pending
)
3413 handle_async_input ();
3418 return (bytes_written
? bytes_written
: -1);
3423 bytes_written
+= rtnval
;
3425 return (bytes_written
);
3430 * All of the following are for USG.
3432 * On USG systems the system calls are INTERRUPTIBLE by signals
3433 * that the user program has elected to catch. Thus the system call
3434 * must be retried in these cases. To handle this without massive
3435 * changes in the source code, we remap the standard system call names
3436 * to names for our own functions in sysdep.c that do the system call
3437 * with retries. Actually, for portability reasons, it is good
3438 * programming practice, as this example shows, to limit all actual
3439 * system calls to a single occurrence in the source. Sure, this
3440 * adds an extra level of function call overhead but it is almost
3441 * always negligible. Fred Fish, Unisoft Systems Inc.
3445 * Warning, this function may not duplicate 4.2 action properly
3446 * under error conditions.
3450 /* In 4.1, param.h fails to define this. */
3451 #define MAXPATHLEN 1024
3460 char *npath
, *spath
;
3461 extern char *getcwd ();
3463 BLOCK_INPUT
; /* getcwd uses malloc */
3464 spath
= npath
= getcwd ((char *) 0, MAXPATHLEN
);
3470 /* On Altos 3068, getcwd can return @hostname/dir, so discard
3471 up to first slash. Should be harmless on other systems. */
3472 while (*npath
&& *npath
!= '/')
3474 strcpy (pathname
, npath
);
3475 free (spath
); /* getcwd uses malloc */
3480 #endif /* HAVE_GETWD */
3483 * Emulate rename using unlink/link. Note that this is
3484 * only partially correct. Also, doesn't enforce restriction
3485 * that files be of same type (regular->regular, dir->dir, etc).
3494 if (access (from
, 0) == 0)
3497 if (link (from
, to
) == 0)
3498 if (unlink (from
) == 0)
3510 /* HPUX curses library references perror, but as far as we know
3511 it won't be called. Anyway this definition will do for now. */
3517 #endif /* not HAVE_PERROR */
3523 * Emulate BSD dup2. First close newd if it already exists.
3524 * Then, attempt to dup oldd. If not successful, call dup2 recursively
3525 * until we are, then close the unsuccessful ones.
3532 register int fd
, ret
;
3537 return fcntl (oldd
, F_DUPFD
, newd
);
3544 ret
= dup2 (old
,new);
3550 #endif /* not HAVE_DUP2 */
3553 * Gettimeofday. Simulate as much as possible. Only accurate
3554 * to nearest second. Emacs doesn't use tzp so ignore it for now.
3555 * Only needed when subprocesses are defined.
3560 #ifndef HAVE_GETTIMEOFDAY
3565 gettimeofday (tp
, tzp
)
3567 struct timezone
*tzp
;
3569 extern long time ();
3571 tp
->tv_sec
= time ((long *)0);
3574 tzp
->tz_minuteswest
= -1;
3581 #endif /* subprocess && !HAVE_GETTIMEOFDAY && HAVE_TIMEVAL && !VMS */
3584 * This function will go away as soon as all the stubs fixed. (fnf)
3591 printf ("%s not yet implemented\r\n", badfunc
);
3592 reset_all_sys_modes ();
3598 /* Directory routines for systems that don't have them. */
3600 #ifdef SYSV_SYSTEM_DIR
3604 #if defined (BROKEN_CLOSEDIR) || !defined (HAVE_CLOSEDIR)
3608 register DIR *dirp
; /* stream from opendir */
3612 rtnval
= emacs_close (dirp
->dd_fd
);
3614 /* Some systems (like Solaris) allocate the buffer and the DIR all
3615 in one block. Why in the world are we freeing this ourselves
3617 #if ! (defined (sun) && defined (USG5_4))
3618 xfree ((char *) dirp
->dd_buf
); /* directory block defined in <dirent.h> */
3620 xfree ((char *) dirp
);
3624 #endif /* BROKEN_CLOSEDIR or not HAVE_CLOSEDIR */
3625 #endif /* SYSV_SYSTEM_DIR */
3627 #ifdef NONSYSTEM_DIR_LIBRARY
3631 char *filename
; /* name of directory */
3633 register DIR *dirp
; /* -> malloc'ed storage */
3634 register int fd
; /* file descriptor for read */
3635 struct stat sbuf
; /* result of fstat */
3637 fd
= emacs_open (filename
, O_RDONLY
, 0);
3642 if (fstat (fd
, &sbuf
) < 0
3643 || (sbuf
.st_mode
& S_IFMT
) != S_IFDIR
3644 || (dirp
= (DIR *) xmalloc (sizeof (DIR))) == 0)
3648 return 0; /* bad luck today */
3653 dirp
->dd_loc
= dirp
->dd_size
= 0; /* refill needed */
3660 register DIR *dirp
; /* stream from opendir */
3662 emacs_close (dirp
->dd_fd
);
3663 xfree ((char *) dirp
);
3671 ino_t od_ino
; /* inode */
3672 char od_name
[DIRSIZ
]; /* filename */
3674 #endif /* not VMS */
3676 struct direct dir_static
; /* simulated directory contents */
3681 register DIR *dirp
; /* stream from opendir */
3684 register struct olddir
*dp
; /* -> directory data */
3686 register struct dir$_name
*dp
; /* -> directory data */
3687 register struct dir$_version
*dv
; /* -> version data */
3692 if (dirp
->dd_loc
>= dirp
->dd_size
)
3693 dirp
->dd_loc
= dirp
->dd_size
= 0;
3695 if (dirp
->dd_size
== 0 /* refill buffer */
3696 && (dirp
->dd_size
= emacs_read (dirp
->dd_fd
, dirp
->dd_buf
, DIRBLKSIZ
)) <= 0)
3700 dp
= (struct olddir
*) &dirp
->dd_buf
[dirp
->dd_loc
];
3701 dirp
->dd_loc
+= sizeof (struct olddir
);
3703 if (dp
->od_ino
!= 0) /* not deleted entry */
3705 dir_static
.d_ino
= dp
->od_ino
;
3706 strncpy (dir_static
.d_name
, dp
->od_name
, DIRSIZ
);
3707 dir_static
.d_name
[DIRSIZ
] = '\0';
3708 dir_static
.d_namlen
= strlen (dir_static
.d_name
);
3709 dir_static
.d_reclen
= sizeof (struct direct
)
3711 + dir_static
.d_namlen
- dir_static
.d_namlen
% 4;
3712 return &dir_static
; /* -> simulated structure */
3715 dp
= (struct dir$_name
*) dirp
->dd_buf
;
3716 if (dirp
->dd_loc
== 0)
3717 dirp
->dd_loc
= (dp
->dir$b_namecount
&1) ? dp
->dir$b_namecount
+ 1
3718 : dp
->dir$b_namecount
;
3719 dv
= (struct dir$_version
*)&dp
->dir$t_name
[dirp
->dd_loc
];
3720 dir_static
.d_ino
= dv
->dir$w_fid_num
;
3721 dir_static
.d_namlen
= dp
->dir$b_namecount
;
3722 dir_static
.d_reclen
= sizeof (struct direct
)
3724 + dir_static
.d_namlen
- dir_static
.d_namlen
% 4;
3725 strncpy (dir_static
.d_name
, dp
->dir$t_name
, dp
->dir$b_namecount
);
3726 dir_static
.d_name
[dir_static
.d_namlen
] = '\0';
3727 dirp
->dd_loc
= dirp
->dd_size
; /* only one record at a time */
3734 /* readdirver is just like readdir except it returns all versions of a file
3735 as separate entries. */
3740 register DIR *dirp
; /* stream from opendir */
3742 register struct dir$_name
*dp
; /* -> directory data */
3743 register struct dir$_version
*dv
; /* -> version data */
3745 if (dirp
->dd_loc
>= dirp
->dd_size
- sizeof (struct dir$_name
))
3746 dirp
->dd_loc
= dirp
->dd_size
= 0;
3748 if (dirp
->dd_size
== 0 /* refill buffer */
3749 && (dirp
->dd_size
= sys_read (dirp
->dd_fd
, dirp
->dd_buf
, DIRBLKSIZ
)) <= 0)
3752 dp
= (struct dir$_name
*) dirp
->dd_buf
;
3753 if (dirp
->dd_loc
== 0)
3754 dirp
->dd_loc
= (dp
->dir$b_namecount
& 1) ? dp
->dir$b_namecount
+ 1
3755 : dp
->dir$b_namecount
;
3756 dv
= (struct dir$_version
*) &dp
->dir$t_name
[dirp
->dd_loc
];
3757 strncpy (dir_static
.d_name
, dp
->dir$t_name
, dp
->dir$b_namecount
);
3758 sprintf (&dir_static
.d_name
[dp
->dir$b_namecount
], ";%d", dv
->dir$w_version
);
3759 dir_static
.d_namlen
= strlen (dir_static
.d_name
);
3760 dir_static
.d_ino
= dv
->dir$w_fid_num
;
3761 dir_static
.d_reclen
= sizeof (struct direct
) - MAXNAMLEN
+ 3
3762 + dir_static
.d_namlen
- dir_static
.d_namlen
% 4;
3763 dirp
->dd_loc
= ((char *) (++dv
) - dp
->dir$t_name
);
3769 #endif /* NONSYSTEM_DIR_LIBRARY */
3773 set_file_times (filename
, atime
, mtime
)
3774 const char *filename
;
3775 EMACS_TIME atime
, mtime
;
3778 struct timeval tv
[2];
3781 return utimes (filename
, tv
);
3782 #else /* not HAVE_UTIMES */
3784 utb
.actime
= EMACS_SECS (atime
);
3785 utb
.modtime
= EMACS_SECS (mtime
);
3786 return utime (filename
, &utb
);
3787 #endif /* not HAVE_UTIMES */
3790 /* mkdir and rmdir functions, for systems which don't have them. */
3794 * Written by Robert Rother, Mariah Corporation, August 1985.
3796 * If you want it, it's yours. All I ask in return is that if you
3797 * figure out how to do this in a Bourne Shell script you send me
3799 * sdcsvax!rmr or rmr@uscd
3801 * Severely hacked over by John Gilmore to make a 4.2BSD compatible
3802 * subroutine. 11Mar86; hoptoad!gnu
3804 * Modified by rmtodd@uokmax 6-28-87 -- when making an already existing dir,
3805 * subroutine didn't return EEXIST. It does now.
3811 #ifdef MKDIR_PROTOTYPE
3815 mkdir (dpath
, dmode
)
3820 int cpid
, status
, fd
;
3821 struct stat statbuf
;
3823 if (stat (dpath
, &statbuf
) == 0)
3825 errno
= EEXIST
; /* Stat worked, so it already exists */
3829 /* If stat fails for a reason other than non-existence, return error */
3830 if (errno
!= ENOENT
)
3833 synch_process_alive
= 1;
3834 switch (cpid
= fork ())
3837 case -1: /* Error in fork */
3838 return (-1); /* Errno is set already */
3840 case 0: /* Child process */
3842 * Cheap hack to set mode of new directory. Since this
3843 * child process is going away anyway, we zap its umask.
3844 * FIXME, this won't suffice to set SUID, SGID, etc. on this
3845 * directory. Does anybody care?
3847 status
= umask (0); /* Get current umask */
3848 status
= umask (status
| (0777 & ~dmode
)); /* Set for mkdir */
3849 fd
= emacs_open ("/dev/null", O_RDWR
, 0);
3856 execl ("/bin/mkdir", "mkdir", dpath
, (char *) 0);
3857 _exit (-1); /* Can't exec /bin/mkdir */
3859 default: /* Parent process */
3860 wait_for_termination (cpid
);
3863 if (synch_process_death
!= 0 || synch_process_retcode
!= 0
3864 || synch_process_termsig
!= 0)
3866 errno
= EIO
; /* We don't know why, but */
3867 return -1; /* /bin/mkdir failed */
3872 #endif /* not HAVE_MKDIR */
3879 int cpid
, status
, fd
;
3880 struct stat statbuf
;
3882 if (stat (dpath
, &statbuf
) != 0)
3884 /* Stat just set errno. We don't have to */
3888 synch_process_alive
= 1;
3889 switch (cpid
= fork ())
3892 case -1: /* Error in fork */
3893 return (-1); /* Errno is set already */
3895 case 0: /* Child process */
3896 fd
= emacs_open ("/dev/null", O_RDWR
, 0);
3903 execl ("/bin/rmdir", "rmdir", dpath
, (char *) 0);
3904 _exit (-1); /* Can't exec /bin/rmdir */
3906 default: /* Parent process */
3907 wait_for_termination (cpid
);
3910 if (synch_process_death
!= 0 || synch_process_retcode
!= 0
3911 || synch_process_termsig
!= 0)
3913 errno
= EIO
; /* We don't know why, but */
3914 return -1; /* /bin/rmdir failed */
3919 #endif /* !HAVE_RMDIR */
3923 /* Functions for VMS */
3929 /* Return as a string the VMS error string pertaining to STATUS.
3930 Reuses the same static buffer each time it is called. */
3934 int status
; /* VMS status code */
3938 static char buf
[257];
3940 bufadr
[0] = sizeof buf
- 1;
3941 bufadr
[1] = (int) buf
;
3942 if (! (SYS$
GETMSG (status
, &len
, bufadr
, 0x1, 0) & 1))
3943 return "untranslatable VMS error status";
3951 /* The following is necessary because 'access' emulation by VMS C (2.0) does
3952 * not work correctly. (It also doesn't work well in version 2.3.)
3957 #define DESCRIPTOR(name,string) struct dsc$descriptor_s name = \
3958 { strlen (string), DSC$K_DTYPE_T, DSC$K_CLASS_S, string }
3962 unsigned short s_buflen
;
3963 unsigned short s_code
;
3965 unsigned short *s_retlenadr
;
3969 #define buflen s.s_buflen
3970 #define code s.s_code
3971 #define bufadr s.s_bufadr
3972 #define retlenadr s.s_retlenadr
3974 #define R_OK 4 /* test for read permission */
3975 #define W_OK 2 /* test for write permission */
3976 #define X_OK 1 /* test for execute (search) permission */
3977 #define F_OK 0 /* test for presence of file */
3980 sys_access (path
, mode
)
3984 static char *user
= NULL
;
3987 /* translate possible directory spec into .DIR file name, so brain-dead
3988 * access can treat the directory like a file. */
3989 if (directory_file_name (path
, dir_fn
))
3993 return access (path
, mode
);
3994 if (user
== NULL
&& (user
= (char *) getenv ("USER")) == NULL
)
4000 unsigned short int dummy
;
4002 static int constant
= ACL$C_FILE
;
4003 DESCRIPTOR (path_desc
, path
);
4004 DESCRIPTOR (user_desc
, user
);
4008 if ((mode
& X_OK
) && ((stat
= access (path
, mode
)) < 0 || mode
== X_OK
))
4011 acces
|= CHP$M_READ
;
4013 acces
|= CHP$M_WRITE
;
4014 itemlst
[0].buflen
= sizeof (int);
4015 itemlst
[0].code
= CHP$_FLAGS
;
4016 itemlst
[0].bufadr
= (char *) &flags
;
4017 itemlst
[0].retlenadr
= &dummy
;
4018 itemlst
[1].buflen
= sizeof (int);
4019 itemlst
[1].code
= CHP$_ACCESS
;
4020 itemlst
[1].bufadr
= (char *) &acces
;
4021 itemlst
[1].retlenadr
= &dummy
;
4022 itemlst
[2].end
= CHP$_END
;
4023 stat
= SYS$
CHECK_ACCESS (&constant
, &path_desc
, &user_desc
, itemlst
);
4024 return stat
== SS$_NORMAL
? 0 : -1;
4028 #else /* not VMS4_4 */
4031 #define ACE$M_WRITE 2
4032 #define ACE$C_KEYID 1
4034 static unsigned short memid
, grpid
;
4035 static unsigned int uic
;
4037 /* Called from init_sys_modes, so it happens not very often
4038 but at least each time Emacs is loaded. */
4040 sys_access_reinit ()
4046 sys_access (filename
, type
)
4052 int status
, size
, i
, typecode
, acl_controlled
;
4053 unsigned int *aclptr
, *aclend
, aclbuf
[60];
4054 union prvdef prvmask
;
4056 /* Get UIC and GRP values for protection checking. */
4059 status
= LIB$
GETJPI (&JPI$_UIC
, 0, 0, &uic
, 0, 0);
4062 memid
= uic
& 0xFFFF;
4066 if (type
!= 2) /* not checking write access */
4067 return access (filename
, type
);
4069 /* Check write protection. */
4071 #define CHECKPRIV(bit) (prvmask.bit)
4072 #define WRITABLE(field) (! ((xab.xab$w_pro >> field) & XAB$M_NOWRITE))
4074 /* Find privilege bits */
4075 status
= SYS$
SETPRV (0, 0, 0, prvmask
);
4077 error ("Unable to find privileges: %s", vmserrstr (status
));
4078 if (CHECKPRIV (PRV$V_BYPASS
))
4079 return 0; /* BYPASS enabled */
4081 fab
.fab$b_fac
= FAB$M_GET
;
4082 fab
.fab$l_fna
= filename
;
4083 fab
.fab$b_fns
= strlen (filename
);
4084 fab
.fab$l_xab
= &xab
;
4085 xab
= cc$rms_xabpro
;
4086 xab
.xab$l_aclbuf
= aclbuf
;
4087 xab
.xab$w_aclsiz
= sizeof (aclbuf
);
4088 status
= SYS$
OPEN (&fab
, 0, 0);
4091 SYS$
CLOSE (&fab
, 0, 0);
4092 /* Check system access */
4093 if (CHECKPRIV (PRV$V_SYSPRV
) && WRITABLE (XAB$V_SYS
))
4095 /* Check ACL entries, if any */
4097 if (xab
.xab$w_acllen
> 0)
4100 aclend
= &aclbuf
[xab
.xab$w_acllen
/ 4];
4101 while (*aclptr
&& aclptr
< aclend
)
4103 size
= (*aclptr
& 0xff) / 4;
4104 typecode
= (*aclptr
>> 8) & 0xff;
4105 if (typecode
== ACE$C_KEYID
)
4106 for (i
= size
- 1; i
> 1; i
--)
4107 if (aclptr
[i
] == uic
)
4110 if (aclptr
[1] & ACE$M_WRITE
)
4111 return 0; /* Write access through ACL */
4113 aclptr
= &aclptr
[size
];
4115 if (acl_controlled
) /* ACL specified, prohibits write access */
4118 /* No ACL entries specified, check normal protection */
4119 if (WRITABLE (XAB$V_WLD
)) /* World writable */
4121 if (WRITABLE (XAB$V_GRP
) &&
4122 (unsigned short) (xab
.xab$l_uic
>> 16) == grpid
)
4123 return 0; /* Group writable */
4124 if (WRITABLE (XAB$V_OWN
) &&
4125 (xab
.xab$l_uic
& 0xFFFF) == memid
)
4126 return 0; /* Owner writable */
4128 return -1; /* Not writable */
4130 #endif /* not VMS4_4 */
4133 static char vtbuf
[NAM$C_MAXRSS
+1];
4135 /* translate a vms file spec to a unix path */
4137 sys_translate_vms (vfile
)
4148 /* leading device or logical name is a root directory */
4149 if (p
= strchr (vfile
, ':'))
4158 if (*p
== '[' || *p
== '<')
4160 while (*++vfile
!= *p
+ 2)
4164 if (vfile
[-1] == *p
)
4187 static char utbuf
[NAM$C_MAXRSS
+1];
4189 /* translate a unix path to a VMS file spec */
4191 sys_translate_unix (ufile
)
4214 if (index (&ufile
[1], '/'))
4221 if (index (&ufile
[1], '/'))
4228 if (strncmp (ufile
, "./", 2) == 0)
4235 ufile
++; /* skip the dot */
4236 if (index (&ufile
[1], '/'))
4241 else if (strncmp (ufile
, "../", 3) == 0)
4249 ufile
+= 2; /* skip the dots */
4250 if (index (&ufile
[1], '/'))
4275 extern char *getcwd ();
4277 #define MAXPATHLEN 1024
4279 ptr
= xmalloc (MAXPATHLEN
);
4280 val
= getcwd (ptr
, MAXPATHLEN
);
4286 strcpy (pathname
, ptr
);
4295 long item_code
= JPI$_OWNER
;
4296 unsigned long parent_id
;
4299 if (((status
= LIB$
GETJPI (&item_code
, 0, 0, &parent_id
)) & 1) == 0)
4302 vaxc$errno
= status
;
4312 return (getgid () << 16) | getuid ();
4317 sys_read (fildes
, buf
, nbyte
)
4322 return read (fildes
, buf
, (nbyte
< MAXIOSIZE
? nbyte
: MAXIOSIZE
));
4327 sys_write (fildes
, buf
, nbyte
)
4332 register int nwrote
, rtnval
= 0;
4334 while (nbyte
> MAXIOSIZE
&& (nwrote
= write (fildes
, buf
, MAXIOSIZE
)) > 0) {
4340 return rtnval
? rtnval
: -1;
4341 if ((nwrote
= write (fildes
, buf
, nbyte
)) < 0)
4342 return rtnval
? rtnval
: -1;
4343 return (rtnval
+ nwrote
);
4348 * VAX/VMS VAX C RTL really loses. It insists that records
4349 * end with a newline (carriage return) character, and if they
4350 * don't it adds one (nice of it isn't it!)
4352 * Thus we do this stupidity below.
4357 sys_write (fildes
, buf
, nbytes
)
4360 unsigned int nbytes
;
4367 fstat (fildes
, &st
);
4373 /* Handle fixed-length files with carriage control. */
4374 if (st
.st_fab_rfm
== FAB$C_FIX
4375 && ((st
.st_fab_rat
& (FAB$M_FTN
| FAB$M_CR
)) != 0))
4377 len
= st
.st_fab_mrs
;
4378 retval
= write (fildes
, p
, min (len
, nbytes
));
4381 retval
++; /* This skips the implied carriage control */
4385 e
= p
+ min (MAXIOSIZE
, nbytes
) - 1;
4386 while (*e
!= '\n' && e
> p
) e
--;
4387 if (p
== e
) /* Ok.. so here we add a newline... sigh. */
4388 e
= p
+ min (MAXIOSIZE
, nbytes
) - 1;
4390 retval
= write (fildes
, p
, len
);
4401 /* Create file NEW copying its attributes from file OLD. If
4402 OLD is 0 or does not exist, create based on the value of
4405 /* Protection value the file should ultimately have.
4406 Set by create_copy_attrs, and use by rename_sansversions. */
4407 static unsigned short int fab_final_pro
;
4410 creat_copy_attrs (old
, new)
4413 struct FAB fab
= cc$rms_fab
;
4414 struct XABPRO xabpro
;
4415 char aclbuf
[256]; /* Choice of size is arbitrary. See below. */
4416 extern int vms_stmlf_recfm
;
4420 fab
.fab$b_fac
= FAB$M_GET
;
4421 fab
.fab$l_fna
= old
;
4422 fab
.fab$b_fns
= strlen (old
);
4423 fab
.fab$l_xab
= (char *) &xabpro
;
4424 xabpro
= cc$rms_xabpro
;
4425 xabpro
.xab$l_aclbuf
= aclbuf
;
4426 xabpro
.xab$w_aclsiz
= sizeof aclbuf
;
4427 /* Call $OPEN to fill in the fab & xabpro fields. */
4428 if (SYS$
OPEN (&fab
, 0, 0) & 1)
4430 SYS$
CLOSE (&fab
, 0, 0);
4431 fab
.fab$l_alq
= 0; /* zero the allocation quantity */
4432 if (xabpro
.xab$w_acllen
> 0)
4434 if (xabpro
.xab$w_acllen
> sizeof aclbuf
)
4435 /* If the acl buffer was too short, redo open with longer one.
4436 Wouldn't need to do this if there were some system imposed
4437 limit on the size of an ACL, but I can't find any such. */
4439 xabpro
.xab$l_aclbuf
= (char *) alloca (xabpro
.xab$w_acllen
);
4440 xabpro
.xab$w_aclsiz
= xabpro
.xab$w_acllen
;
4441 if (SYS$
OPEN (&fab
, 0, 0) & 1)
4442 SYS$
CLOSE (&fab
, 0, 0);
4448 xabpro
.xab$l_aclbuf
= 0;
4453 fab
.fab$l_fna
= new;
4454 fab
.fab$b_fns
= strlen (new);
4458 fab
.fab$b_rfm
= vms_stmlf_recfm
? FAB$C_STMLF
: FAB$C_VAR
;
4459 fab
.fab$b_rat
= FAB$M_CR
;
4462 /* Set the file protections such that we will be able to manipulate
4463 this file. Once we are done writing and renaming it, we will set
4464 the protections back. */
4466 fab_final_pro
= xabpro
.xab$w_pro
;
4468 SYS$
SETDFPROT (0, &fab_final_pro
);
4469 xabpro
.xab$w_pro
&= 0xff0f; /* set O:rewd for now. This is set back later. */
4471 /* Create the new file with either default attrs or attrs copied
4473 if (!(SYS$
CREATE (&fab
, 0, 0) & 1))
4475 SYS$
CLOSE (&fab
, 0, 0);
4476 /* As this is a "replacement" for creat, return a file descriptor
4477 opened for writing. */
4478 return open (new, O_WRONLY
);
4483 #include <varargs.h>
4486 #define va_count(X) ((X) = *(((int *) &(va_alist)) - 1))
4491 sys_creat (va_alist
)
4494 va_list list_incrementer
;
4497 int rfd
; /* related file descriptor */
4498 int fd
; /* Our new file descriptor */
4505 extern int vms_stmlf_recfm
;
4508 va_start (list_incrementer
);
4509 name
= va_arg (list_incrementer
, char *);
4510 mode
= va_arg (list_incrementer
, int);
4512 rfd
= va_arg (list_incrementer
, int);
4513 va_end (list_incrementer
);
4516 /* Use information from the related file descriptor to set record
4517 format of the newly created file. */
4518 fstat (rfd
, &st_buf
);
4519 switch (st_buf
.st_fab_rfm
)
4522 strcpy (rfm
, "rfm = fix");
4523 sprintf (mrs
, "mrs = %d", st_buf
.st_fab_mrs
);
4524 strcpy (rat
, "rat = ");
4525 if (st_buf
.st_fab_rat
& FAB$M_CR
)
4527 else if (st_buf
.st_fab_rat
& FAB$M_FTN
)
4528 strcat (rat
, "ftn");
4529 else if (st_buf
.st_fab_rat
& FAB$M_PRN
)
4530 strcat (rat
, "prn");
4531 if (st_buf
.st_fab_rat
& FAB$M_BLK
)
4532 if (st_buf
.st_fab_rat
& (FAB$M_CR
|FAB$M_FTN
|FAB$M_PRN
))
4533 strcat (rat
, ", blk");
4535 strcat (rat
, "blk");
4536 return creat (name
, 0, rfm
, rat
, mrs
);
4539 strcpy (rfm
, "rfm = vfc");
4540 sprintf (fsz
, "fsz = %d", st_buf
.st_fab_fsz
);
4541 strcpy (rat
, "rat = ");
4542 if (st_buf
.st_fab_rat
& FAB$M_CR
)
4544 else if (st_buf
.st_fab_rat
& FAB$M_FTN
)
4545 strcat (rat
, "ftn");
4546 else if (st_buf
.st_fab_rat
& FAB$M_PRN
)
4547 strcat (rat
, "prn");
4548 if (st_buf
.st_fab_rat
& FAB$M_BLK
)
4549 if (st_buf
.st_fab_rat
& (FAB$M_CR
|FAB$M_FTN
|FAB$M_PRN
))
4550 strcat (rat
, ", blk");
4552 strcat (rat
, "blk");
4553 return creat (name
, 0, rfm
, rat
, fsz
);
4556 strcpy (rfm
, "rfm = stm");
4560 strcpy (rfm
, "rfm = stmcr");
4564 strcpy (rfm
, "rfm = stmlf");
4568 strcpy (rfm
, "rfm = udf");
4572 strcpy (rfm
, "rfm = var");
4575 strcpy (rat
, "rat = ");
4576 if (st_buf
.st_fab_rat
& FAB$M_CR
)
4578 else if (st_buf
.st_fab_rat
& FAB$M_FTN
)
4579 strcat (rat
, "ftn");
4580 else if (st_buf
.st_fab_rat
& FAB$M_PRN
)
4581 strcat (rat
, "prn");
4582 if (st_buf
.st_fab_rat
& FAB$M_BLK
)
4583 if (st_buf
.st_fab_rat
& (FAB$M_CR
|FAB$M_FTN
|FAB$M_PRN
))
4584 strcat (rat
, ", blk");
4586 strcat (rat
, "blk");
4590 strcpy (rfm
, vms_stmlf_recfm
? "rfm = stmlf" : "rfm=var");
4591 strcpy (rat
, "rat=cr");
4593 /* Until the VAX C RTL fixes the many bugs with modes, always use
4594 mode 0 to get the user's default protection. */
4595 fd
= creat (name
, 0, rfm
, rat
);
4596 if (fd
< 0 && errno
== EEXIST
)
4598 if (unlink (name
) < 0)
4599 report_file_error ("delete", build_string (name
));
4600 fd
= creat (name
, 0, rfm
, rat
);
4606 /* fwrite to stdout is S L O W. Speed it up by using fputc...*/
4608 sys_fwrite (ptr
, size
, num
, fp
)
4609 register char * ptr
;
4612 register int tot
= num
* size
;
4620 * The VMS C library routine creat actually creates a new version of an
4621 * existing file rather than truncating the old version. There are times
4622 * when this is not the desired behavior, for instance, when writing an
4623 * auto save file (you only want one version), or when you don't have
4624 * write permission in the directory containing the file (but the file
4625 * itself is writable). Hence this routine, which is equivalent to
4626 * "close (creat (fn, 0));" on Unix if fn already exists.
4632 struct FAB xfab
= cc$rms_fab
;
4633 struct RAB xrab
= cc$rms_rab
;
4636 xfab
.fab$l_fop
= FAB$M_TEF
; /* free allocated but unused blocks on close */
4637 xfab
.fab$b_fac
= FAB$M_TRN
| FAB$M_GET
; /* allow truncate and get access */
4638 xfab
.fab$b_shr
= FAB$M_NIL
; /* allow no sharing - file must be locked */
4639 xfab
.fab$l_fna
= fn
;
4640 xfab
.fab$b_fns
= strlen (fn
);
4641 xfab
.fab$l_dna
= ";0"; /* default to latest version of the file */
4643 xrab
.rab$l_fab
= &xfab
;
4645 /* This gibberish opens the file, positions to the first record, and
4646 deletes all records from there until the end of file. */
4647 if ((SYS$
OPEN (&xfab
) & 01) == 01)
4649 if ((SYS$
CONNECT (&xrab
) & 01) == 01 &&
4650 (SYS$
FIND (&xrab
) & 01) == 01 &&
4651 (SYS$
TRUNCATE (&xrab
) & 01) == 01)
4662 /* Define this symbol to actually read SYSUAF.DAT. This requires either
4663 SYSPRV or a readable SYSUAF.DAT. */
4669 * Routine to read the VMS User Authorization File and return
4670 * a specific user's record.
4673 static struct UAF retuaf
;
4676 get_uaf_name (uname
)
4683 uaf_fab
= cc$rms_fab
;
4684 uaf_rab
= cc$rms_rab
;
4685 /* initialize fab fields */
4686 uaf_fab
.fab$l_fna
= "SYS$SYSTEM:SYSUAF.DAT";
4687 uaf_fab
.fab$b_fns
= 21;
4688 uaf_fab
.fab$b_fac
= FAB$M_GET
;
4689 uaf_fab
.fab$b_org
= FAB$C_IDX
;
4690 uaf_fab
.fab$b_shr
= FAB$M_GET
|FAB$M_PUT
|FAB$M_UPD
|FAB$M_DEL
;
4691 /* initialize rab fields */
4692 uaf_rab
.rab$l_fab
= &uaf_fab
;
4693 /* open the User Authorization File */
4694 status
= SYS$
OPEN (&uaf_fab
);
4698 vaxc$errno
= status
;
4701 status
= SYS$
CONNECT (&uaf_rab
);
4705 vaxc$errno
= status
;
4708 /* read the requested record - index is in uname */
4709 uaf_rab
.rab$l_kbf
= uname
;
4710 uaf_rab
.rab$b_ksz
= strlen (uname
);
4711 uaf_rab
.rab$b_rac
= RAB$C_KEY
;
4712 uaf_rab
.rab$l_ubf
= (char *)&retuaf
;
4713 uaf_rab
.rab$w_usz
= sizeof retuaf
;
4714 status
= SYS$
GET (&uaf_rab
);
4718 vaxc$errno
= status
;
4721 /* close the User Authorization File */
4722 status
= SYS$
DISCONNECT (&uaf_rab
);
4726 vaxc$errno
= status
;
4729 status
= SYS$
CLOSE (&uaf_fab
);
4733 vaxc$errno
= status
;
4747 uaf_fab
= cc$rms_fab
;
4748 uaf_rab
= cc$rms_rab
;
4749 /* initialize fab fields */
4750 uaf_fab
.fab$l_fna
= "SYS$SYSTEM:SYSUAF.DAT";
4751 uaf_fab
.fab$b_fns
= 21;
4752 uaf_fab
.fab$b_fac
= FAB$M_GET
;
4753 uaf_fab
.fab$b_org
= FAB$C_IDX
;
4754 uaf_fab
.fab$b_shr
= FAB$M_GET
|FAB$M_PUT
|FAB$M_UPD
|FAB$M_DEL
;
4755 /* initialize rab fields */
4756 uaf_rab
.rab$l_fab
= &uaf_fab
;
4757 /* open the User Authorization File */
4758 status
= SYS$
OPEN (&uaf_fab
);
4762 vaxc$errno
= status
;
4765 status
= SYS$
CONNECT (&uaf_rab
);
4769 vaxc$errno
= status
;
4772 /* read the requested record - index is in uic */
4773 uaf_rab
.rab$b_krf
= 1; /* 1st alternate key */
4774 uaf_rab
.rab$l_kbf
= (char *) &uic
;
4775 uaf_rab
.rab$b_ksz
= sizeof uic
;
4776 uaf_rab
.rab$b_rac
= RAB$C_KEY
;
4777 uaf_rab
.rab$l_ubf
= (char *)&retuaf
;
4778 uaf_rab
.rab$w_usz
= sizeof retuaf
;
4779 status
= SYS$
GET (&uaf_rab
);
4783 vaxc$errno
= status
;
4786 /* close the User Authorization File */
4787 status
= SYS$
DISCONNECT (&uaf_rab
);
4791 vaxc$errno
= status
;
4794 status
= SYS$
CLOSE (&uaf_fab
);
4798 vaxc$errno
= status
;
4804 static struct passwd retpw
;
4812 /* copy these out first because if the username is 32 chars, the next
4813 section will overwrite the first byte of the UIC */
4814 retpw
.pw_uid
= up
->uaf$w_mem
;
4815 retpw
.pw_gid
= up
->uaf$w_grp
;
4817 /* I suppose this is not the best style, to possibly overwrite one
4818 byte beyond the end of the field, but what the heck... */
4819 ptr
= &up
->uaf$t_username
[UAF$S_USERNAME
];
4820 while (ptr
[-1] == ' ')
4823 strcpy (retpw
.pw_name
, up
->uaf$t_username
);
4825 /* the rest of these are counted ascii strings */
4826 strncpy (retpw
.pw_gecos
, &up
->uaf$t_owner
[1], up
->uaf$t_owner
[0]);
4827 retpw
.pw_gecos
[up
->uaf$t_owner
[0]] = '\0';
4828 strncpy (retpw
.pw_dir
, &up
->uaf$t_defdev
[1], up
->uaf$t_defdev
[0]);
4829 retpw
.pw_dir
[up
->uaf$t_defdev
[0]] = '\0';
4830 strncat (retpw
.pw_dir
, &up
->uaf$t_defdir
[1], up
->uaf$t_defdir
[0]);
4831 retpw
.pw_dir
[up
->uaf$t_defdev
[0] + up
->uaf$t_defdir
[0]] = '\0';
4832 strncpy (retpw
.pw_shell
, &up
->uaf$t_defcli
[1], up
->uaf$t_defcli
[0]);
4833 retpw
.pw_shell
[up
->uaf$t_defcli
[0]] = '\0';
4837 #else /* not READ_SYSUAF */
4838 static struct passwd retpw
;
4839 #endif /* not READ_SYSUAF */
4850 unsigned char * full
;
4851 #endif /* READ_SYSUAF */
4856 if ('a' <= *ptr
&& *ptr
<= 'z')
4861 if (!(up
= get_uaf_name (name
)))
4863 return cnv_uaf_pw (up
);
4865 if (strcmp (name
, getenv ("USER")) == 0)
4867 retpw
.pw_uid
= getuid ();
4868 retpw
.pw_gid
= getgid ();
4869 strcpy (retpw
.pw_name
, name
);
4870 if (full
= egetenv ("FULLNAME"))
4871 strcpy (retpw
.pw_gecos
, full
);
4873 *retpw
.pw_gecos
= '\0';
4874 strcpy (retpw
.pw_dir
, egetenv ("HOME"));
4875 *retpw
.pw_shell
= '\0';
4880 #endif /* not READ_SYSUAF */
4890 if (!(up
= get_uaf_uic (uid
)))
4892 return cnv_uaf_pw (up
);
4894 if (uid
== sys_getuid ())
4895 return getpwnam (egetenv ("USER"));
4898 #endif /* not READ_SYSUAF */
4901 /* return total address space available to the current process. This is
4902 the sum of the current p0 size, p1 size and free page table entries
4908 unsigned long free_pages
;
4909 unsigned long frep0va
;
4910 unsigned long frep1va
;
4913 item_code
= JPI$_FREPTECNT
;
4914 if (((status
= LIB$
GETJPI (&item_code
, 0, 0, &free_pages
)) & 1) == 0)
4917 vaxc$errno
= status
;
4922 item_code
= JPI$_FREP0VA
;
4923 if (((status
= LIB$
GETJPI (&item_code
, 0, 0, &frep0va
)) & 1) == 0)
4926 vaxc$errno
= status
;
4929 item_code
= JPI$_FREP1VA
;
4930 if (((status
= LIB$
GETJPI (&item_code
, 0, 0, &frep1va
)) & 1) == 0)
4933 vaxc$errno
= status
;
4937 return free_pages
+ frep0va
+ (0x7fffffff - frep1va
);
4941 define_logical_name (varname
, string
)
4945 struct dsc$descriptor_s strdsc
=
4946 {strlen (string
), DSC$K_DTYPE_T
, DSC$K_CLASS_S
, string
};
4947 struct dsc$descriptor_s envdsc
=
4948 {strlen (varname
), DSC$K_DTYPE_T
, DSC$K_CLASS_S
, varname
};
4949 struct dsc$descriptor_s lnmdsc
=
4950 {7, DSC$K_DTYPE_T
, DSC$K_CLASS_S
, "LNM$JOB"};
4952 return LIB$
SET_LOGICAL (&envdsc
, &strdsc
, &lnmdsc
, 0, 0);
4956 delete_logical_name (varname
)
4959 struct dsc$descriptor_s envdsc
=
4960 {strlen (varname
), DSC$K_DTYPE_T
, DSC$K_CLASS_S
, varname
};
4961 struct dsc$descriptor_s lnmdsc
=
4962 {7, DSC$K_DTYPE_T
, DSC$K_CLASS_S
, "LNM$JOB"};
4964 return LIB$
DELETE_LOGICAL (&envdsc
, &lnmdsc
);
4982 error ("execvp system call not implemented");
4991 struct FAB from_fab
= cc$rms_fab
, to_fab
= cc$rms_fab
;
4992 struct NAM from_nam
= cc$rms_nam
, to_nam
= cc$rms_nam
;
4993 char from_esn
[NAM$C_MAXRSS
];
4994 char to_esn
[NAM$C_MAXRSS
];
4996 from_fab
.fab$l_fna
= from
;
4997 from_fab
.fab$b_fns
= strlen (from
);
4998 from_fab
.fab$l_nam
= &from_nam
;
4999 from_fab
.fab$l_fop
= FAB$M_NAM
;
5001 from_nam
.nam$l_esa
= from_esn
;
5002 from_nam
.nam$b_ess
= sizeof from_esn
;
5004 to_fab
.fab$l_fna
= to
;
5005 to_fab
.fab$b_fns
= strlen (to
);
5006 to_fab
.fab$l_nam
= &to_nam
;
5007 to_fab
.fab$l_fop
= FAB$M_NAM
;
5009 to_nam
.nam$l_esa
= to_esn
;
5010 to_nam
.nam$b_ess
= sizeof to_esn
;
5012 status
= SYS$
RENAME (&from_fab
, 0, 0, &to_fab
);
5018 if (status
== RMS$_DEV
)
5022 vaxc$errno
= status
;
5027 /* This function renames a file like `rename', but it strips
5028 the version number from the "to" filename, such that the "to" file is
5029 will always be a new version. It also sets the file protection once it is
5030 finished. The protection that we will use is stored in fab_final_pro,
5031 and was set when we did a creat_copy_attrs to create the file that we
5034 We could use the chmod function, but Eunichs uses 3 bits per user category
5035 to describe the protection, and VMS uses 4 (write and delete are separate
5036 bits). To maintain portability, the VMS implementation of `chmod' wires
5037 the W and D bits together. */
5040 static struct fibdef fib
; /* We need this initialized to zero */
5041 char vms_file_written
[NAM$C_MAXRSS
];
5044 rename_sans_version (from
,to
)
5051 struct FAB to_fab
= cc$rms_fab
;
5052 struct NAM to_nam
= cc$rms_nam
;
5053 struct dsc$descriptor fib_d
={sizeof (fib
),0,0,(char*) &fib
};
5054 struct dsc$descriptor fib_attr
[2]
5055 = {{sizeof (fab_final_pro
),ATR$C_FPRO
,0,(char*) &fab_final_pro
},{0,0,0,0}};
5056 char to_esn
[NAM$C_MAXRSS
];
5058 $
DESCRIPTOR (disk
,to_esn
);
5060 to_fab
.fab$l_fna
= to
;
5061 to_fab
.fab$b_fns
= strlen (to
);
5062 to_fab
.fab$l_nam
= &to_nam
;
5063 to_fab
.fab$l_fop
= FAB$M_NAM
;
5065 to_nam
.nam$l_esa
= to_esn
;
5066 to_nam
.nam$b_ess
= sizeof to_esn
;
5068 status
= SYS$
PARSE (&to_fab
, 0, 0); /* figure out the full file name */
5070 if (to_nam
.nam$l_fnb
&& NAM$M_EXP_VER
)
5071 *(to_nam
.nam$l_ver
) = '\0';
5073 stat
= rename (from
, to_esn
);
5077 strcpy (vms_file_written
, to_esn
);
5079 to_fab
.fab$l_fna
= vms_file_written
; /* this points to the versionless name */
5080 to_fab
.fab$b_fns
= strlen (vms_file_written
);
5082 /* Now set the file protection to the correct value */
5083 SYS$
OPEN (&to_fab
, 0, 0); /* This fills in the nam$w_fid fields */
5085 /* Copy these fields into the fib */
5086 fib
.fib$r_fid_overlay
.fib$w_fid
[0] = to_nam
.nam$w_fid
[0];
5087 fib
.fib$r_fid_overlay
.fib$w_fid
[1] = to_nam
.nam$w_fid
[1];
5088 fib
.fib$r_fid_overlay
.fib$w_fid
[2] = to_nam
.nam$w_fid
[2];
5090 SYS$
CLOSE (&to_fab
, 0, 0);
5092 stat
= SYS$
ASSIGN (&disk
, &chan
, 0, 0); /* open a channel to the disk */
5095 stat
= SYS$
QIOW (0, chan
, IO$_MODIFY
, iosb
, 0, 0, &fib_d
,
5096 0, 0, 0, &fib_attr
, 0);
5099 stat
= SYS$
DASSGN (chan
);
5102 strcpy (vms_file_written
, to_esn
); /* We will write this to the terminal*/
5113 unsigned short fid
[3];
5114 char esa
[NAM$C_MAXRSS
];
5117 fab
.fab$l_fop
= FAB$M_OFP
;
5118 fab
.fab$l_fna
= file
;
5119 fab
.fab$b_fns
= strlen (file
);
5120 fab
.fab$l_nam
= &nam
;
5123 nam
.nam$l_esa
= esa
;
5124 nam
.nam$b_ess
= NAM$C_MAXRSS
;
5126 status
= SYS$
PARSE (&fab
);
5127 if ((status
& 1) == 0)
5130 vaxc$errno
= status
;
5133 status
= SYS$
SEARCH (&fab
);
5134 if ((status
& 1) == 0)
5137 vaxc$errno
= status
;
5141 fid
[0] = nam
.nam$w_fid
[0];
5142 fid
[1] = nam
.nam$w_fid
[1];
5143 fid
[2] = nam
.nam$w_fid
[2];
5145 fab
.fab$l_fna
= new;
5146 fab
.fab$b_fns
= strlen (new);
5148 status
= SYS$
PARSE (&fab
);
5149 if ((status
& 1) == 0)
5152 vaxc$errno
= status
;
5156 nam
.nam$w_fid
[0] = fid
[0];
5157 nam
.nam$w_fid
[1] = fid
[1];
5158 nam
.nam$w_fid
[2] = fid
[2];
5160 nam
.nam$l_esa
= nam
.nam$l_name
;
5161 nam
.nam$b_esl
= nam
.nam$b_name
+ nam
.nam$b_type
+ nam
.nam$b_ver
;
5163 status
= SYS$
ENTER (&fab
);
5164 if ((status
& 1) == 0)
5167 vaxc$errno
= status
;
5178 printf ("%s not yet implemented\r\n", badfunc
);
5179 reset_all_sys_modes ();
5186 /* Arrange to return a range centered on zero. */
5187 return rand () - (1 << 30);
5199 /* Called from init_sys_modes. */
5201 hft_init (struct tty_display_info
*tty_out
)
5205 /* If we're not on an HFT we shouldn't do any of this. We determine
5206 if we are on an HFT by trying to get an HFT error code. If this
5207 call fails, we're not on an HFT. */
5209 if (ioctl (0, HFQERROR
, &junk
) < 0)
5211 #else /* not IBMR2AIX */
5212 if (ioctl (0, HFQEIO
, 0) < 0)
5214 #endif /* not IBMR2AIX */
5216 /* On AIX the default hft keyboard mapping uses backspace rather than delete
5217 as the rubout key's ASCII code. Here this is changed. The bug is that
5218 there's no way to determine the old mapping, so in reset_sys_modes
5219 we need to assume that the normal map had been present. Of course, this
5220 code also doesn't help if on a terminal emulator which doesn't understand
5224 struct hfkeymap keymap
;
5226 buf
.hf_bufp
= (char *)&keymap
;
5227 buf
.hf_buflen
= sizeof (keymap
);
5228 keymap
.hf_nkeys
= 2;
5229 keymap
.hfkey
[0].hf_kpos
= 15;
5230 keymap
.hfkey
[0].hf_kstate
= HFMAPCHAR
| HFSHFNONE
;
5232 keymap
.hfkey
[0].hf_keyidh
= '<';
5233 #else /* not IBMR2AIX */
5234 keymap
.hfkey
[0].hf_page
= '<';
5235 #endif /* not IBMR2AIX */
5236 keymap
.hfkey
[0].hf_char
= 127;
5237 keymap
.hfkey
[1].hf_kpos
= 15;
5238 keymap
.hfkey
[1].hf_kstate
= HFMAPCHAR
| HFSHFSHFT
;
5240 keymap
.hfkey
[1].hf_keyidh
= '<';
5241 #else /* not IBMR2AIX */
5242 keymap
.hfkey
[1].hf_page
= '<';
5243 #endif /* not IBMR2AIX */
5244 keymap
.hfkey
[1].hf_char
= 127;
5245 hftctl (0, HFSKBD
, &buf
);
5249 /* Reset the rubout key to backspace. */
5252 hft_reset (struct tty_display_info
*tty_out
)
5255 struct hfkeymap keymap
;
5259 if (ioctl (0, HFQERROR
, &junk
) < 0)
5261 #else /* not IBMR2AIX */
5262 if (ioctl (0, HFQEIO
, 0) < 0)
5264 #endif /* not IBMR2AIX */
5266 buf
.hf_bufp
= (char *)&keymap
;
5267 buf
.hf_buflen
= sizeof (keymap
);
5268 keymap
.hf_nkeys
= 2;
5269 keymap
.hfkey
[0].hf_kpos
= 15;
5270 keymap
.hfkey
[0].hf_kstate
= HFMAPCHAR
| HFSHFNONE
;
5272 keymap
.hfkey
[0].hf_keyidh
= '<';
5273 #else /* not IBMR2AIX */
5274 keymap
.hfkey
[0].hf_page
= '<';
5275 #endif /* not IBMR2AIX */
5276 keymap
.hfkey
[0].hf_char
= 8;
5277 keymap
.hfkey
[1].hf_kpos
= 15;
5278 keymap
.hfkey
[1].hf_kstate
= HFMAPCHAR
| HFSHFSHFT
;
5280 keymap
.hfkey
[1].hf_keyidh
= '<';
5281 #else /* not IBMR2AIX */
5282 keymap
.hfkey
[1].hf_page
= '<';
5283 #endif /* not IBMR2AIX */
5284 keymap
.hfkey
[1].hf_char
= 8;
5285 hftctl (0, HFSKBD
, &buf
);
5292 /* These are included on Sunos 4.1 when we do not use shared libraries.
5293 X11 libraries may refer to these functions but (we hope) do not
5294 actually call them. */
5314 #endif /* USE_DL_STUBS */
5323 register int length
;
5327 long max_str
= 65535;
5329 while (length
> max_str
) {
5330 (void) LIB$
MOVC5 (&zero
, &zero
, &zero
, &max_str
, b
);
5335 (void) LIB$
MOVC5 (&zero
, &zero
, &zero
, &max_str
, b
);
5337 while (length
-- > 0)
5339 #endif /* not VMS */
5342 #endif /* no bzero */
5343 #endif /* BSTRING */
5345 #if (!defined (BSTRING) && !defined (bcopy)) || defined (NEED_BCOPY)
5348 /* Saying `void' requires a declaration, above, where bcopy is used
5349 and that declaration causes pain for systems where bcopy is a macro. */
5350 bcopy (b1
, b2
, length
)
5353 register int length
;
5356 long max_str
= 65535;
5358 while (length
> max_str
) {
5359 (void) LIB$
MOVC3 (&max_str
, b1
, b2
);
5365 (void) LIB$
MOVC3 (&length
, b1
, b2
);
5367 while (length
-- > 0)
5369 #endif /* not VMS */
5371 #endif /* (!defined (BSTRING) && !defined (bcopy)) || defined (NEED_BCOPY) */
5376 bcmp (b1
, b2
, length
) /* This could be a macro! */
5379 register int length
;
5382 struct dsc$descriptor_s src1
= {length
, DSC$K_DTYPE_T
, DSC$K_CLASS_S
, b1
};
5383 struct dsc$descriptor_s src2
= {length
, DSC$K_DTYPE_T
, DSC$K_CLASS_S
, b2
};
5385 return STR$
COMPARE (&src1
, &src2
);
5387 while (length
-- > 0)
5392 #endif /* not VMS */
5394 #endif /* no bcmp */
5395 #endif /* not BSTRING */
5397 #ifndef HAVE_STRSIGNAL
5404 if (0 <= code
&& code
< NSIG
)
5407 signame
= sys_errlist
[code
];
5409 /* Cast to suppress warning if the table has const char *. */
5410 signame
= (char *) sys_siglist
[code
];
5416 #endif /* HAVE_STRSIGNAL */
5418 /* arch-tag: edb43589-4e09-4544-b325-978b5b121dcf
5419 (do not change this comment) */