unixcall.c
Go to the documentation of this file.
1 /****************************************************************/
2 /* unixcall.c
3 /* 1986-Jul-6 original for Ustation
4 /* 1986-Dec process id's, file changes, syserrlist
5 /* 1987-Feb dup,isatty
6 /* 1987-Apr getwd,stat,time
7 /* 1988-Jan,Feb socket, select
8 /* 1988-Dec ioctl
9 /* 1990-Mar VxWorks
10 /* Copyright(c) 1988 MATSUI Toshihiro, Electrotechnical Laboratory.
11 /****************************************************************/
12 
13 static char *rcsid="@(#)$Id$";
14 
15 /* SunOS's gettimeofday used to accept only one argument.
16 #ifdef Solaris2
17 #define _SVID_GETTOD
18 #endif
19 */
20 
21 #include "eus.h"
22 
23 #if vxworks
24 #define NSIG NUM_SIGNALS
25 #define SIG_DFL 0
26 #include <sigLib.h>
27 #include <socket.h>
28 #include <in.h>
29 #else
30 #include <sys/types.h>
31 #include <sys/times.h>
32 #include <sys/stat.h>
33 #include <signal.h>
34 #include <sys/ioctl.h>
35 #include <time.h>
36 #include <sys/time.h>
37 #include <sys/socket.h>
38 #include <sys/un.h>
39 #include <netinet/in.h>
40 #include <netdb.h>
41 #include <sys/mman.h>
42 #include <string.h>
43 #include <unistd.h> /* for lseek */
44 #endif
45 
46 /*SONY/news doesn't have message queu ipc facilities*/
47 #if !vxworks
48 #include <sys/ipc.h>
49 #include <sys/msg.h>
50 #endif
51 
52 #if (SunOS4_1 || (mips && !IRIX && !IRIX6)) && !Linux
53 /* Sun likes to change ioccom constants frequently. */
54 #define IOC_VOID _IOC_VOID
55 #define IOC_IN _IOC_IN
56 #define IOC_OUT _IOC_OUT
57 #define IOC_INOUT _IOC_INOUT
58 #endif
59 
60 #if Linux
61 #define IOC_VOID 0
62 #endif
63 
64 #if Solaris2 || Linux || alpha || Cygwin
65 #include <errno.h>
66 #include <dirent.h>
67 #else
68 extern int errno;
69 #endif
70 
71 #if Linux
72 #define IOC_VOID 0
73 #endif
74 
75 
76 #if alpha
77 #include <sys/utsname.h>
78 #include <sys/types.h>
79 #include <sys/ipc.h>
80 #include <sys/msg.h>
81 #endif
82 
83 #if system5 || Linux || Cygwin
84 #include <sys/utsname.h>
85 #endif
86 
87 #include <time.h>
88 //extern char *tzname[2];
89 #if !Cygwin /* extern timezone */
90 extern time_t timezone, altzone; /*long*/
91 #endif
92 extern int daylight;
93 
94 extern pointer eussigvec[NSIG];
95 
97 
98 
99 /***************** times and status *****************/
100 
101 #if !vxworks
102 pointer PTIMES(ctx,n,argv)
103 register context *ctx;
104 int n;
105 pointer argv[];
106 { struct tms buffer;
107  register pointer t;
108  long et;
109  ckarg(0);
110  GC_REGION(et=times(&buffer););
111  t=cons(ctx,makeint(buffer.tms_cstime),NIL);
112  t=cons(ctx,makeint(buffer.tms_cutime),t);
113  t=cons(ctx,makeint(buffer.tms_stime),t);
114  t=cons(ctx,makeint(buffer.tms_utime),t);
115  t=cons(ctx,mkbigint(et),t);
116  return(t);}
117 
118 pointer RUNTIME(ctx,n,argv)
119 register context *ctx;
120 int n;
121 pointer argv[];
122 { struct tms buffer;
123  ckarg(0);
124  GC_REGION(times(&buffer););
125  return(makeint(buffer.tms_utime+buffer.tms_stime));}
126 
127 pointer LOCALTIME(ctx,n,argv)
128 register context *ctx;
129 int n;
130 pointer argv[];
131 { long clock;
132  struct tm *tms;
133  pointer timevec;
134  pointer *tv;
135  pointer tz0, tz1, tz;
136  struct tm res;
137 
138  if (n==1) clock=coerceintval(argv[0]);
139  else clock=time(0);
140  tms=localtime_r((time_t *)&clock,&res); /* localtime-->localtime_r */
141  timevec=makevector(C_VECTOR,10);
142  vpush(timevec);
143 
144 #ifdef Cygwin
145  if (getenv("TZ")==NULL) {
146  tzname[0]="UTC";
147  tzname[1]="UTC";
148  }
149 #endif
150 
151  tz0=makestring(tzname[0],strlen(tzname[0]));
152  vpush(tz0);
153  tz1=makestring(tzname[1],strlen(tzname[1]));
154  vpush(tz1);
155  tz=cons(ctx, tz1, NIL);
156  tz=cons(ctx, tz0, tz);
157  tv=timevec->c.vec.v;
158  tv[0]=makeint(tms->tm_sec);
159  tv[1]=makeint(tms->tm_min);
160  tv[2]=makeint(tms->tm_hour);
161  tv[3]=makeint(tms->tm_mday);
162  tv[4]=makeint(tms->tm_mon);
163  tv[5]=makeint(tms->tm_year);
164  tv[6]=makeint(tms->tm_wday);
165  tv[7]=makeint(tms->tm_yday);
166  tv[8]=(tms->tm_isdst>0)?T:NIL;
167  tv[9]=tz;
168  vpop(); vpop(); vpop();
169  return(timevec);}
170 
171 pointer ASCTIME(ctx,n,argv)
172 register context *ctx;
173 int n;
174 register pointer argv[];
175 { char *atp;
176  struct tm tms1, *tms;
177  pointer a=argv[0];
178  int i;
179 #define ASCTIME_STRLEN 30 /* at lease 26 chars */
180  char at[ASCTIME_STRLEN];
181 
182  ckarg(1);
183  if (isintvector(argv[0])) tms=(struct tm *)a->c.ivec.iv;
184  else if (isvector(a)) {
185  tms1.tm_sec=ckintval(a->c.vec.v[0]);
186  tms1.tm_min=ckintval(a->c.vec.v[1]);
187  tms1.tm_hour=ckintval(a->c.vec.v[2]);
188  tms1.tm_mday=ckintval(a->c.vec.v[3]);
189  tms1.tm_mon=ckintval(a->c.vec.v[4]);
190  tms1.tm_year=ckintval(a->c.vec.v[5]);
191  tms1.tm_wday=ckintval(a->c.vec.v[6]);
192  /* tms1.tm_yday=ckintval(a->c.vec.v[7]); */
193  tms1.tm_isdst=(a->c.vec.v[8]==NIL)?0:1;
194  tms= &tms1; }
195  else error(E_NOINTVECTOR);
196 #if defined(__USE_POSIX) || Cygwin || Linux
197  atp=asctime_r(tms,at); /* asctime --> asctime_r */
198 #else
199  atp=asctime_r(tms,at,ASCTIME_STRLEN); /* asctime --> asctime_r */
200 #endif
201  return(makestring(atp,strlen(atp)));}
202 
203 #if !Solaris2
204 #include <sys/resource.h>
205 pointer GETRUSAGE(ctx,n,argv)
206 register context *ctx;
207 int n; pointer argv[];
208 { register int who,i;
209  long rusage[18];
210  eusfloat_t utime,stime;
211  register pointer r=NIL;
212  numunion nu;
213 
214  ckarg(1); who=ckintval(argv[0]);
215  getrusage(who,(struct rusage *)rusage);
216  utime=rusage[0]+rusage[1]*1.0e-6;
217  stime=rusage[2]+rusage[3]*1.0e-6;
218  for (i=17; i>=4; i--) r=cons(ctx,makeint(rusage[i]),r);
219  r=cons(ctx,makeflt(stime),r); r=cons(ctx,makeflt(utime),r);
220  /*(utime stime maxrss ixrss idrss isrss page-reclaims page-faults swap
221  inblock outblock msgsnd msgrcv nsignals
222  voluntary-context-switch involuntary-context-switch) */
223  return(r);}
224 
226 register context *ctx;
227 int n; pointer argv[];
228 { ckarg(0);
229  return(makeint(getpagesize())); }
230 
231 #endif
232 
234 register context *ctx;
235 int n;
236 register pointer argv[];
237 { struct timeval /*{long tv_sec, tv_usec;}*/ tm;
238  eusfloat_t ftime;
239  pointer p;
240 
241  /* (sec usec timezone daylight) */
242  /* timezone is seconds west to the GMT */
243  gettimeofday(&tm, 0);
244  p=cons(ctx, makeint(daylight), NIL);
245  p=cons(ctx, makeint(timezone),p);
246  p=cons(ctx, makeint(tm.tv_usec), p);
247  vpush(p);
248  p=cons(ctx, mkbigint(tm.tv_sec), p);
249  vpop();
250  return(p);}
251 
252 pointer GETITIMER(ctx,n,argv)
253 register context *ctx;
254 int n;
255 register pointer argv[];
256 { int stat;
257  struct itimerval tmval;
258  eusfloat_t interval,value;
259  numunion nu;
260  ckarg(1);
261  stat=getitimer(ckintval(argv[0]), &tmval);
262  if (stat<0) return(NIL);
263  interval=tmval.it_interval.tv_sec + ( tmval.it_interval.tv_usec*1.0E-6);
264  value=tmval.it_value.tv_sec + (tmval.it_value.tv_usec*1.0E-6);
265  return(cons(ctx,makeflt(value),
266  cons(ctx,makeflt(interval),NIL)));}
267 
268 pointer SETITIMER(ctx,n,argv)
269 register context *ctx;
270 int n;
271 register pointer argv[];
272 { int stat;
273  pointer result=NIL;
274  struct itimerval tmval,oldtmval;
275  eusfloat_t interval,value;
276  numunion nu;
277 
278  ckarg(3);
279  value=ckfltval(argv[1]); interval=ckfltval(argv[2]);
280  tmval.it_value.tv_sec=value;
281  tmval.it_value.tv_usec=(value-tmval.it_value.tv_sec)*1.0E6;
282  tmval.it_interval.tv_sec=interval;
283  tmval.it_interval.tv_usec=(interval-tmval.it_interval.tv_sec)*1.0E6;
284  stat=setitimer(ckintval(argv[0]), &tmval, &oldtmval);
285  if (stat<0) return(result);
286  interval=oldtmval.it_interval.tv_sec + (oldtmval.it_interval.tv_usec*1.0E-6);
287  value=oldtmval.it_value.tv_sec + (oldtmval.it_value.tv_usec*1.0E-6);
288  return(cons(ctx,makeflt(interval),
289  cons(ctx,makeflt(value),result)));}
290 #endif /* ! vxworks */
291 
292 /****************************************************************/
293 /* signal handling
294 /****************************************************************/
295 
296 #ifdef SIGADDSET
297 #undef SIGADDSET
298 #endif
299 #ifdef SIGDELSET
300 #undef SIGDELSET
301 #endif
302 
303 pointer SIGADDSET(ctx,n,argv)
304 register context *ctx;
305 int n;
306 register pointer argv[];
307 { int signum;
308  sigset_t *set;
309  ckarg(2);
310  signum=ckintval(argv[1]);
311  if (isvector(argv[0]) &&
312  ((elmtypeof(argv[0])==ELM_INT) || (elmtypeof(argv[0])==ELM_BIT))) {
313  set=(sigset_t *)argv[0]->c.ivec.iv;
314  sigaddset(set, signum);
315  return(argv[0]);}
316  else error(E_USER,(pointer)"integer/bit vector expected for sigaddset");
317  }
318 
319 pointer SIGDELSET(ctx,n,argv)
320 register context *ctx;
321 int n;
322 register pointer argv[];
323 { int signum;
324  sigset_t *set;
325  ckarg(2);
326  signum=ckintval(argv[1]);
327  if (isvector(argv[0]) &&
328  ((elmtypeof(argv[0])==ELM_INT) || (elmtypeof(argv[0])==ELM_BIT))) {
329  set=(sigset_t *)argv[0]->c.ivec.iv;
330  sigdelset(set, signum);
331  return(argv[0]);}
332  else error(E_USER,(pointer)"integer/bit vector expected for sigaddset");
333  }
334 
336 context *ctx;
337 int n;
338 pointer argv[];
339 { sigset_t *set, *oset;
340  int how, stat;
341  ckarg2(2,3);
342  how=ckintval(argv[0]);
343  if (isvector(argv[1]) &&
344  ((elmtypeof(argv[1])==ELM_INT) || (elmtypeof(argv[1])==ELM_BIT))) {
345  set=(sigset_t *)argv[1]->c.ivec.iv;
346  if (isvector(argv[2]) &&
347  ((elmtypeof(argv[2])==ELM_INT) || (elmtypeof(argv[2])==ELM_BIT)))
348  oset=(sigset_t *)argv[2]->c.ivec.iv;
349  else oset=(sigset_t *)0;
350  stat=sigprocmask(how, set, oset);
351  if (stat==0) return(T); else return(makeint(-errno));
352  }
353  else error(E_USER,(pointer)"integer/bit vector expected for sigprocmask");
354  }
355 
356 pointer KILL(ctx,n,argv)
357 register context *ctx;
358 int n;
359 register pointer argv[];
360 { ckarg(2);
361  return(makeint(kill(ckintval(argv[0]),ckintval(argv[1]))));}
362 
363 #if Solaris2 || Linux || IRIX || IRIX6 || Cygwin
364 pointer SIGNAL(ctx,n,argv)
365 register context *ctx;
366 int n;
367 pointer argv[];
368 { register int s,i;eusinteger_t f;
369  struct sigaction sv;
370  register pointer a=argv[1],oldval;
371  extern void eusint();
372  unsigned long int j;
373 
374  ckarg2(1,3);
375  s=min(ckintval(argv[0]),NSIG-1);
376  oldval=eussigvec[s];
377  if (n==1) return(oldval);
378  if (isint(a)) { f=max(1,intval(a)); eussigvec[s]=NIL;}
379  else { f=(eusinteger_t)eusint; eussigvec[s]=a;}
380  sv.sa_handler= (void (*)())f;
381 #if Linux || Cygwin
382 
383 #if LIB6 && !Darwin
384  for (j=0; j< _SIGSET_NWORDS; j++) sv.sa_mask.__val[j]=0;
385 #else
386  /* old type sigmask */
387  sv.sa_mask=0;
388 #endif
389 /*LIB6*/
390 
391 #elif (IRIX || IRIX6) && !IRIX6_2
392  for (i=0; i<4; i++) sv.sa_mask.sigbits[i]=0;
393 #else
394  for (i=0; i<4; i++) sv.sa_mask.__sigbits[i]=0;
395 #endif
396 
397  if (n==3) sv.sa_flags= ckintval(argv[2]);
398  else sv.sa_flags=0;
399  /* printf("signal %d flag=%d\n", s, sv.sa_flags); */
400  s=sigaction(s,&sv,0);
401  if (s== -1) return(makeint(-errno)); else return(oldval);
402  }
403 
404 #else
405 pointer SIGNAL(ctx,n,argv)
406 register context *ctx;
407 int n;
408 pointer argv[];
409 { register int s;eusinteger_t f;
410  struct sigvec sv;
411  register pointer a=argv[1],oldval;
412  extern void eusint();
413 
414  ckarg2(1,3);
415  s=min(ckintval(argv[0]),NSIG-1);
416  oldval=eussigvec[s];
417  if (n==1) return(oldval);
418  if (isint(a)) { f=max(1,intval(a)); eussigvec[s]=NIL;}
419  else { f=(eusinteger_t)eusint; eussigvec[s]=a;}/* ???? */
420  sv.sv_handler=(void (*)())f;
421  sv.sv_mask=0; /*sigmask(s)???;*/
422 /*news doesn't have system5 compatible signal handling option*/
423 #if sun3 || sun4 || mips || alpha
424  if (n==3) sv.sv_flags=ckintval(argv[2]);
425  else sv.sv_flags=0;
426 #endif
427  s=sigvec(s,&sv,0);
428  if (s== -1) return(makeint(-errno)); else return(oldval);
429  }
430 
431 #endif
432 
433 #if !vxworks
434 
435 #include <sys/wait.h>
436 pointer WAIT(ctx,n,argv)
437 register context *ctx;
438 int n;
439 pointer argv[];
440 { int completion=0, stat;
441  GC_REGION(stat = wait(&completion););
442  return(cons(ctx,makeint(stat),
443  cons(ctx,makeint(completion),NIL)));}
444 
445 pointer ALARM(ctx,n,argv)
446 register context *ctx;
447 int n; pointer argv[];
448 { ckarg(1);
449  return(makeint(alarm(ckintval(argv[0]))));}
450 
451 
452 #if sun3 || sun4 || news || sanyo || alpha || Linux
453 #if !Solaris2
454 pointer UALARM(ctx,n,argv)
455 register context *ctx;
456 int n; pointer argv[];
457 { ckarg(2);
458  return(makeint(ualarm(ckintval(argv[0]), ckintval(argv[1]))));}
459 #endif
460 #endif
461 
462 #endif
463 
464 /**********************************************/
465 /* process, user, and group identification
466 /**********************************************/
467 
468 pointer GETPID(ctx,n,argv)
469 register context *ctx;
470 int n;
471 pointer *argv; /* unused argument */
472 { ckarg(0);
473  return(makeint(getpid()));}
474 
475 #if !vxworks
476 pointer GETPPID(ctx,n,argv)
477 register context *ctx;
478 int n;
479 pointer argv[];
480 { ckarg(0);
481  return(makeint(getppid()));}
482 
483 pointer GETPGRP(ctx,n,argv)
484 register context *ctx;
485 int n;
486 pointer argv[];
487 #if system5 | Linux | Cygwin
488 { ckarg(0);
489  return(makeint(getpgrp()));}
490 #else
491 { int pid;
492  if (n==1) pid=ckintval(argv[0]);
493  else pid=getpid();
494  return(makeint(getpgrp(pid)));}
495 #endif
496 
497 pointer SETPGRP(context *ctx, int n, pointer *argv)
498 #if system5 | Linux | Cygwin
499 { ckarg(0);
500  return(makeint(setpgrp()));}
501 #else
502 { int pid;
503  ckarg(2);
504  return(makeint(setpgrp(ckintval(argv[0]),ckintval(argv[1]))));}
505 #endif
506 
507 pointer GETUID(context *ctx, int n, pointer *argv)
508 { ckarg(0);
509  return(makeint(getuid()));}
510 
511 pointer GETEUID(ctx,n,argv)
512 register context *ctx;
513 int n;
514 pointer argv[];
515 { ckarg(0);
516  return(makeint(geteuid()));}
517 
518 pointer GETGID(ctx,n,argv)
519 register context *ctx;
520 int n;
521 pointer argv[];
522 { ckarg(0);
523  return(makeint(getgid()));}
524 
525 pointer GETEGID(ctx,n,argv)
526 register context *ctx;
527 int n;
528 pointer argv[];
529 { ckarg(0);
530  return(makeint(getegid()));}
531 
532 pointer SETUID(ctx,n,argv)
533 register context *ctx;
534 int n;
535 pointer argv[];
536 { ckarg(1);
537  n=setuid(ckintval(argv[0]));
538  if (n<0) return(makeint(errno)); else return(T);}
539 
540 pointer SETGID(ctx,n,argv)
541 register context *ctx;
542 int n;
543 pointer argv[];
544 { ckarg(1);
545  n=setgid(ckintval(argv[0]));
546  if (n<0) return(makeint(errno)); else return(T);}
547 
548 #endif
550 #if system5 || Linux || Cygwin
551 pointer UNAME(ctx,n,argv)
552 register context *ctx;
553 int n;
554 pointer *argv;
555 { struct utsname u;
556  pointer s;
557  ckarg(0);
558  uname(&u);
559  vpush(makestring(u.sysname,strlen(u.sysname)));
560  vpush(makestring(u.nodename,strlen(u.nodename)));
561  vpush(makestring(u.release,strlen(u.release)));
562  vpush(makestring(u.version,strlen(u.version)));
563  vpush(makestring(u.machine,strlen(u.machine)));
564  s=stacknlist(ctx,5);
565  return(s);}
566 #endif
567 
568 /****************************************************************/
569 /* process creation and deletion
570 /****************************************************************/
571 #if !vxworks
572 #if !Solaris2 || !THREADED
573 pointer FORK(ctx,n,argv)
574 register context *ctx;
575 int n;
576 pointer *argv;
577 { ckarg(0);
578  return(makeint(fork()));
579  }
580 #else
581 /* for the problem of calling fork(2) in MT *
582  * Jan. 10 2003 by ikuo@jsk.t.u-tokyo.ac.jp */
583 static int ctxid_in_child;
584 static void *prepare(void) {
585  int i, me=thr_self();
586  /* preserve current context */
587  ctxid_in_child=me;
588  /* suspend all threads except self */
589  for (i=0; i<MAXTHREAD; i++) {
590  if (euscontexts[i]!=0 && i!=me &&
591  euscontexts[i]->threadobj->c.thrp.suspend==NIL) {
592  thr_suspend(i);
593  euscontexts[i]->threadobj->c.thrp.suspend=T; } }
594 }
595 static void *parent(void) {
596  /* continue all suspended threads */
597  int i, me=thr_self();
598  for (i=0; i<MAXTHREAD; i++) {
599  if (euscontexts[i]!=0 && i!=me) {
600  euscontexts[i]->threadobj->c.thrp.suspend=NIL;
601  thr_continue(i); } }
602 }
603 static void *child(void) {
604  /* do not continue suspended threads */
605  int me=thr_self();
606  /* copy current context (tid changed in child) */
608 }
609 pointer FORK(register context *ctx, int n, pointer *argv)
610 {ckarg(0);
611  pthread_atfork (prepare, parent, child);
612  return(makeint(fork()));
613 }
614 #endif /* endof Solaris || THREADED */
615 
616 #if Solaris2
617 pointer FORK1(ctx,n,argv)
618 register context *ctx;
619 int n;
620 pointer *argv;
621 { ckarg(0);
622  return(makeint(fork1()));
623  }
624 #endif
625 
626 #if sun3 || sun4 || vax || news || sanyo || (mips && !IRIX && !IRIX6) || alpha || Linux
627 pointer VFORK(ctx,n,argv)
628 register context *ctx;
629 int n;
630 pointer *argv;
631 { ckarg(0);
632  return(makeint(vfork()));}
633 #endif
634 
635 pointer EXEC(ctx,n,argv)
636 register context *ctx;
637 int n;
638 pointer *argv;
639 { byte *exeargv[512];
640  int i=0,stat;
641  if (n>512) error(E_MISMATCHARG);
642  while (i<n) {
643  exeargv[i]=Getstring(argv[i])->c.str.chars;
644  i++;}
645  exeargv[i]=0;
646  stat=execvp(exeargv[0],(char **)exeargv);
647  return(makeint(-errno));}
648 
649 #if !Solaris2
650 static pointer SETPRIORITY(ctx,n,argv)
651 register context *ctx;
652 int n;
653 pointer *argv;
654 /* (SETPRIORITY which who priority)
655  which 0:process, 1:process-group, 2:user
656  who 0:self, others pid, pgrp-id user-id */
657 { ckarg(3);
658  return(makeint(setpriority(ckintval(argv[0]),
659  ckintval(argv[1]),
660  ckintval(argv[2]))));}
661 
662 static pointer GETPRIORITY(ctx,n,argv)
663 register context *ctx;
664 int n;
665 pointer *argv;
666 /* (GETPRIORITY which who) */
667 { ckarg(2);
668  return(makeint(getpriority(ckintval(argv[0]), ckintval(argv[1]))));}
669 #endif
670 #endif
672 pointer EXIT(ctx,n,argv)
673 register context *ctx;
674 int n;
675 pointer *argv;
676 { pointer exithook=speval(QEXITHOOK);
677 /*
678  Exit function can not finish threads which create in Euslisp
679 on SunOS 4.1. So we use thr_exit function on SunOS 4.1.
680 */
681 #if SunOS4_1 /* changed by H.Nakagaki at 28-Jun-1995 */
682  if (n==0) thr_exit(0);
683  else thr_exit(ckintval(argv[0]));
684 #else
685  if (exithook != NIL) {
686  ufuncall(ctx,exithook,exithook,(pointer)(ctx->vsp-n),0,n);}
687  if (n==0) exit(0);
688  else exit(ckintval(argv[0]));
689 #endif
690 }
691 
692 pointer _EXIT(ctx,n,argv)
693 register context *ctx;
694 int n;
695 pointer *argv;
696 { pointer exithook=speval(QEXITHOOK);
697  if (n==0) _exit(0);
698  else _exit(ckintval(argv[0]));
699 }
700 
701 /****************************************************************/
702 /* unix raw I/O and file systems
703 /****************************************************************/
704 
705 pointer UNIXREAD(ctx,n,argv)
706 register context *ctx;
707 int n;
708 pointer argv[];
709 /* (unix:read stream [length]) */
710 /* (unix:read fd buffer [length [offset]]) */
711 #if (WORD_SIZE == 64)
712 { register int fd,offset=0;
713  register long int size;
714 #else
715 { register int fd,size,offset=0;
716 #endif
717  register pointer strm,buf,count;
718  byte *bufp;
719 
720  ckarg2(1,4);
721  strm=argv[0];
722  if (isiostream(strm)) strm=strm->c.iostream.in;
723  if (isfilestream(strm)) {
724  if (strm->c.stream.direction!=K_IN) error(E_IODIRECTION);
725  if (isint(strm->c.fstream.fname)) error(E_STREAM);
726  buf=strm->c.fstream.buffer;
727  bufp=buf->c.str.chars;
728  fd=intval(strm->c.fstream.fd);
729  if (n==2) size=min(strlength(buf),ckintval(argv[1]));
730  else size=strlength(buf);}
731  else if (isint(strm)) {
732  fd=intval(strm);
733  buf=argv[1];
734  if (isvector(buf) && (elmtypeof(buf)==ELM_FOREIGN))
735  bufp=buf->c.foreign.chars;
736  else if (isstring(buf)) bufp=buf->c.str.chars;
737  else error(E_NOSTRING);
738  if (n>=3) size=min(strlength(buf),ckintval(argv[2]));
739  else size=strlength(buf);
740  if (n==4) offset=ckintval(argv[3]);}
741  else error(E_STREAM);
742  GC_REGION(size=read(fd, &bufp[offset],size););
743  count=makeint(size);
744  if (isstream(strm)) {
745  strm->c.stream.count=0; strm->c.stream.tail=count;}
746  if (size<0) return(makeint(-errno));
747  else return(count);}
748 
749 pointer UNIXWRITE(ctx,n,argv)
750 register context *ctx;
751 register int n;
752 pointer *argv;
753 /* (unix:write fd string [count])
754  (unix:write stream string [count]) */
755 { register pointer strm,buf;
756  register int size,fd;
757  byte *bufp;
758  ckarg2(2,3);
759  strm=argv[0];
760  if (isiostream(strm)) strm=strm->c.iostream.out;
761  if (isfilestream(strm)) {
762  if (strm->c.stream.direction!=K_OUT) error(E_IODIRECTION);
763  if (isint(strm->c.fstream.fname)) error(E_STREAM);
764  fd=intval(strm->c.fstream.fd);}
765  else if (isint(strm)) fd=intval(strm);
766  else error(E_STREAM);
767  buf=argv[1];
768  if (isvector(buf) && (elmtypeof(buf)==ELM_FOREIGN))
769  bufp=buf->c.foreign.chars;
770  else if (isstring(buf)) bufp=buf->c.str.chars;
771  else error(E_NOSTRING);
772  size=strlength(buf);
773  if (n==3) size=min(size,ckintval(argv[2]));
774  size=write(fd,bufp,size);
775  return(makeint(size));}
776 
777 
778 pointer UNIXCLOSE(ctx,n,argv)
779 register context *ctx;
780 int n;
781 pointer argv[];
782 { ckarg(1);
783  if (close(ckintval(argv[0]))==0) return(T); else return(makeint(errno));}
784 
785 
786 #if !Cygwin /* Cygwin does not have lockf */
787 pointer LOCKF(ctx,n,argv)
788 register context *ctx;
789 int n;
790 pointer argv[];
791 { register pointer a=argv[0];
792  int fd,func,size,result;
793  ckarg2(2,3);
794  if (isiostream(a)) a=a->c.iostream.out;
795  if (isfilestream(a)) fd=intval(a->c.fstream.fd);
796  else if (isint(argv[0])) fd=intval(argv[0]);
797  else error(E_STREAM);
798  func= ckintval(argv[1]);
799  if (n==3) size=ckintval(argv[2]);
800  else size=0;
801  result=lockf(fd,func,size);
802  return(makeint(result));}
803 #endif
804 
805 #include <fcntl.h>
806 pointer FCNTL(ctx,n,argv)
807 register context *ctx;
808 int n;
809 pointer argv[];
810 { register pointer a=argv[0]; int fd,result;
811  ckarg(3);
812  if (isiostream(a)) a=a->c.iostream.in;
813  if (isfilestream(a)) fd=intval(a->c.fstream.fd);
814  else if (isint(argv[0])) fd=intval(argv[0]);
815  else error(E_STREAM);
816  result=fcntl(fd,ckintval(argv[1]),ckintval(argv[2]));
817  return(makeint(result));}
818 
819 
820 pointer IOCTL(ctx,n,argv)
821 register context *ctx;
822 int n;
823 register pointer argv[];
824 { register pointer strm;
825  eusinteger_t ctlarg;
826  int request;
827  int fd;
828  ckarg(3);
829  strm=argv[0];
830  if (isiostream(strm)) strm=strm->c.iostream.out;
831  if (isfilestream(strm)) {
832  fd=intval(strm->c.fstream.fd);
833  if (isint(strm->c.fstream.fname)) error(E_STREAM);}
834  else fd=ckintval(argv[0]);
835  if (isint(argv[1])) request=ckintval(argv[1]);
836  else if (isflt(argv[1])) error(E_NOINT);
837  else request=argv[1]->c.ivec.iv[0];
838  if (isstring(argv[2])) ctlarg=(eusinteger_t)(argv[2]->c.str.chars);/* ???? */
839  else ctlarg=ckintval(argv[2]);
840  return(makeint(ioctl(fd,request,ctlarg)));
841  }
842 
843 
844 #if !vxworks && !Solaris2
845 int bytesize(p)
846 pointer p;
847 { register int s=vecsize(p);
848  switch (elmtypeof(p)) {
849  case ELM_BIT: return((s+7)/8);
850  case ELM_BYTE: case ELM_CHAR: case ELM_FOREIGN: return(s);
851  case ELM_FLOAT: return(s*sizeof(float));
852  case ELM_INT: return(s*sizeof(int));
853  default: return(s*sizeof(pointer));}}
854 
855 #if Linux_ppc
856 #define IOC_IN _IOC_READ
857 #define IOC_OUT _IOC_WRITE
858 #define IOC_INOUT (IOC_IN | IOC_OUT)
859 #endif
860 
861 
862 pointer IOCTL_(ctx,n,argv)
863 register context *ctx;
864 /* (UNIX:IOCTL_ stream command1 command2) */
865 /* equivalent to C's ioctl(dev, _IO(command1, command2), addr) */
866 int n;
867 register pointer argv[];
868 { register pointer strm;
869  int size=0,x,y,fd;
870  eusinteger_t addr;
871  ckarg(3);
872  strm=argv[0];
873  if (isiostream(strm)) strm=strm->c.iostream.out;
874  if (isfilestream(strm)) fd=intval(strm->c.fstream.fd);
875  else fd=ckintval(strm);
876  if (isint(strm->c.fstream.fname)) error(E_STREAM);
877  x=ckintval(argv[1]); y=ckintval(argv[2]);
878 #if alpha || Linux_ppc
879  if (ioctl(fd,_IO(x, y), addr))
880 #else
881  if (ioctl(fd,IOC_VOID | (size<<16) | (x<<8) | y, addr))
882 #endif
883  return(makeint(-errno));
884  else return(T); }
885 
886 pointer IOCTL_R(ctx,n,argv)
887 register context *ctx;
888 /* (UNIX:IOCTL_R stream x y buffer [size]) */
889 /* equivalent to C's ioctl(dev, _IORN(size, x, y), addr) */
890 int n;
891 register pointer argv[];
892 { register pointer strm;
893  int size,x,y,fd;
894  eusinteger_t addr;
895  ckarg2(4,5);
896  strm=argv[0];
897  if (isiostream(strm)) strm=strm->c.iostream.out;
898  if (isfilestream(strm)) fd=intval(strm->c.fstream.fd);
899  else fd=ckintval(strm);
900  if (isint(strm->c.fstream.fname)) error(E_STREAM);
901  x=ckintval(argv[1]); y=ckintval(argv[2]);
902  if (isstring(argv[3]) || isintvector(argv[3]))
903  addr=(eusinteger_t)(argv[3]->c.str.chars);/* ???? */
904  else error(E_NOSTRING);
905  if (n==5) size=ckintval(argv[4]);
906  else size=bytesize(argv[3]);
907 #if alpha
908  if (ioctl(fd,_IOC(IOC_OUT, x, y, size), addr))
909 #else
910  if (ioctl(fd,IOC_OUT | (size<<16) | (x<<8) | y, addr))
911 #endif
912  return(makeint(-errno));
913  else return(T); }
914 
915 pointer IOCTL_W(ctx,n,argv)
916 register context *ctx;
917 /* (UNIX:IOCTL_W stream x y buffer [size]) */
918 /* equivalent to C's ioctl(dev, _IOWN(size, x, y), addr) */
919 int n;
920 register pointer argv[];
921 { register pointer strm;
922  int size,x,y,fd;
923  eusinteger_t addr;
924  ckarg2(4,5);
925  strm=argv[0];
926  if (isiostream(strm)) strm=strm->c.iostream.out;
927  if (isfilestream(strm)) fd=intval(strm->c.fstream.fd);
928  else fd=ckintval(strm);
929  if (isint(strm->c.fstream.fname)) error(E_STREAM);
930  x=ckintval(argv[1]); y=ckintval(argv[2]);
931  if (isstring(argv[3]) || isintvector(argv[3]))
932  addr=(eusinteger_t)(argv[3]->c.str.chars);/* ???? */
933  else error(E_NOSTRING);
934  if (n==5) size=ckintval(argv[4]);
935  else size=bytesize(argv[3]);
936 #if alpha || Linux_ppc
937  if (ioctl(fd,_IOC(IOC_IN, x, y, size), addr))
938 #else
939  if (ioctl(fd,IOC_IN | (size<<16) | (x<<8) | y, addr))
940 #endif
941  return(makeint(-errno));
942  else return(T); }
943 
944 #if !Cygwin /* Cygwin does not have IOC_INOUT */
945 pointer IOCTL_WR(ctx,n,argv)
946 register context *ctx;
947 /* (UNIX:IOCTL_WR stream x y buffer [size]) */
948 /* equivalent to C's ioctl(dev, _IOWRN(size, x, y), addr) */
949 int n;
950 register pointer argv[];
951 { register pointer strm=argv[0];
952  int size,x,y,fd;
953  eusinteger_t addr;
954 
955  ckarg2(4,5);
956  if (isiostream(strm)) strm=strm->c.iostream.out;
957  if (isfilestream(strm)) fd=intval(strm->c.fstream.fd);
958  else fd=ckintval(strm);
959  if (isint(strm->c.fstream.fname)) error(E_STREAM);
960  x=ckintval(argv[1]); y=ckintval(argv[2]);
961  if (isstring(argv[3]) || isintvector(argv[3]))
962  addr=(eusinteger_t)(argv[3]->c.str.chars);
963  else error(E_NOSTRING);
964  if (n==5) size=ckintval(argv[4]);
965  else size=bytesize(argv[3]);
966 #if alpha || Linux_ppc
967  if (ioctl(fd,_IOC(IOC_INOUT, x, y, size), addr))
968 #else
969  if (ioctl(fd,IOC_INOUT | (size <<16) | (x<<8) | y, addr))
970 #endif
971  return(makeint(-errno)) ;
972  else return(T); }
973 #endif /*Cygwin*/
974 
975 #endif /*vxworks*/
976 
977 /* DUP and DUP2 work only for numeric fd, not for stream obj.*/
978 #if !vxworks
979 
980 pointer DUP(ctx,n,argv)
981 register context *ctx;
982 int n;
983 pointer *argv;
984 { int newfd,oldfd;
985  ckarg(1);
986  oldfd=ckintval(argv[0]);
987  newfd=dup(oldfd);
988  return(makeint(newfd));}
989 
990 pointer DUP2(ctx,n,argv)
991 register context *ctx;
992 int n;
993 pointer *argv;
994 { int newfd,oldfd,stat;
995  ckarg(2);
996  newfd=ckintval(argv[0]);
997  oldfd=ckintval(argv[1]);
998  stat=dup2(newfd,oldfd);
999  return(makeint(stat));}
1000 
1001 pointer MKNOD(ctx,n,argv)
1002 register context *ctx;
1003 int n;
1004 pointer *argv;
1005 { int stat;
1006  ckarg(2);
1007  stat=mknod((char *)Getstring(argv[0])->c.str.chars,ckintval(argv[1]),0);
1008  if (stat<0) return(makeint(-errno));
1009  else return(T);}
1010 
1011 pointer MKDIR(ctx, n, argv)
1012 register context *ctx;
1013 int n;
1014 pointer *argv;
1015 { int stat, mode;
1016  ckarg2(1,2);
1017  if (n==2) mode=ckintval(argv[1]); else mode=0775;
1018  stat=mkdir((char *)Getstring(argv[0])->c.str.chars,mode);
1019  if (stat<0) return(makeint(-errno));
1020  else return(T);}
1021 
1022 pointer LINK(ctx,n,argv)
1023 register context *ctx;
1024 int n;
1025 pointer argv[];
1026 { int stat;
1027  ckarg(2);
1028  stat=link(Getstring(argv[0])->c.str.chars,Getstring(argv[1])->c.str.chars);
1029  if (stat<0) return(makeint(-errno)); else return(T);}
1030 
1031 pointer UNLINK(ctx,n,argv)
1032 register context *ctx;
1033 int n;
1034 pointer argv[];
1035 { pointer s;
1036  int stat;
1037  ckarg(1);
1038  s=Getstring(argv[0]);
1039  stat=unlink(s->c.str.chars);
1040  if (stat<0) return(makeint(-errno));
1041  else return(T);}
1042 
1043 pointer RMDIR(ctx,n,argv)
1044 register context *ctx;
1045 int n;
1046 pointer argv[];
1047 { pointer s;
1048  int stat;
1049  ckarg(1);
1050  s=Getstring(argv[0]);
1051  stat=rmdir(s->c.str.chars);
1052  if (stat<0) return(makeint(-errno));
1053  else return(T);}
1054 
1055 pointer RENAME(ctx,n,argv) /*(rename from to)*/
1056 register context *ctx;
1057 int n;
1058 register pointer argv[];
1059 { byte *from, *to;
1060  int stat;
1061  ckarg(2);
1062  from =(byte *)get_string(argv[0]);
1063  to =(byte *)get_string(argv[1]);
1064  stat=rename((char *)from,(char *) to);
1065  if (stat<0) return(makeint(-errno));
1066  else return(T);}
1067 
1068 pointer ACCESS(ctx,n,argv)
1069 register context *ctx;
1070 int n;
1071 pointer *argv;
1072 { pointer path;
1073  int mode,stat;
1074  ckarg2(1,2);
1075  path=Getstring(argv[0]);
1076  if (n==2) mode=ckintval(argv[1]); else mode=0;
1077  stat=access(path->c.str.chars,mode);
1078  if (stat==0) return(T); else return(makeint(-errno));}
1079 
1080 /*
1081 pointer FLOCK(ctx,n,argv)
1082 register context *ctx;
1083 int n;
1084 pointer argv[];
1085 { int fd=ckintval(argv[0]), op=ckintval(argv[1]), stat;
1086  ckarg(2);
1087  stat=flock(fd,op);
1088  if (stat==0) return(T); else return(makeint(-errno));}
1089 */
1090 
1091 pointer STAT(ctx,n,argv)
1092 register context *ctx;
1093 int n;
1094 pointer *argv;
1095 { register pointer a;
1096  struct stat s;
1097  ckarg(1);
1098  if (stat((char *)Getstring(argv[0])->c.str.chars, &s)<0) return(makeint(-errno));
1099  a=cons(ctx,mkbigint(s.st_ctime),NIL);
1100  a=cons(ctx,mkbigint(s.st_mtime),a);
1101  a=cons(ctx,mkbigint(s.st_atime),a);
1102  a=cons(ctx,makeint(s.st_size),a);
1103  a=cons(ctx,makeint(s.st_gid),a);
1104  a=cons(ctx,makeint(s.st_uid),a);
1105  a=cons(ctx,makeint(s.st_nlink),a);
1106  a=cons(ctx,makeint(s.st_rdev),a);
1107  a=cons(ctx,makeint(s.st_dev),a);
1108  a=cons(ctx,makeint(s.st_ino),a);
1109  a=cons(ctx,makeint(s.st_mode),a);
1110  return(a);}
1111 #endif /* !vxworks*/
1112 
1113 #if Solaris2 || Linux || alpha || Cygwin
1114 /*
1115  Usage: (unix::directory "directory_name")
1116  Return: a reverse list of file names in "directory_name" dir.
1117 */
1118 
1119 pointer DIRECTORY(ctx, n, argv)
1120 register context *ctx;
1121 int n;
1122 pointer argv[];
1123 { register pointer a;
1124  register char *str;
1125  byte *s;
1126  DIR *dirp;
1127  struct dirent *direntp;
1128  int flag=0;
1129 
1130  ckarg2(0,1);
1131  if (n==1) s=get_string(argv[0]); else s=(byte *)".";
1132  if ( (dirp = opendir((char *)s)) == NULL ) return (NIL);
1133  while ( (direntp = readdir( dirp )) != NULL ){
1134  str=direntp->d_name;
1135  if(flag) a=cons(ctx,makestring(str,strlen(str)),a);
1136  else { a=cons(ctx,makestring(str,strlen(str)),NIL); flag++;}
1137  }
1138  closedir(dirp);
1139  return (a);
1140 }
1141 #else
1142 pointer DIRECTORY(ctx, n, argv)
1143 register context *ctx;
1144 int n;
1145 pointer argv[];
1146 {
1147  printf("Not Implemented!");
1148  return (NIL);
1149 }
1150 #endif
1151 
1152 pointer LSEEK(ctx,n,argv)
1153 register context *ctx;
1154 int n;
1155 pointer *argv;
1156 { pointer strm,fd;
1157  int whence, ret;
1158  ckarg2(2,3);
1159  if (n==3) whence=ckintval(argv[2]); else whence=0;
1160  strm=argv[0];
1161  if (isiostream(strm)) strm=strm->c.iostream.out;
1162  if (isfilestream(strm)){
1163  fd=strm->c.fstream.fd;
1164  if (isint(strm->c.fstream.fname)) error(E_STREAM);}
1165  else fd=strm;
1166  if (!isint(fd)) error(E_STREAM);
1167  ret=lseek(intval(fd),ckintval(argv[1]),whence);
1168  if (ret==-1) perror("lseek");
1169  return(makeint(ret)); }
1170 
1171 #if !vxworks
1172 /*change current working directory*/
1173 pointer CHDIR(ctx,n,argv)
1174 register context *ctx;
1175 int n;
1176 pointer argv[];
1177 { register int stat;
1178  ckarg(1);
1179  stat=chdir(Getstring(argv[0])->c.str.chars);
1180  if (stat<0) return(makeint(-errno)); else return(T);}
1181 
1182 /*change file access mode*/
1183 pointer CHMOD(ctx,n,argv)
1184 register context *ctx;
1185 int n;
1186 pointer *argv;
1187 { byte *path;
1188  int mode,stat;
1189  ckarg(2);
1190  path=Getstring(argv[0])->c.str.chars;
1191  mode=ckintval(argv[1]);
1192  stat=chmod((char *)path,mode);
1193  if (stat==0) return(T); else return(makeint(errno));}
1194 
1195 /*change file owner*/
1196 pointer CHOWN(ctx,n,argv)
1197 register context *ctx;
1198 int n;
1199 pointer *argv;
1200 { byte *path;
1201  int owner,newowner,stat;
1202  ckarg(3);
1203  path=Getstring(argv[0])->c.str.chars;
1204  owner=ckintval(argv[1]);
1205  newowner=ckintval(argv[2]);
1206  stat=chown(path,owner,newowner);
1207  if (stat==0) return(T); else return(makeint(errno));}
1208 
1209 /*create two pipes*/
1210 pointer PIPE(ctx,n,argv)
1211 register context *ctx;
1212 int n;
1213 pointer *argv;
1214 { int pfd[2],stat,size;
1215  register pointer instream,outstream;
1216 
1217  ckarg2(0,1);
1218  if (n==1) size=ckintval(argv[0]); else size=128;
1219  stat=pipe(pfd);
1220  if (stat<0) return(makeint(-errno));
1221  instream=mkfilestream(ctx,K_IN,makebuffer(size),pfd[0],NIL); /*no file named*/
1222  vpush(instream);
1223  outstream=mkfilestream(ctx,K_OUT,makebuffer(size),pfd[1],NIL);
1224  return((pointer)mkiostream(ctx,vpop(),outstream));
1225  }
1226 
1227 
1228 /* message queu operations */
1229 #if !news
1230 pointer MSGGET(ctx,n,argv)
1231 register context *ctx;
1232 int n;
1233 pointer argv[];
1234 { register int key,qid,mode;
1235  ckarg2(1,2);
1236  key=ckintval(argv[0]);
1237  if (n==2) mode=ckintval(argv[1]); else mode=0666;
1238  qid=msgget(key,IPC_CREAT | (mode & 0777));
1239  return(makeint(qid));}
1240 
1241 pointer MSGRCV(ctx,n,argv)
1242 register context *ctx;
1243 int n;
1244 pointer *argv;
1245 { register int qid,mtype,flag,stat;
1246  register pointer buf,lsave;
1247  ckarg2(2,4);
1248  qid=ckintval(argv[0]);
1249  buf=argv[1];
1250  if (!isstring(buf)) error(E_NOSTRING);
1251  if (n>=3) mtype=ckintval(argv[2]); else mtype=0;
1252  if (n==4) if (argv[3]==NIL) flag=0; else flag=IPC_NOWAIT;
1253  else flag=0;
1254  lsave=buf->c.str.length;
1255  buf->c.str.length=(pointer)(eusinteger_t)mtype;/* ???? */
1256  rcv_again:
1257  stat=msgrcv(qid,&buf->c.str.length,intval(lsave),mtype,flag);
1258  if (stat<0) { breakck; goto rcv_again;}
1259  mtype=(int)(eusinteger_t)(buf->c.str.length);/* ???? */
1260  buf->c.str.length=lsave;
1261  if (stat<0) return(makeint(-errno));
1262  else return(cons(ctx,makeint(mtype),cons(ctx,makeint(stat),NIL)));}
1263 
1264 pointer MSGSND(ctx,n,argv)
1265 register context *ctx;
1266 int n;
1267 pointer *argv;
1268 { register int qid,msize,mtype,flag,stat;
1269  register pointer buf,lsave;
1270  ckarg2(2,5);
1271  qid=ckintval(argv[0]);
1272  buf=argv[1];
1273  if (!isstring(buf)) error(E_NOSTRING);
1274  lsave=buf->c.str.length;
1275  if (n>=3) {
1276  msize=ckintval(argv[2]);
1277  if (msize>intval(lsave) || msize<0) error(E_ARRAYINDEX);}
1278  else msize=intval(lsave);
1279  if (n>=4) mtype=ckintval(argv[3]); else mtype=mypid;
1280  if (n==5) if (argv[4]==NIL) flag=0; else flag=IPC_NOWAIT;
1281  else flag=0;
1282  buf->c.str.length=(pointer)(eusinteger_t)mtype;
1283  stat=msgsnd(qid,(struct msgbuf *)&buf->c.str.length,msize,flag);
1284  buf->c.str.length=lsave;
1285  if (stat<0) return(makeint(-errno));
1286  else return(makeint(stat));}
1287 
1288 pointer MSGCTL(ctx,n,argv)
1289 register context *ctx;
1290 int n;
1291 pointer argv[];
1292 { int qid,cmnd,stat;
1293  byte *buf;
1294  ckarg2(2,3);
1295  qid=ckintval(argv[0]); cmnd=ckintval(argv[1]);
1296  if (n==3) buf=get_string(argv[2]);
1297  else buf=NULL;
1298  stat=msgctl(qid,cmnd,(struct msqid_ds *)buf);
1299  if (stat==(long int)NULL) return(T); else return(makeint(-errno));}
1300 #endif
1301 #endif
1302 
1303 /****************************************************************/
1304 /* UNIX subroutines
1305 /****************************************************************/
1306 
1307 pointer SYSTEM(ctx,n,argv)
1308 register context *ctx;
1309 int n;
1310 register pointer argv[];
1311 { int stat;
1312  eusinteger_t s;
1313 /* extern int eusint(); */
1314  extern void eusint(); /* ???? */
1315 
1316  s=(eusinteger_t)signal(SIGCHLD,SIG_DFL);/* ???? */
1317  if (n==0) stat=system("csh");
1318  else if (isstring(argv[0])) stat=system((char *)argv[0]->c.str.chars);
1319  else { signal(SIGCHLD,(void (*)())s); error(E_NOSTRING);}
1320  signal(SIGCHLD,(void (*)())s);
1321  return(makeint(stat));}
1322 
1323 pointer GETWD(ctx,n,argv)
1324 register context *ctx;
1325 int n;
1326 pointer argv[];
1327 { char buf[256];
1328  ckarg(0);
1329 #if Solaris2 || Linux || Cygwin
1330  char *r = getcwd(buf,256);
1331 #else
1332  getwd(buf);
1333 #endif
1334  return(makestring(buf,strlen(buf)));}
1335 
1336 pointer GETENV(ctx,n,argv)
1337 register context *ctx;
1338 int n;
1339 pointer *argv;
1340 { register char *envval;
1341  ckarg(1);
1342  envval=(char *)getenv((char *)Getstring(argv[0])->c.str.chars);
1343  if (envval) return(makestring(envval,strlen(envval)));
1344  else return(NIL);}
1345 
1346 #if sun3 || sun4 || vax || mips || alpha || Linux
1347 pointer PUTENV(ctx,n,argv)
1348 register context *ctx;
1349 int n;
1350 pointer argv[];
1351 {
1352  char *b;
1353  pointer a=argv[0];
1354  ckarg(1);
1355  if (!isstring(a)) error(E_NOSTRING);
1356  b= (char *)malloc(vecsize(a)+1);
1357  strcpy(b, (char *)a->c.str.chars);
1358  putenv(b);
1359  return(makeint((eusinteger_t)b));}
1360 #endif
1361 
1362 pointer ENVIRON(context *ctx, int n, pointer argv[])
1363 { extern char **environ;
1364  char *b;
1365  int count=0;
1366  ckarg(0);
1367  while ((b=environ[count++])) {
1368  vpush(makestring(b, strlen(b)));}
1369  return(stacknlist(ctx, count-1)); }
1370 
1371 pointer SLEEP(ctx,n,argv)
1372 register context *ctx;
1373 int n;
1374 pointer *argv;
1375 { ckarg(1);
1376  struct timespec treq;
1377  GC_REGION(treq.tv_sec=ckintval(argv[0]));;
1378  treq.tv_nsec = 0;
1379  if (nanosleep(&treq, NULL)<0) return(NIL);
1380  return(T);}
1381 
1382 
1383 #if sun3 || sun4 && !Solaris2 || Linux || alpha || Cygwin
1384 pointer USLEEP(ctx,n,argv)
1385 register context *ctx;
1386 int n;
1387 pointer *argv;
1388 { ckarg(1);
1389  struct timespec treq;
1390  GC_REGION(treq.tv_sec = ckintval(argv[0])/1000000;
1391  treq.tv_nsec = (ckintval(argv[0])%1000000)*1000);
1392  if (nanosleep(&treq, NULL)<0) return(NIL);
1393  return(T);}
1394 #endif
1395 
1396 pointer ERRNO(ctx,n,argv)
1397 context *ctx;
1398 int n;
1399 pointer argv[];
1400 {
1401  return(makeint(errno));
1402  }
1403 
1404 pointer PERROR(ctx,n,argv)
1405 context *ctx;
1406 int n;
1407 pointer argv[];
1408 {
1409  ckarg(1);
1410  char *s=Getstring(argv[0])->c.str.chars;
1411  fprintf(stderr, "%c[3%cm;; ERROR ", 0x1b, 49);
1412  perror(s);
1413  fprintf(stderr, "%c[0m", 0x1b);
1414  return T;
1415  }
1416 
1417 pointer SYSERRLIST(ctx,n,argv)
1418 register context *ctx;
1419 register int n;
1420 pointer argv[];
1421 { int i;
1422  char *errstr;
1423  int errno_save;
1424  ckarg(1);
1425  n=ckintval(argv[0]);
1426  errno_save=errno;
1427  errstr=strerror(n);
1428  if (errno==errno_save) return(makestring(errstr, strlen(errstr)));
1429  else error(E_ARRAYINDEX);}
1430 
1431 pointer PAUSE(ctx,n,argv)
1432 register context *ctx;
1433 int n;
1434 pointer argv[];
1435 { ckarg(0);
1436  return(makeint(pause()));}
1437 
1438 pointer ISATTY(ctx,n,argv)
1439 register context *ctx;
1440 int n;
1441 pointer argv[];
1442 { pointer a;
1443  int fd;
1444  ckarg(1);
1445  a=argv[0];
1446  if (isiostream(a)) a=a->c.iostream.in;
1447  if (isfilestream(a)) fd=intval(a->c.fstream.fd);
1448  else fd=ckintval(a);
1449  /*
1450 #if Cygwin
1451  if (getenv("EMACS") && (strcmp (getenv("EMACS"), "t")) == 0 ) return(T);
1452 #endif
1453  */
1454  if (isatty(fd)) return(T); else return(NIL);}
1455 
1456 
1457 /****************************************************************/
1458 /* functions for I P C (interprocess communication)
1459 /* using sockets
1460 /* 1988-Jan socket for internet
1461 /* 1988-Feb select system call
1462 /****************************************************************/
1463 
1464 pointer SOCKET(ctx,n,argv)
1465 register context *ctx;
1466 int n;
1467 pointer argv[];
1468 { int proto,s;
1469  ckarg2(2,3);
1470  if (n==3) proto=ckintval(argv[2]);
1471  else proto=0;
1472  s=socket(ckintval(argv[0]),ckintval(argv[1]),proto);
1473  if (s<0) return(makeint(-errno));
1474  else return(makeint(s)); }
1475 
1476 pointer BIND(ctx,n,argv) /*bind ipc socket to real path name*/
1477 register context *ctx;
1478 int n;
1479 register pointer argv[];
1480 { int s,l;
1481  pointer sockname;
1482  struct sockaddr *sa;
1483 
1484  ckarg(2);
1485  s=ckintval(argv[0]); /*socket id*/
1486  if (!isstring(argv[1])) error(E_USER,(pointer)"socket address expected");
1487  sa= (struct sockaddr *)(argv[1]->c.str.chars);
1488  if (sa->sa_family==AF_UNIX) l=strlen(sa->sa_data)+2;
1489  else l=sizeof(struct sockaddr_in);
1490  s=(int)bind(s, sa, l);
1491  if (s) return(makeint(-errno)); else return(makeint(0));}
1492 
1493 pointer CONNECT(ctx,n,argv)
1494 register context *ctx;
1495 int n;
1496 pointer argv[];
1497 { int s,l;
1498  struct sockaddr *sa;
1499  ckarg(2);
1500  s=ckintval(argv[0]); /*socket id*/
1501  if (!isstring(argv[1])) error(E_USER,(pointer)"socket address expected");
1502  sa= (struct sockaddr *)(argv[1]->c.str.chars);
1503  if (sa->sa_family==AF_UNIX) l=strlen(sa->sa_data)+2;
1504  else l=sizeof(struct sockaddr_in);
1505  s=(int)connect(s, sa, l);
1506  breakck;
1507  if (s) return(makeint(-errno)); else return(makeint(0));
1508 }
1509 
1510 pointer LISTEN(ctx,n,argv)
1511 register context *ctx;
1512 int n;
1513 pointer argv[];
1514 { int backlog,stat;
1515  ckarg2(1,2);
1516  if (n==2) backlog=ckintval(argv[1]);
1517  else backlog=3;
1518  stat=listen(ckintval(argv[0]),backlog);
1519  if (stat<0) return(makeint(-errno)); else return(makeint(0));}
1520 
1521 pointer ACCEPT(ctx,n,argv)
1522 register context *ctx;
1523 int n;
1524 pointer argv[];
1525 { int ns,len,s;
1526  pointer sockname;
1527 #if vxworks || Cygwin || Linux || Solaris2
1528  struct sockaddr sockun;
1529 #else
1530  struct sockaddr_un sockun; // ??? why not sockaddr or sockaddr_in ???
1531 #endif
1532 
1533  ckarg(1);
1534  len=sizeof(sockun);
1535  s=ckintval(argv[0]);
1536  ns=accept(s, (struct sockaddr *)&sockun, &len);
1537  if (ns<0) return(makeint(-errno));
1538  sockname=makestring((char *)&sockun,len);
1539  return(cons(ctx,makeint(ns),cons(ctx,sockname,NIL)));}
1540 
1541 /* non-connected (datagram) socket communication */
1542 /* Address must be bound to a socket at the receiver side. */
1543 /* Sender specifies the address when it calls SENDTO. */
1544 pointer SENDTO(ctx,n,argv)
1545 register context *ctx;
1546 int n;
1547 pointer argv[];
1548 /* unix: sendto(sock,msg,len,flags,to,tolen) */
1549 /* eus: (SENDTO sock addr msg [len [flags]]) */
1550 { int len, sock, flags, stat;
1551  pointer msg, addr;
1552  ckarg2(3,5);
1553  sock=ckintval(argv[0]);
1554  addr=(pointer)Getstring(argv[1]);
1555  msg=(pointer)Getstring(argv[2]);
1556  if (n>=4) len=ckintval(argv[3]); else len=vecsize(msg);
1557  if (n>=5) flags=ckintval(argv[4]); else flags=0;
1558  stat=sendto(sock, (char *)msg->c.str.chars, len, flags,
1559  (struct sockaddr *)addr->c.str.chars, vecsize(addr));
1560  if (stat<0) stat= -errno;
1561  /* returns the number of bytes actually sent*/
1562  return(makeint(stat));}
1563 
1564 pointer RECVFROM(ctx,n,argv)
1565 register context *ctx;
1566 int n;
1567 pointer argv[];
1568 /* unix: recvfrom(s,buf,len,flags,from,fromlen) */
1569 /* eus: (RECVFROM sock [msg [from [flags]]])
1570  no address is required since it has already bound to
1571  the socket */
1572 { int len=2000, sock, flags, stat, addrlen;
1573  unsigned char buf[2000], *bufp=buf, *addrp=NULL;
1574  pointer msg, addr;
1575  ckarg2(1,4);
1576  sock=ckintval(argv[0]);
1577  if (n>=2) {
1578  msg=argv[1];
1579  if (isstring(msg)) msg=(pointer)Getstring(argv[1]); /*message buffer*/
1580  else msg=makebuffer(ckintval(argv[1]));
1581  bufp=msg->c.str.chars;
1582  len=vecsize(msg);}
1583  if (n>=3) {
1584  addr=Getstring(argv[2]);
1585  addrlen=vecsize(addr);
1586  addrp=addr->c.str.chars;}
1587  if (n>=4) flags=ckintval(argv[3]); else flags=0;
1588  stat=recvfrom(sock, (char *)bufp, len, flags, (struct sockaddr *)addrp, &addrlen);
1589  if (stat<0) return(makeint(-errno));
1590  /* if the result is negative, it indicates error number,
1591  otherwise, the actual length of the message is returned. */
1592  if (n<2) return(makestring((char *)bufp,stat));
1593  else return(makeint(stat));}
1594 
1595 #if !Solaris2
1596 pointer GETPEERNAME(ctx,n,argv)
1597 register context *ctx;
1598 int n;
1599 pointer argv[];
1600 { char name[128];
1601  int namelen, stat;
1602  ckarg(1);
1603  stat=getpeername(ckintval(argv[0]), (struct sockaddr *)name, &namelen);
1604  if (stat<0) return(makeint(-errno));
1605  else return(makestring(name,namelen));}
1606 #endif
1608 #if !vxworks
1609 
1610 eusinteger_t *checkbitvec(pointer a, long *size)
1611 { if (a==NIL) { *size=0; return(0);}
1612  if (!isvector(a)) error(E_NOVECTOR);
1613  switch(elmtypeof(a)) {
1614  case ELM_BIT: *size=vecsize(a); return(a->c.ivec.iv);
1615  case ELM_INT: *size=vecsize(a) * WORD_SIZE; return(a->c.ivec.iv);
1616  case ELM_BYTE: case ELM_CHAR:
1617  *size=vecsize(a) * 8; return(a->c.ivec.iv);
1618  case ELM_FOREIGN: *size=vecsize(a) * 8; return((eusinteger_t *)a->c.foreign.chars);
1619  default: error(E_USER,(pointer)"bit-vector expected");
1620  }
1621 }
1622 
1623 pointer SELECT(ctx,n,argv)
1624 register context *ctx;
1625 int n;
1626 register pointer argv[];
1627 { register pointer a=argv[0];
1628  long i, maxwidth, width,size0, size1, size2;
1629  fd_set *readfds, *writefds, *exceptfds;
1630  eusfloat_t timeout;
1631  struct timeval to;
1632  numunion nu;
1633 
1634  ckarg(4);
1635  readfds=(fd_set *)checkbitvec(argv[0], &size0);
1636  writefds=(fd_set *)checkbitvec(argv[1], &size1);
1637  exceptfds=(fd_set *)checkbitvec(argv[2], &size2);
1638  maxwidth=min(256, max(max(size0, size1), size2));
1639 
1640 /* printf("SELECT: readfds=%x\n", readfds);
1641  printf("SELECT: writefds=%x\n", writefds);
1642  printf("SELECT: exceptfds=%x\n", exceptfds); */
1643 
1644  /* find the highest numbered fd */
1645  width=0;
1646  for (i=0; i<maxwidth; i++) {
1647  if (readfds && FD_ISSET(i, readfds)) width=i;
1648  if (writefds && FD_ISSET(i, writefds)) width=i;
1649  if (exceptfds && FD_ISSET(i, exceptfds)) width=i;}
1650  width = width + 1;
1651 
1652  timeout=ckfltval(argv[3]);
1653  if (timeout==0.0)
1654  {GC_REGION(i=select(width, readfds, writefds, exceptfds,0););}
1655  else {
1656  to.tv_sec=timeout;
1657  timeout=timeout-to.tv_sec;
1658  timeout=timeout*1000000;
1659  to.tv_usec=timeout;
1660  GC_REGION(i=select(width, readfds, writefds, exceptfds,&to);)}
1661  if (i<0) return(makeint(-errno));
1662  else return(makeint(i)); }
1663 
1664 pointer SELECT_READ(ctx,n,argv)
1665 register context *ctx;
1666 int n;
1667 pointer argv[];
1668 { struct timeval to;
1669  eusfloat_t timeout;
1670  long i, size, width, fds;
1671  fd_set *fdvec;
1672  numunion nu;
1673 
1674  ckarg(2);
1675  if (isint(argv[0])) {
1676  fds=intval(argv[0]);
1677  fdvec=(fd_set *)&fds;
1678  size=30; }
1679  else fdvec=(fd_set *)checkbitvec(argv[0], &size);
1680  size=min(256,size);
1681  for (i=0; i<size; i++) if (FD_ISSET(i, fdvec)) width=i;
1682  width = width+1;
1683 
1684  timeout=ckfltval(argv[1]);
1685  if (timeout==0.0) {GC_REGION(n=select(width, fdvec, 0, 0, 0););}
1686  else {
1687  to.tv_sec=timeout;
1688  timeout=timeout-to.tv_sec;
1689  timeout=timeout*1000000;
1690  to.tv_usec=timeout;
1691  GC_REGION(n=select(width, fdvec, 0, 0, &to););}
1692  if (n<0) return(makeint(-errno));
1693  if (isint(argv[0])) {
1694  /*fds=fdvec-> __fds_bits[0];*/
1695  /* fds_bits should be __fds_bits on some operating systems */
1696  return(makeint(fds)); }
1697  else return(argv[0]); }
1698 
1699 #endif /* !vxworks */
1700 
1701 
1702 /****************************************************************/
1703 /* physical memory allocator
1704 /* 1988-Jul
1705 /****************************************************************/
1706 pointer SBRK(ctx,n,argv)
1707 register context *ctx;
1708 int n; pointer argv[];
1709  { return(makeint((eusinteger_t)sbrk(ckintval(argv[0]))));}
1710 
1711 pointer MALLOC(ctx,n,argv)
1712 register context *ctx;
1713 int n; pointer argv[];
1714  { return(makeint((eusinteger_t)malloc(ckintval(argv[0]))));}
1715 
1716 pointer FREE(ctx,n,argv)
1717 register context *ctx;
1718 int n; pointer argv[];
1719 { free((void *)bigintval(argv[0]));
1720  return(makeint(1));}
1721 
1722 #if sun3 || sun4 || news || alpha
1723 pointer VALLOC(ctx,n,argv)
1724 register context *ctx;
1725 int n; pointer argv[];
1726 { return(makeint(valloc(ckintval(argv[0]))));}
1727 #endif
1728 
1729 #if sun3 || sun4 || news || alpha || Linux || Cygwin
1730 
1731 pointer MMAP(ctx,n,argv)
1732 register context *ctx;
1733 int n; register pointer argv[];
1734 { int fd;
1735  eusinteger_t offset,result,len;
1736  pointer strm;
1737  ckarg(6);
1738  strm=argv[4];
1739  if (isiostream(strm)) strm=strm->c.iostream.in;
1740  if (isfilestream(strm)) fd=intval(strm->c.fstream.fd);
1741  else fd=ckintval(strm);
1742  len=ckintval(argv[1]);
1743  if (isintvector(argv[5]))
1744  offset=((argv[5]->c.ivec.iv[0])<<16) + argv[5]->c.ivec.iv[1];
1745  else offset=ckintval(argv[5]);
1746  result=(eusinteger_t)mmap((caddr_t)ckintval(argv[0]), len,
1747  ckintval(argv[2]), ckintval(argv[3]), fd, offset);
1748  if (result== -1) return(makeint(-errno));
1749  else return((pointer)make_foreign_string(result, len));}
1750 
1751 pointer MUNMAP(ctx,n,argv)
1752 register context *ctx;
1753 int n; pointer argv[];
1754 { return(makeint(munmap((caddr_t)ckintval(argv[0]),ckintval(argv[1]))));}
1755 
1756 /*
1757 pointer VADVISE(ctx,n,argv)
1758 register context *ctx;
1759 int n; pointer argv[];
1760 { n=vadvise(ckintval(argv[0]));
1761  if (n==0) return(T); else return(makeint(errno));}
1762 */
1763 
1764 #endif
1765 
1766 /****************************************************************/
1767 /* network library routines
1768 /****************************************************************/
1769 #if !vxworks
1770 
1771 pointer GETHOSTNAME(ctx,n,argv)
1772 register context *ctx;
1773 int n; pointer argv[];
1774 { char buf[32]; int stat;
1775  stat=gethostname(buf,32);
1776  if (stat==0) return(makestring(buf,strlen(buf)));
1777  else return(makeint(errno));}
1778 
1779 pointer GETHOSTBYNAME(ctx,n,argv)
1780 register context *ctx;
1781 int n;
1782 register pointer *argv;
1783 { register struct hostent *hp;
1784  register pointer s;
1785 
1786  ckarg(1);
1787  hp=gethostbyname((char *)Getstring(argv[0])->c.str.chars);
1788  if (hp==NULL) return(makeint(-errno));
1789  s=cons(ctx,makeint(hp->h_addrtype),NIL);
1790  s=cons(ctx,makestring(hp->h_addr,hp->h_length),s);
1791  return(s);} /*list of 32bit address and address type*/
1792 
1793 pointer GETHOSTBYADDR(ctx,n,argv)
1794 register context *ctx;
1795 int n;
1796 pointer *argv;
1797 { pointer addr;
1798  struct hostent *host;
1799  ckarg(1);
1800  addr=Getstring(argv[0]);
1801  host=gethostbyaddr((char *)addr->c.str.chars, vecsize(addr), 2);
1802  if (host==NULL) return(makeint(-errno));
1803  else return(makestring(host->h_name, strlen(host->h_name)));}
1804 
1805 #if !Cygwin /* Cygwin does not hvae getnetbyname */
1806 pointer GETNETBYNAME(ctx,n,argv)
1807 register context *ctx;
1808 int n;
1809 register pointer *argv;
1810 { struct netent *np;
1811  ckarg(1);
1812  np=getnetbyname((char *)Getstring(argv[0])->c.str.chars);
1813  if (np==NULL) return(makeint(-errno));
1814  return(cons(ctx,makeint(np->n_net),
1815  cons(ctx,makeint(np->n_addrtype),NIL)));}
1816 #endif
1817 
1818 pointer GETPROTOBYNAME(ctx,n,argv)
1819 register context *ctx;
1820 int n;
1821 register pointer *argv;
1822 { struct protoent *pp;
1823  ckarg(1);
1824  pp=getprotobyname((char *)Getstring(argv[0])->c.str.chars);
1825  if (pp==NULL) return(makeint(-errno));
1826  return(makeint(pp->p_proto));}
1827 
1828 pointer GETSERVBYNAME(ctx,n,argv)
1829 register context *ctx;
1830 int n;
1831 register pointer *argv;
1832 { struct servent *sp;
1833  pointer s;
1834  byte *p;
1835  long int port;
1836 
1837  ckarg2(1,2);
1838  if (n==2 && argv[1]!=NIL) p=Getstring(argv[1])->c.str.chars;
1839  else p=NULL;
1840  sp=getservbyname((char *)Getstring(argv[0])->c.str.chars,(char *)p);
1841  if (sp==NULL) return(makeint(-errno));
1842  s=makestring(sp->s_proto,strlen(sp->s_proto));
1843  vpush(s);
1844  port = ntohs(sp->s_port);
1845  s=cons(ctx,makeint(port),cons(ctx,s,NIL));
1846  vpop();
1847  return(s);}
1848 
1849 /* Append by I.Hara for IPC */
1850 /* htons -- convert values between host and network byte order */
1851 pointer H2NS(ctx,n,argv)
1852 register context *ctx;
1853 int n;
1854 register pointer *argv;
1855 { int hostshort;
1856  unsigned short netshort;
1857  ckarg(1);
1858  hostshort=ckintval(argv[0]);
1859  netshort=htons((short)hostshort);
1860  return(makeint(netshort));}
1861 
1862 pointer N2HS(ctx,n,argv)
1863 register context *ctx;
1864 int n;
1865 register pointer *argv;
1866 { int hostshort;
1867  unsigned short netshort;
1868  ckarg(1);
1869  netshort=ckintval(argv[0]);
1870  hostshort=ntohs((short)netshort);
1871  return(makeint(hostshort));}
1872 
1873 #endif
1874 
1875 
1876 
1877 
1878 #ifdef DBM
1879 /* ndbm --- data base
1880  1988-May
1881  (c) T.Matsui
1882 */
1883 
1884 #if sun3 || sun4
1885 
1886 #include <ndbm.h>
1887 
1888 pointer DBM_OPEN(ctx,n,argv)
1889 register context *ctx;
1890 int n;
1891 register pointer argv[];
1892 { DBM *dbm;
1893  ckarg(3);
1894  dbm=dbm_open(Getstring(argv[0])->c.str.chars,
1895  ckintval(argv[1]),
1896  ckintval(argv[2]));
1897  return(makeint(dbm));}
1898 
1899 pointer DBM_CLOSE(ctx,n,argv)
1900 register context *ctx;
1901 int n;
1902 register pointer argv[];
1903 { ckarg(1);
1904  dbm_close(ckintval(argv[0]));
1905  return(T);}
1906 
1907 pointer DBM_FETCH(ctx,n,argv)
1908 register context *ctx;
1909 int n;
1910 register pointer argv[];
1911 { register pointer s;
1912  datum key,content;
1913  ckarg(2);
1914  s=Getstring(argv[1]);
1915  key.dptr=(char *)(s->c.str.chars);
1916  key.dsize=strlength(s);
1917  content=dbm_fetch(ckintval(argv[0]), key);
1918  if (content.dptr==NULL) return(NIL);
1919  return(makestring(content.dptr,content.dsize));}
1920 
1921 pointer DBM_STORE(ctx,n,argv)
1922 register context *ctx;
1923 int n;
1924 register pointer argv[];
1925 { register pointer s;
1926  datum key,content;
1927  ckarg(4);
1928  s=Getstring(argv[1]);
1929  key.dptr=(char *)s->c.str.chars;
1930  key.dsize=strlength(s);
1931  s=Getstring(argv[2]);
1932  content.dptr=(char *)s->c.str.chars;
1933  content.dsize=strlength(s);
1934  n=dbm_store(ckintval(argv[0]), key, content, ckintval(argv[3]));
1935  return((n==0)?T:NIL);}
1936 
1937 pointer DBM_DELETE(ctx,n,argv)
1938 register context *ctx;
1939 int n;
1940 register pointer argv[];
1941 { register pointer s;
1942  datum key;
1943  ckarg(2);
1944  s=Getstring(argv[1]);
1945  key.dptr=(char *)s->c.str.chars;
1946  key.dsize=strlength(s);
1947  n=dbm_delete(ckintval(argv[0]), key);
1948  return((n==0)?T:NIL);}
1949 
1950 pointer DBM_FIRSTKEY(ctx,n,argv)
1951 register context *ctx;
1952 int n;
1953 register pointer argv[];
1954 { datum key;
1955  ckarg(1);
1956  key=dbm_firstkey(ckintval(argv[0]), key);
1957  if (key.dptr==NULL) return(NIL);
1958  return(makestring(key.dptr,key.dsize));}
1959 
1960 pointer DBM_NEXTKEY(ctx,n,argv)
1961 register context *ctx;
1962 int n;
1963 register pointer argv[];
1964 { datum key;
1965  ckarg(1);
1966  key=dbm_nextkey(ckintval(argv[0]), key);
1967  if (key.dptr==NULL) return(NIL);
1968  return(makestring(key.dptr,key.dsize));}
1969 
1970 pointer DBM_ERROR(ctx,n,argv)
1971 register context *ctx;
1972 int n;
1973 register pointer argv[];
1974 { ckarg(1);
1975  n=dbm_error((DBM *)ckintval(argv[0]));
1976  return((n==0)?T:NIL);}
1977 
1978 pointer DBM_CLEARERR(ctx,n,argv)
1979 register context *ctx;
1980 int n;
1981 register pointer argv[];
1982 { ckarg(1);
1983  dbm_clearerr((DBM *)ckintval(argv[0]));
1984  return(T);}
1985 
1986 #endif /*sun3 || sun4*/
1987 #endif /*ifdef DBM*/
1988 
1989 
1990 /* initialization of unixcall functions*/
1991 void unixcall(ctx,mod)
1992 register context *ctx;
1993 pointer mod;
1994 { pointer p=Spevalof(PACKAGE);
1995 
1996  Spevalof(PACKAGE)=unixpkg;
1997 
1998 /* common to unix and to vxworks */
1999  defun(ctx,"SIGADDSET",mod,SIGADDSET,NULL);
2000  defun(ctx,"SIGDELSET",mod,SIGDELSET,NULL);
2001  defun(ctx,"SIGPROCMASK",mod,SIGPROCMASK,NULL);
2002  defun(ctx,"KILL",mod,KILL,NULL);
2003  defun(ctx,"SIGNAL",mod,SIGNAL,NULL);
2004  defun(ctx,"EXIT",mod,EXIT,NULL);
2005  defun(ctx,"_EXIT",mod,_EXIT,NULL);
2006  defun(ctx,"GETPID",mod,GETPID,NULL);
2007  defun(ctx,"UREAD",mod,UNIXREAD,NULL);
2008  defun(ctx,"WRITE",mod,UNIXWRITE,NULL);
2009  defun(ctx,"UCLOSE",mod,UNIXCLOSE,NULL);
2010  defun(ctx,"IOCTL",mod,IOCTL,NULL);
2011  defun(ctx,"LSEEK",mod,LSEEK,NULL);
2012  defun(ctx,"SBRK",mod,SBRK,NULL);
2013  defun(ctx,"MALLOC",mod,MALLOC,NULL);
2014  defun(ctx,"FREE",mod,FREE,NULL);
2015 
2016  defun(ctx,"SOCKET",mod,SOCKET,NULL);
2017  defun(ctx,"BIND",mod,BIND,NULL);
2018  defun(ctx,"CONNECT",mod,CONNECT,NULL);
2019  defun(ctx,"LISTEN",mod,LISTEN,NULL);
2020  defun(ctx,"ACCEPT",mod,ACCEPT,NULL);
2021  defun(ctx,"SENDTO",mod,SENDTO,NULL);
2022  defun(ctx,"RECVFROM",mod,RECVFROM,NULL);
2023 #if !Solaris2
2024  defun(ctx,"GETPEERNAME",mod,GETPEERNAME,NULL);
2025 #endif
2026 /* #endif /*socket*/
2027 
2028 /*not supported by vxworks*/
2029 #if !vxworks
2030  defun(ctx,"PTIMES",mod,PTIMES,NULL);
2031  defun(ctx,"RUNTIME",mod,RUNTIME,NULL);
2032  defun(ctx,"LOCALTIME",mod,LOCALTIME,NULL);
2033  defun(ctx,"ASCTIME",mod,ASCTIME,NULL);
2034  defun(ctx,"GETITIMER",mod,GETITIMER,NULL);
2035  defun(ctx,"SETITIMER",mod,SETITIMER,NULL);
2036 
2037 #if !Solaris2
2038  defun(ctx,"GETRUSAGE",mod,GETRUSAGE,NULL);
2039  defun(ctx,"GETPAGESIZE",mod,GETPAGESIZE,NULL);
2040 #endif
2041 
2042  defun(ctx,"GETTIMEOFDAY",mod,GETTIMEOFDAY,NULL);
2043  defun(ctx,"ALARM",mod,ALARM,NULL);
2044 
2045 #if sun3 || sun4 || news || sanyo || alpha || Linux
2046 #if !Solaris2
2047  defun(ctx,"UALARM",mod,UALARM,NULL);
2048 #endif
2049 #endif
2050 
2051  defun(ctx,"WAIT",mod,WAIT,NULL);
2052  defun(ctx,"FORK",mod,FORK,NULL);
2053 #if Solaris2
2054  defun(ctx,"FORK1",mod,FORK1,NULL);
2055 #endif
2056  defun(ctx,"GETPPID",mod,GETPPID,NULL);
2057  defun(ctx,"GETPGRP",mod,GETPGRP,NULL);
2058  defun(ctx,"SETPGRP",mod,SETPGRP,NULL);
2059  defun(ctx,"GETUID",mod,GETUID,NULL);
2060  defun(ctx,"GETEUID",mod,GETEUID,NULL);
2061  defun(ctx,"GETGID",mod,GETGID,NULL);
2062  defun(ctx,"GETEGID",mod,GETEGID,NULL);
2063  defun(ctx,"SETUID",mod,SETUID,NULL);
2064  defun(ctx,"SETGID",mod,SETGID,NULL);
2065  defun(ctx,"MKNOD",mod,MKNOD,NULL);
2066  defun(ctx,"MKDIR",mod,MKDIR,NULL);
2067 #if !Cygwin /* Cygwin does not have LOCKF */
2068  defun(ctx,"LOCKF",mod,LOCKF,NULL);
2069 #endif
2070  defun(ctx,"FCNTL",mod,FCNTL,NULL);
2071 #if !Solaris2
2072  defun(ctx,"IOCTL_",mod,IOCTL_,NULL);
2073  defun(ctx,"IOCTL_R",mod,IOCTL_R,NULL);
2074  defun(ctx,"IOCTL_W",mod,IOCTL_W,NULL);
2075 #if !Cygwin /* Cygwin does not have IOCTL_WR */
2076  defun(ctx,"IOCTL_WR",mod,IOCTL_WR,NULL);
2077 #endif
2078 #endif
2079  defun(ctx,"DUP",mod,DUP,NULL);
2080  defun(ctx,"DUP2",mod,DUP2,NULL);
2081  defun(ctx,"SYSTEM",mod,SYSTEM,NULL);
2082  defun(ctx,"GETWD",mod,GETWD,NULL);
2083  defun(ctx,"GETENV",mod,GETENV,NULL);
2084  defun(ctx,"ENVIRON",mod,ENVIRON,NULL);
2085  defun(ctx,"SLEEP",mod,SLEEP,NULL);
2086  defun(ctx,"ERRNO",mod,ERRNO,NULL);
2087  defun(ctx,"PERROR",mod,PERROR,NULL);
2088  defun(ctx,"SYSERRLIST",mod,SYSERRLIST,NULL);
2089  defun(ctx,"PAUSE",mod,PAUSE,NULL);
2090  defun(ctx,"ISATTY",mod,ISATTY,NULL);
2091  defun(ctx,"LINK",mod,LINK,NULL);
2092  defun(ctx,"UNLINK",mod,UNLINK,NULL);
2093  defun(ctx,"RMDIR",mod,RMDIR,NULL);
2094  defun(ctx,"RENAME",mod,RENAME,NULL);
2095  defun(ctx,"ACCESS",mod,ACCESS,NULL);
2096 /* defun(ctx,"FLOCK",mod,FLOCK,NULL); */
2097  defun(ctx,"STAT",mod,STAT,NULL);
2098  defun(ctx,"CHDIR",mod,CHDIR,NULL);
2099  defun(ctx,"CHMOD",mod,CHMOD,NULL);
2100  defun(ctx,"CHOWN",mod,CHOWN,NULL);
2101  defun(ctx,"PIPE",mod,PIPE,NULL);
2102  defun(ctx,"SELECT",mod,SELECT,NULL);
2103  defun(ctx,"SELECT-READ-FD",mod,SELECT_READ,NULL);
2104  defun(ctx,"READDIR",mod,DIRECTORY,NULL);
2105 
2106 #if !vxworks
2107  defun(ctx,"GETHOSTNAME",mod,GETHOSTNAME,NULL);
2108  defun(ctx,"GETHOSTBYNAME",mod,GETHOSTBYNAME,NULL);
2109  defun(ctx,"GETHOSTBYADDR",mod,GETHOSTBYADDR,NULL);
2110 #if !Cygwin /* Cygwin does not have GETNETBYNMAE */
2111  defun(ctx,"GETNETBYNAME",mod,GETNETBYNAME,NULL);
2112 #endif
2113  defun(ctx,"GETPROTOBYNAME",mod,GETPROTOBYNAME,NULL);
2114  defun(ctx,"GETSERVBYNAME",mod,GETSERVBYNAME,NULL);
2115 /* Append by I.Hara for IPC */
2116  defun(ctx,"HTONS",mod,H2NS,NULL);
2117  defun(ctx,"NTOHS",mod,N2HS,NULL);
2118 #endif
2119 
2120 #if sun3 || sun4 || vax || news || sanyo || (mips && !IRIX && !IRIX6) || alpha || Linux
2121  defun(ctx,"VFORK",mod,VFORK,NULL);
2122 #endif
2123  defun(ctx,"EXEC",mod,EXEC,NULL);
2124 #if !Solaris2 && !Cygwin
2125  defun(ctx,"GETPRIORITY",mod,GETPRIORITY,NULL);
2126  defun(ctx,"SETPRIORITY",mod,SETPRIORITY,NULL);
2127 #endif
2128 
2129 #if sun3 || sun4 || vax || mips || alpha || Linux
2130  defun(ctx,"PUTENV",mod,PUTENV,NULL);
2131 #endif
2132 #if sun3 || sun4 && !Solaris2 || Linux || alpha || Cygwin
2133  defun(ctx,"USLEEP",mod,USLEEP,NULL);
2134 #endif
2135 
2136 #if !news
2137  defun(ctx,"MSGGET",mod,MSGGET,NULL);
2138  defun(ctx,"MSGSND",mod,MSGSND,NULL);
2139  defun(ctx,"MSGRCV",mod,MSGRCV,NULL);
2140  defun(ctx,"MSGCTL",mod,MSGCTL,NULL);
2141 #endif
2142 
2143 #if sun3 || sun4 || news || alpha
2144  defun(ctx,"VALLOC",mod,VALLOC,NULL);
2145 #endif
2146 #if sun3 || sun4 || news || alpha || Linux || Cygwin
2147  defun(ctx,"MMAP",mod,MMAP,NULL);
2148  defun(ctx,"MUNMAP",mod,MUNMAP,NULL);
2149 /* defun(ctx,"VADVISE",mod,VADVISE,NULL); */
2150 #endif
2151 
2152 #if system5 || Linux || Cygwin
2153  defun(ctx,"UNAME",mod,UNAME,NULL);
2154 #endif
2155 
2156 #endif /*socket*/
2157 
2158 /*ndbm libraries*/
2159 #ifdef DBM
2160 #if sun3 || sun4
2161  defun(ctx,"DBM-OPEN",mod,DBM_OPEN,NULL);
2162  defun(ctx,"DBM-CLOSE",mod,DBM_CLOSE,NULL);
2163  defun(ctx,"DBM-FETCH",mod,DBM_FETCH,NULL);
2164  defun(ctx,"DBM-STORE",mod,DBM_STORE,NULL);
2165  defun(ctx,"DBM-DELETE",mod,DBM_DELETE,NULL);
2166  defun(ctx,"DBM-FIRSTKEY",mod,DBM_FIRSTKEY,NULL);
2167  defun(ctx,"DBM-NEXTKEY",mod,DBM_NEXTKEY,NULL);
2168  defun(ctx,"DBM-ERROR",mod,DBM_ERROR,NULL);
2169  defun(ctx,"DBM-CLEARERR",mod,DBM_CLEARERR,NULL);
2170 #endif
2171 
2172 #endif
2173 /* restore package*/ pointer_update(Spevalof(PACKAGE),p);
2174 }
pointer K_IN
Definition: eus.c:130
context * euscontexts[MAXTHREAD]
Definition: eus.c:105
eusinteger_t iv[1]
Definition: eus.h:305
pointer IOCTL_(context *, int, pointer *)
pointer GETITIMER(context *ctx, int n, argv)
Definition: unixcall.c:252
pointer N2HS(context *, int, pointer *)
f
pointer GETENV(context *, int, pointer *)
pointer SETPGRP(context *, int, pointer *)
pointer PAUSE(context *, int, pointer *)
struct vector vec
Definition: eus.h:414
pointer RMDIR(context *, int, pointer *)
pointer UNIXWRITE(context *, int, pointer *)
pointer SIGNAL(context *ctx, int n, argv)
Definition: unixcall.c:364
pointer UNIXCLOSE(context *, int, pointer *)
pointer ACCESS(context *, int, pointer *)
static void * parent(void)
Definition: unixcall.c:595
#define makeint(v)
Definition: sfttest.c:2
struct cell * pointer
Definition: eus.h:165
pointer LOCKF(context *, int, pointer *)
pointer DBM_CLOSE(context *ctx, int n, argv)
Definition: ndbm.c:21
pointer C_VECTOR
Definition: eus.c:144
pointer UALARM(context *ctx, int n, argv)
Definition: unixcall.c:454
pointer K_OUT
Definition: eus.c:130
pointer FCNTL(context *, int, pointer *)
Definition: eus.h:524
pointer SBRK(context *, int, pointer *)
pointer cons(context *, pointer, pointer)
Definition: makes.c:97
static pointer GETPRIORITY(context *ctx, int n, pointer *argv)
Definition: unixcall.c:662
struct filestream fstream
Definition: eus.h:406
pointer EXEC(context *ctx, int n, pointer *argv)
Definition: unixcall.c:635
pointer mkfilestream(context *, pointer, pointer, int, pointer)
Definition: makes.c:253
pointer MSGCTL(context *, int, pointer *)
struct string str
Definition: eus.h:402
pointer GETHOSTBYNAME(context *, int, pointer *)
int thr_continue(int)
Definition: pthreads.c:58
pointer unixpkg
Definition: eus.c:109
struct threadport thrp
Definition: eus.h:421
byte chars[1]
Definition: eus.h:212
pointer DBM_STORE(context *ctx, int n, argv)
Definition: ndbm.c:43
pointer * vsp
Definition: eus.h:525
static char me[3]
Definition: helpsub.c:29
pointer Getstring()
pointer GETPAGESIZE(context *ctx, int n, argv)
Definition: unixcall.c:225
pointer SENDTO(context *, int, pointer *)
Definition: eus.h:195
pointer T
Definition: eus.c:110
GLfloat n[6][3]
Definition: cube.c:15
pointer PUTENV(context *, int, pointer *)
pointer SIGADDSET(context *ctx, int n, argv)
Definition: unixcall.c:303
pointer RECVFROM(context *, int, pointer *)
pointer SYSERRLIST(context *, int, pointer *)
pointer MKDIR(context *, int, pointer *)
byte * chars
Definition: eus.h:216
pointer GETPGRP(context *ctx, int n, argv)
Definition: unixcall.c:483
pointer ASCTIME(context *ctx, int n, argv)
Definition: unixcall.c:171
pointer H2NS(context *, int, pointer *)
pointer GETEUID(context *ctx, int n, argv)
Definition: unixcall.c:511
int daylight
pointer MSGGET(context *, int, pointer *)
pointer SIGDELSET(context *ctx, int n, argv)
Definition: unixcall.c:319
struct foreign foreign
Definition: eus.h:403
#define intval(p)
Definition: sfttest.c:1
long tv_sec
Definition: posix.c:11
defun("ADR_TO_STRING", mod, ADR_TO_STRING)
eusinteger_t * checkbitvec(pointer, long *)
pointer ufuncall(context *, pointer, pointer, pointer, struct bindframe *, int)
Definition: eval.c:1469
char * tzname[2]
pointer DUP2(context *, int, pointer *)
pointer MKNOD(context *, int, pointer *)
pointer LINK(context *, int, pointer *)
pointer MSGSND(context *, int, pointer *)
pointer KILL(context *ctx, int n, argv)
Definition: unixcall.c:356
pointer LISTEN(context *, int, pointer *)
Definition: eus.h:1006
pointer makevector(pointer, int)
Definition: makes.c:417
pointer PTIMES(context *ctx, int n, argv)
Definition: unixcall.c:102
ckarg(2)
pointer GETEGID(context *ctx, int n, argv)
Definition: unixcall.c:525
float ckfltval()
pointer GETSERVBYNAME(context *, int, pointer *)
pointer RENAME(context *, int, pointer *)
#define min(x, y)
Definition: rmflags.c:17
pointer DBM_OPEN(context *ctx, int n, argv)
Definition: ndbm.c:10
pointer DBM_NEXTKEY(context *ctx, int n, argv)
Definition: ndbm.c:82
pointer FORK(context *ctx, int n, pointer *argv)
Definition: unixcall.c:573
pointer GETHOSTNAME(context *, int, pointer *)
static void key(unsigned char c, int x, int y)
Definition: dinoshade.c:753
struct intvector ivec
Definition: eus.h:416
pointer FORK1(context *ctx, int n, pointer *argv)
Definition: unixcall.c:617
pointer GETGID(context *ctx, int n, argv)
Definition: unixcall.c:518
union cell::cellunion c
pointer out
Definition: eus.h:291
pointer VFORK(context *ctx, int n, pointer *argv)
Definition: unixcall.c:627
int errno
pointer ENVIRON(context *, int, pointer *)
pointer MALLOC(context *, int, pointer *)
long tv_nsec
Definition: posix.c:12
pointer CHMOD(context *, int, pointer *)
pointer GETNETBYNAME(context *, int, pointer *)
pointer IOCTL_R(context *, int, pointer *)
Definition: eus.h:428
struct stream stream
Definition: eus.h:405
pointer GETUID(context *ctx, int n, pointer *argv)
Definition: unixcall.c:507
long l
Definition: structsize.c:3
pointer mkiostream(context *, pointer, pointer)
Definition: makes.c:269
pointer RUNTIME(context *ctx, int n, argv)
Definition: unixcall.c:118
pointer ERRNO(context *, int, pointer *)
int thr_suspend(int)
Definition: pthreads.c:64
static void * child(void)
Definition: unixcall.c:603
Definition: eus.h:381
pointer fname
Definition: eus.h:287
void unixcall(context *, pointer)
pointer GETRUSAGE(context *ctx, int n, argv)
Definition: unixcall.c:205
static pointer SETPRIORITY(context *ctx, int n, pointer *argv)
Definition: unixcall.c:650
pointer USLEEP(context *, int, pointer *)
short s
Definition: structsize.c:2
pointer CHDIR(context *, int, pointer *)
pointer SETITIMER(context *ctx, int n, argv)
Definition: unixcall.c:268
pointer GETWD(context *, int, pointer *)
pointer IOCTL_W(context *, int, pointer *)
pointer makebuffer(int)
Definition: makes.c:140
pointer SELECT_READ(context *, int, pointer *)
pointer IOCTL(context *, int, pointer *)
pointer PIPE(context *, int, pointer *)
static char * rcsid
Definition: unixcall.c:13
pointer SIGPROCMASK(context *ctx, int n, argv)
Definition: unixcall.c:335
pointer GETHOSTBYADDR(context *, int, pointer *)
eusinteger_t coerceintval(pointer)
Definition: sequence.c:55
pointer SETGID(context *ctx, int n, argv)
Definition: unixcall.c:540
pointer error(enum errorcode ec,...) pointer error(va_alist) va_dcl
Definition: eus.c:297
pointer GETPID(context *ctx, int n, pointer *argv)
Definition: unixcall.c:468
long eusinteger_t
Definition: eus.h:19
pointer SETUID(context *ctx, int n, argv)
Definition: unixcall.c:532
pointer QEXITHOOK
Definition: eus.c:122
pointer SYSTEM(context *, int, pointer *)
pointer DBM_FETCH(context *ctx, int n, argv)
Definition: ndbm.c:29
pointer DBM_FIRSTKEY(context *ctx, int n, argv)
Definition: ndbm.c:72
pointer DIRECTORY(context *, int, pointer *)
pointer buffer
Definition: eus.h:283
byte * get_string()
pointer UNLINK(context *, int, pointer *)
pointer PACKAGE
Definition: eus.c:110
pointer direction
Definition: eus.h:275
pointer UNIXREAD(context *ctx, int n, argv)
Definition: unixcall.c:705
pointer stacknlist(context *, int)
Definition: makes.c:129
pointer GETPEERNAME(context *, int, pointer *)
pointer ISATTY(context *, int, pointer *)
#define GC_REGION(cmp_statement)
Definition: eus.h:173
pointer MMAP(context *, int, pointer *)
pointer SELECT(context *, int, pointer *)
static int ctxid_in_child
Definition: unixcall.c:583
pointer ACCEPT(context *, int, pointer *)
pointer FREE(context *, int, pointer *)
pointer LOCALTIME(context *ctx, int n, argv)
Definition: unixcall.c:127
time_t altzone
static void * prepare(void)
Definition: unixcall.c:584
void eusint(int s, int code, int x, eusinteger_t addr)
Definition: eus.c:976
int count
Definition: thrtest.c:11
pointer _EXIT(context *ctx, int n, pointer *argv)
Definition: unixcall.c:692
pointer makestring(char *, int)
Definition: makes.c:147
pointer tail
Definition: eus.h:278
pointer MSGRCV(context *, int, pointer *)
pointer CHOWN(context *, int, pointer *)
#define max(I1, I2)
Definition: eustags.c:134
pointer DUP(context *, int, pointer *)
pointer DBM_ERROR(context *ctx, int n, argv)
Definition: ndbm.c:92
#define NULL
Definition: transargv.c:8
struct iostream iostream
Definition: eus.h:407
pointer EXIT(context *ctx, int n, pointer *argv)
Definition: unixcall.c:672
pointer LSEEK(context *, int, pointer *)
pointer WAIT(context *ctx, int n, argv)
Definition: unixcall.c:436
pointer fd
Definition: eus.h:286
pointer IOCTL_WR(context *, int, pointer *)
pointer SOCKET(context *, int, pointer *)
pointer make_foreign_string(eusinteger_t, int)
Definition: makes.c:157
pointer count
Definition: eus.h:277
Definition: posix.c:10
time_t timezone
Definition: eus.h:954
pointer in
Definition: eus.h:291
unsigned char byte
Definition: eus.h:163
pointer eussigvec[NSIG]
Definition: eus.c:182
unsigned int thr_self()
Definition: eus.c:25
pointer BIND(context *, int, pointer *)
static char buf[CHAR_SIZE]
Definition: helpsub.c:23
double eusfloat_t
Definition: eus.h:21
eusinteger_t mypid
Definition: eus.c:38
pointer ALARM(context *ctx, int n, argv)
Definition: unixcall.c:445
pointer CONNECT(context *, int, pointer *)
pointer NIL
Definition: eus.c:110
pointer GETTIMEOFDAY(context *ctx, int n, argv)
Definition: unixcall.c:233
pointer SLEEP(context *, int, pointer *)
pointer GETPPID(context *ctx, int n, argv)
Definition: unixcall.c:476
pointer v[1]
Definition: eus.h:301
pointer MUNMAP(context *, int, pointer *)
pointer DBM_DELETE(context *ctx, int n, argv)
Definition: ndbm.c:59
static int sock
pointer threadobj
Definition: eus.h:538
if(n==1)
Definition: unixcall.c:492
Definition: eus.h:956
char a[26]
Definition: freq.c:4
pointer length
Definition: eus.h:211
pointer GETPROTOBYNAME(context *, int, pointer *)
pointer STAT(context *, int, pointer *)
pointer UNAME(context *ctx, int n, pointer *argv)
Definition: unixcall.c:551
pointer makeflt()
int bytesize(pointer)
pointer DBM_CLEARERR(context *ctx, int n, argv)
Definition: ndbm.c:100


euslisp
Author(s): Toshihiro Matsui
autogenerated on Mon Feb 28 2022 22:18:28