Silence new warning grep in void context warning in various modules and test files...
[p5sagit/p5-mst-13.2.git] / ext / POSIX / POSIX.xs
CommitLineData
6e22d046 1#define PERL_EXT_POSIX
2
2986a63f 3#ifdef NETWARE
4 #define _POSIX_
4efcf9a2 5 /*
6 * Ideally this should be somewhere down in the includes
7 * but putting it in other places is giving compiler errors.
8 * Also here I am unable to check for HAS_UNAME since it wouldn't have
9 * yet come into the file at this stage - sgp 18th Oct 2000
10 */
2986a63f 11 #include <sys/utsname.h>
12#endif /* NETWARE */
13
c5be433b 14#define PERL_NO_GET_CONTEXT
15
463ee0b2 16#include "EXTERN.h"
760ac839 17#define PERLIO_NOT_STDIO 1
463ee0b2 18#include "perl.h"
19#include "XSUB.h"
acfe0abc 20#if defined(PERL_IMPLICIT_SYS)
873ef191 21# undef signal
22# undef open
cd661bb6 23# undef setmode
35ff7856 24# define open PerlLIO_open3
873ef191 25#endif
2304df62 26#include <ctype.h>
a0d0e21e 27#ifdef I_DIRENT /* XXX maybe better to just rely on perl.h? */
2304df62 28#include <dirent.h>
a0d0e21e 29#endif
2304df62 30#include <errno.h>
2304df62 31#ifdef I_FLOAT
32#include <float.h>
33#endif
a0d0e21e 34#ifdef I_LIMITS
2304df62 35#include <limits.h>
a0d0e21e 36#endif
2304df62 37#include <locale.h>
38#include <math.h>
85e6fe83 39#ifdef I_PWD
2304df62 40#include <pwd.h>
85e6fe83 41#endif
2304df62 42#include <setjmp.h>
43#include <signal.h>
2304df62 44#include <stdarg.h>
17c3b450 45
2304df62 46#ifdef I_STDDEF
47#include <stddef.h>
48#endif
6990d991 49
b5846a0b 50#ifdef I_UNISTD
51#include <unistd.h>
52#endif
53
3609ea0d 54/* XXX This comment is just to make I_TERMIO and I_SGTTY visible to
a0d0e21e 55 metaconfig for future extension writers. We don't use them in POSIX.
56 (This is really sneaky :-) --AD
57*/
58#if defined(I_TERMIOS)
59#include <termios.h>
60#endif
a0d0e21e 61#ifdef I_STDLIB
2304df62 62#include <stdlib.h>
a0d0e21e 63#endif
5518ecd4 64#ifndef __ultrix__
2304df62 65#include <string.h>
5518ecd4 66#endif
2304df62 67#include <sys/stat.h>
2304df62 68#include <sys/types.h>
2304df62 69#include <time.h>
6dead956 70#ifdef I_UNISTD
1d2dff63 71#include <unistd.h>
6dead956 72#endif
bf4acbe4 73#ifdef MACOS_TRADITIONAL
74#undef fdopen
75#endif
71be2cbc 76#include <fcntl.h>
77
e2465f50 78#ifdef HAS_TZNAME
fb207d52 79# if !defined(WIN32) && !defined(__CYGWIN__) && !defined(NETWARE) && !defined(__UWIN__)
e2465f50 80extern char *tzname[];
81# endif
82#else
fb207d52 83#if !defined(WIN32) && !defined(__UWIN__) || (defined(__MINGW32__) && !defined(tzname))
e2465f50 84char *tzname[] = { "" , "" };
85#endif
cb2479a8 86#endif
87
aec614a5 88#ifndef PERL_UNUSED_DECL
89# ifdef HASATTRIBUTE
90# if (defined(__GNUC__) && defined(__cplusplus)) || defined(__INTEL_COMPILER)
91# define PERL_UNUSED_DECL
92# else
93# define PERL_UNUSED_DECL __attribute__((unused))
94# endif
27da23d5 95# else
aec614a5 96# define PERL_UNUSED_DECL
27da23d5 97# endif
27da23d5 98#endif
99
100#ifndef dNOOP
101#define dNOOP extern int Perl___notused PERL_UNUSED_DECL
102#endif
103
104#ifndef dVAR
105#define dVAR dNOOP
106#endif
107
6c418a22 108#if defined(__VMS) && !defined(__POSIX_SOURCE)
6c418a22 109# include <libdef.h> /* LIB$_INVARG constant */
110# include <lib$routines.h> /* prototype for lib$ediv() */
111# include <starlet.h> /* prototype for sys$gettim() */
774d564b 112# if DECC_VERSION < 50000000
86200d5c 113# define pid_t int /* old versions of DECC miss this in types.h */
774d564b 114# endif
6c418a22 115
6990d991 116# undef mkfifo
6c418a22 117# define mkfifo(a,b) (not_here("mkfifo"),-1)
118# define tzset() not_here("tzset")
119
5f6761f9 120#if ((__VMS_VER >= 70000000) && (__DECC_VER >= 50200000)) || (__CRTL_VER >= 70000000)
121# define HAS_TZNAME /* shows up in VMS 7.0 or Dec C 5.6 */
122# include <utsname.h>
5f6761f9 123# endif /* __VMS_VER >= 70000000 or Dec C 5.6 */
6c418a22 124
125 /* The POSIX notion of ttyname() is better served by getname() under VMS */
126 static char ttnambuf[64];
127# define ttyname(fd) (isatty(fd) > 0 ? getname(fd,ttnambuf,0) : NULL)
128
129 /* The non-POSIX CRTL times() has void return type, so we just get the
130 current time directly */
34f7a5fe 131 clock_t vms_times(struct tms *bufptr) {
d28f7c37 132 dTHX;
6c418a22 133 clock_t retval;
134 /* Get wall time and convert to 10 ms intervals to
135 * produce the return value that the POSIX standard expects */
136# if defined(__DECC) && defined (__ALPHA)
137# include <ints.h>
138 uint64 vmstime;
139 _ckvmssts(sys$gettim(&vmstime));
140 vmstime /= 100000;
141 retval = vmstime & 0x7fffffff;
142# else
143 /* (Older hw or ccs don't have an atomic 64-bit type, so we
144 * juggle 32-bit ints (and a float) to produce a time_t result
145 * with minimal loss of information.) */
146 long int vmstime[2],remainder,divisor = 100000;
147 _ckvmssts(sys$gettim((unsigned long int *)vmstime));
148 vmstime[1] &= 0x7fff; /* prevent overflow in EDIV */
149 _ckvmssts(lib$ediv(&divisor,vmstime,(long int *)&retval,&remainder));
150# endif
151 /* Fill in the struct tms using the CRTL routine . . .*/
34f7a5fe 152 times((tbuffer_t *)bufptr);
6c418a22 153 return (clock_t) retval;
154 }
155# define times(t) vms_times(t)
156#else
d308986b 157#if defined (__CYGWIN__)
f89d6eaa 158# define tzname _tzname
159#endif
2986a63f 160#if defined (WIN32) || defined (NETWARE)
6990d991 161# undef mkfifo
6dead956 162# define mkfifo(a,b) not_here("mkfifo")
873ef191 163# define ttyname(a) (char*)not_here("ttyname")
6dead956 164# define sigset_t long
86200d5c 165# define pid_t long
6dead956 166# ifdef __BORLANDC__
167# define tzname _tzname
168# endif
169# ifdef _MSC_VER
170# define mode_t short
171# endif
62520c91 172# ifdef __MINGW32__
173# define mode_t short
f6c6487a 174# ifndef tzset
175# define tzset() not_here("tzset")
176# endif
177# ifndef _POSIX_OPEN_MAX
178# define _POSIX_OPEN_MAX FOPEN_MAX /* XXX bogus ? */
179# endif
62520c91 180# endif
6dead956 181# define sigaction(a,b,c) not_here("sigaction")
182# define sigpending(a) not_here("sigpending")
183# define sigprocmask(a,b,c) not_here("sigprocmask")
184# define sigsuspend(a) not_here("sigsuspend")
185# define sigemptyset(a) not_here("sigemptyset")
186# define sigaddset(a,b) not_here("sigaddset")
187# define sigdelset(a,b) not_here("sigdelset")
188# define sigfillset(a) not_here("sigfillset")
189# define sigismember(a,b) not_here("sigismember")
2986a63f 190#ifndef NETWARE
6e22d046 191# undef setuid
192# undef setgid
2986a63f 193# define setuid(a) not_here("setuid")
194# define setgid(a) not_here("setgid")
195#endif /* NETWARE */
6dead956 196#else
6990d991 197
198# ifndef HAS_MKFIFO
bf4acbe4 199# if defined(OS2) || defined(MACOS_TRADITIONAL)
d6a255e6 200# define mkfifo(a,b) not_here("mkfifo")
3609ea0d 201# else /* !( defined OS2 ) */
d6a255e6 202# ifndef mkfifo
203# define mkfifo(path, mode) (mknod((path), (mode) | S_IFIFO, 0))
204# endif
6990d991 205# endif
206# endif /* !HAS_MKFIFO */
207
bf4acbe4 208# ifdef MACOS_TRADITIONAL
bf4acbe4 209# define ttyname(a) (char*)not_here("ttyname")
210# define tzset() not_here("tzset")
211# else
27da23d5 212# ifdef I_GRP
213# include <grp.h>
214# endif
bf4acbe4 215# include <sys/times.h>
216# ifdef HAS_UNAME
217# include <sys/utsname.h>
218# endif
219# include <sys/wait.h>
6c418a22 220# endif
6c418a22 221# ifdef I_UTIME
222# include <utime.h>
223# endif
2986a63f 224#endif /* WIN32 || NETWARE */
6dead956 225#endif /* __VMS */
2304df62 226
227typedef int SysRet;
a0d0e21e 228typedef long SysRetLong;
2304df62 229typedef sigset_t* POSIX__SigSet;
230typedef HV* POSIX__SigAction;
a0d0e21e 231#ifdef I_TERMIOS
232typedef struct termios* POSIX__Termios;
233#else /* Define termios types to int, and call not_here for the functions.*/
234#define POSIX__Termios int
235#define speed_t int
236#define tcflag_t int
237#define cc_t int
238#define cfgetispeed(x) not_here("cfgetispeed")
239#define cfgetospeed(x) not_here("cfgetospeed")
240#define tcdrain(x) not_here("tcdrain")
241#define tcflush(x,y) not_here("tcflush")
242#define tcsendbreak(x,y) not_here("tcsendbreak")
243#define cfsetispeed(x,y) not_here("cfsetispeed")
244#define cfsetospeed(x,y) not_here("cfsetospeed")
245#define ctermid(x) (char *) not_here("ctermid")
246#define tcflow(x,y) not_here("tcflow")
247#define tcgetattr(x,y) not_here("tcgetattr")
248#define tcsetattr(x,y,z) not_here("tcsetattr")
249#endif
250
251/* Possibly needed prototypes */
20ce7b12 252char *cuserid (char *);
6e22d046 253#ifndef WIN32
20ce7b12 254double strtod (const char *, char **);
255long strtol (const char *, char **, int);
256unsigned long strtoul (const char *, char **, int);
6e22d046 257#endif
a0d0e21e 258
259#ifndef HAS_CUSERID
260#define cuserid(a) (char *) not_here("cuserid")
261#endif
262#ifndef HAS_DIFFTIME
263#ifndef difftime
264#define difftime(a,b) not_here("difftime")
265#endif
266#endif
267#ifndef HAS_FPATHCONF
3609ea0d 268#define fpathconf(f,n) (SysRetLong) not_here("fpathconf")
a0d0e21e 269#endif
270#ifndef HAS_MKTIME
271#define mktime(a) not_here("mktime")
8990e307 272#endif
273#ifndef HAS_NICE
274#define nice(a) not_here("nice")
275#endif
a0d0e21e 276#ifndef HAS_PATHCONF
3609ea0d 277#define pathconf(f,n) (SysRetLong) not_here("pathconf")
a0d0e21e 278#endif
279#ifndef HAS_SYSCONF
3609ea0d 280#define sysconf(n) (SysRetLong) not_here("sysconf")
a0d0e21e 281#endif
8990e307 282#ifndef HAS_READLINK
283#define readlink(a,b,c) not_here("readlink")
284#endif
285#ifndef HAS_SETPGID
286#define setpgid(a,b) not_here("setpgid")
287#endif
8990e307 288#ifndef HAS_SETSID
289#define setsid() not_here("setsid")
290#endif
a0d0e21e 291#ifndef HAS_STRCOLL
292#define strcoll(s1,s2) not_here("strcoll")
293#endif
a89d8a78 294#ifndef HAS_STRTOD
295#define strtod(s1,s2) not_here("strtod")
296#endif
297#ifndef HAS_STRTOL
298#define strtol(s1,s2,b) not_here("strtol")
299#endif
300#ifndef HAS_STRTOUL
301#define strtoul(s1,s2,b) not_here("strtoul")
302#endif
a0d0e21e 303#ifndef HAS_STRXFRM
304#define strxfrm(s1,s2,n) not_here("strxfrm")
8990e307 305#endif
306#ifndef HAS_TCGETPGRP
307#define tcgetpgrp(a) not_here("tcgetpgrp")
308#endif
309#ifndef HAS_TCSETPGRP
310#define tcsetpgrp(a,b) not_here("tcsetpgrp")
311#endif
312#ifndef HAS_TIMES
2986a63f 313#ifndef NETWARE
8990e307 314#define times(a) not_here("times")
2986a63f 315#endif /* NETWARE */
8990e307 316#endif
317#ifndef HAS_UNAME
318#define uname(a) not_here("uname")
319#endif
320#ifndef HAS_WAITPID
321#define waitpid(a,b,c) not_here("waitpid")
322#endif
323
a0d0e21e 324#ifndef HAS_MBLEN
325#ifndef mblen
326#define mblen(a,b) not_here("mblen")
327#endif
328#endif
329#ifndef HAS_MBSTOWCS
330#define mbstowcs(s, pwcs, n) not_here("mbstowcs")
331#endif
332#ifndef HAS_MBTOWC
333#define mbtowc(pwc, s, n) not_here("mbtowc")
334#endif
335#ifndef HAS_WCSTOMBS
336#define wcstombs(s, pwcs, n) not_here("wcstombs")
337#endif
338#ifndef HAS_WCTOMB
339#define wctomb(s, wchar) not_here("wcstombs")
340#endif
341#if !defined(HAS_MBLEN) && !defined(HAS_MBSTOWCS) && !defined(HAS_MBTOWC) && !defined(HAS_WCSTOMBS) && !defined(HAS_WCTOMB)
342/* If we don't have these functions, then we wouldn't have gotten a typedef
343 for wchar_t, the wide character type. Defining wchar_t allows the
344 functions referencing it to compile. Its actual type is then meaningless,
345 since without the above functions, all sections using it end up calling
346 not_here() and croak. --Kaveh Ghazi (ghazi@noc.rutgers.edu) 9/18/94. */
347#ifndef wchar_t
348#define wchar_t char
349#endif
350#endif
351
352#ifndef HAS_LOCALECONV
353#define localeconv() not_here("localeconv")
354#endif
355
172ea7c8 356#ifdef HAS_LONG_DOUBLE
53796371 357# if LONG_DOUBLESIZE > NVSIZE
172ea7c8 358# undef HAS_LONG_DOUBLE /* XXX until we figure out how to use them */
359# endif
360#endif
361
362#ifndef HAS_LONG_DOUBLE
363#ifdef LDBL_MAX
364#undef LDBL_MAX
365#endif
366#ifdef LDBL_MIN
367#undef LDBL_MIN
368#endif
369#ifdef LDBL_EPSILON
370#undef LDBL_EPSILON
371#endif
372#endif
373
ec193bec 374/* Background: in most systems the low byte of the wait status
375 * is the signal (the lowest 7 bits) and the coredump flag is
376 * the eight bit, and the second lowest byte is the exit status.
377 * BeOS bucks the trend and has the bytes in different order.
378 * See beos/beos.c for how the reality is bent even in BeOS
379 * to follow the traditional. However, to make the POSIX
380 * wait W*() macros to work in BeOS, we need to unbend the
381 * reality back in place. --jhi */
382#ifdef __BEOS__
383# define WMUNGE(x) (((x) & 0xFF00) >> 8 | ((x) & 0x00FF) << 8)
384#else
385# define WMUNGE(x) (x)
386#endif
387
8990e307 388static int
f0f333f4 389not_here(char *s)
8990e307 390{
391 croak("POSIX::%s not implemented on this architecture", s);
392 return -1;
393}
463ee0b2 394
1cb0fb50 395#include "const-c.inc"
a290f238 396
397/* These were implemented in the old "constant" subroutine. They are actually
398 macros that take an integer argument and return an integer result. */
399static int
400int_macro_int (const char *name, STRLEN len, IV *arg_result) {
401 /* Initially switch on the length of the name. */
402 /* This code has been edited from a "constant" function generated by:
403
404use ExtUtils::Constant qw (constant_types C_constant XS_constant);
405
406my $types = {map {($_, 1)} qw(IV)};
407my @names = (qw(S_ISBLK S_ISCHR S_ISDIR S_ISFIFO S_ISREG WEXITSTATUS WIFEXITED
408 WIFSIGNALED WIFSTOPPED WSTOPSIG WTERMSIG));
409
410print constant_types(); # macro defs
411foreach (C_constant ("POSIX", 'int_macro_int', 'IV', $types, undef, 5, @names) ) {
412 print $_, "\n"; # C constant subs
413}
414print "#### XS Section:\n";
415print XS_constant ("POSIX", $types);
a290f238 416 */
417
418 switch (len) {
419 case 7:
420 /* Names all of length 7. */
421 /* S_ISBLK S_ISCHR S_ISDIR S_ISREG */
422 /* Offset 5 gives the best switch position. */
423 switch (name[5]) {
424 case 'E':
425 if (memEQ(name, "S_ISREG", 7)) {
426 /* ^ */
427#ifdef S_ISREG
428 *arg_result = S_ISREG(*arg_result);
429 return PERL_constant_ISIV;
2304df62 430#else
a290f238 431 return PERL_constant_NOTDEF;
2304df62 432#endif
a290f238 433 }
434 break;
435 case 'H':
436 if (memEQ(name, "S_ISCHR", 7)) {
437 /* ^ */
438#ifdef S_ISCHR
439 *arg_result = S_ISCHR(*arg_result);
440 return PERL_constant_ISIV;
2304df62 441#else
a290f238 442 return PERL_constant_NOTDEF;
2304df62 443#endif
a290f238 444 }
445 break;
446 case 'I':
447 if (memEQ(name, "S_ISDIR", 7)) {
448 /* ^ */
449#ifdef S_ISDIR
450 *arg_result = S_ISDIR(*arg_result);
451 return PERL_constant_ISIV;
2304df62 452#else
a290f238 453 return PERL_constant_NOTDEF;
2304df62 454#endif
a290f238 455 }
456 break;
457 case 'L':
458 if (memEQ(name, "S_ISBLK", 7)) {
459 /* ^ */
460#ifdef S_ISBLK
461 *arg_result = S_ISBLK(*arg_result);
462 return PERL_constant_ISIV;
2304df62 463#else
a290f238 464 return PERL_constant_NOTDEF;
2304df62 465#endif
a290f238 466 }
467 break;
468 }
469 break;
470 case 8:
471 /* Names all of length 8. */
472 /* S_ISFIFO WSTOPSIG WTERMSIG */
473 /* Offset 3 gives the best switch position. */
474 switch (name[3]) {
475 case 'O':
476 if (memEQ(name, "WSTOPSIG", 8)) {
477 /* ^ */
478#ifdef WSTOPSIG
bfbc3223 479 int i = *arg_result;
480 *arg_result = WSTOPSIG(WMUNGE(i));
a290f238 481 return PERL_constant_ISIV;
2304df62 482#else
a290f238 483 return PERL_constant_NOTDEF;
2304df62 484#endif
a290f238 485 }
486 break;
487 case 'R':
488 if (memEQ(name, "WTERMSIG", 8)) {
489 /* ^ */
490#ifdef WTERMSIG
bfbc3223 491 int i = *arg_result;
492 *arg_result = WTERMSIG(WMUNGE(i));
a290f238 493 return PERL_constant_ISIV;
2304df62 494#else
a290f238 495 return PERL_constant_NOTDEF;
2304df62 496#endif
a290f238 497 }
498 break;
499 case 'S':
500 if (memEQ(name, "S_ISFIFO", 8)) {
501 /* ^ */
502#ifdef S_ISFIFO
503 *arg_result = S_ISFIFO(*arg_result);
504 return PERL_constant_ISIV;
2304df62 505#else
a290f238 506 return PERL_constant_NOTDEF;
2304df62 507#endif
a290f238 508 }
509 break;
510 }
511 break;
512 case 9:
513 if (memEQ(name, "WIFEXITED", 9)) {
514#ifdef WIFEXITED
bfbc3223 515 int i = *arg_result;
516 *arg_result = WIFEXITED(WMUNGE(i));
a290f238 517 return PERL_constant_ISIV;
2304df62 518#else
a290f238 519 return PERL_constant_NOTDEF;
2304df62 520#endif
a290f238 521 }
522 break;
523 case 10:
524 if (memEQ(name, "WIFSTOPPED", 10)) {
525#ifdef WIFSTOPPED
bfbc3223 526 int i = *arg_result;
527 *arg_result = WIFSTOPPED(WMUNGE(i));
a290f238 528 return PERL_constant_ISIV;
2304df62 529#else
a290f238 530 return PERL_constant_NOTDEF;
2304df62 531#endif
a290f238 532 }
533 break;
534 case 11:
535 /* Names all of length 11. */
536 /* WEXITSTATUS WIFSIGNALED */
537 /* Offset 1 gives the best switch position. */
538 switch (name[1]) {
539 case 'E':
540 if (memEQ(name, "WEXITSTATUS", 11)) {
541 /* ^ */
542#ifdef WEXITSTATUS
bfbc3223 543 int i = *arg_result;
544 *arg_result = WEXITSTATUS(WMUNGE(i));
a290f238 545 return PERL_constant_ISIV;
2304df62 546#else
a290f238 547 return PERL_constant_NOTDEF;
2304df62 548#endif
a290f238 549 }
550 break;
551 case 'I':
552 if (memEQ(name, "WIFSIGNALED", 11)) {
553 /* ^ */
554#ifdef WIFSIGNALED
bfbc3223 555 int i = *arg_result;
556 *arg_result = WIFSIGNALED(WMUNGE(i));
a290f238 557 return PERL_constant_ISIV;
2304df62 558#else
a290f238 559 return PERL_constant_NOTDEF;
2304df62 560#endif
a290f238 561 }
562 break;
563 }
564 break;
565 }
566 return PERL_constant_NOTFOUND;
567}
568
1dfe7606 569static void
40b7a5f5 570restore_sigmask(pTHX_ SV *osset_sv)
1dfe7606 571{
7feb700b 572 /* Fortunately, restoring the signal mask can't fail, because
573 * there's nothing we can do about it if it does -- we're not
574 * supposed to return -1 from sigaction unless the disposition
575 * was unaffected.
576 */
7feb700b 577 sigset_t *ossetp = (sigset_t *) SvPV_nolen( osset_sv );
578 (void)sigprocmask(SIG_SETMASK, ossetp, (sigset_t *)0);
1dfe7606 579}
580
2304df62 581MODULE = SigSet PACKAGE = POSIX::SigSet PREFIX = sig
582
583POSIX::SigSet
584new(packname = "POSIX::SigSet", ...)
d3f5e399 585 const char * packname
2304df62 586 CODE:
587 {
588 int i;
a02a5408 589 Newx(RETVAL, 1, sigset_t);
2304df62 590 sigemptyset(RETVAL);
a0d0e21e 591 for (i = 1; i < items; i++)
2304df62 592 sigaddset(RETVAL, SvIV(ST(i)));
593 }
594 OUTPUT:
595 RETVAL
463ee0b2 596
8990e307 597void
2304df62 598DESTROY(sigset)
599 POSIX::SigSet sigset
600 CODE:
01667c76 601 Safefree(sigset);
2304df62 602
603SysRet
604sigaddset(sigset, sig)
605 POSIX::SigSet sigset
606 int sig
607
608SysRet
609sigdelset(sigset, sig)
610 POSIX::SigSet sigset
611 int sig
612
613SysRet
614sigemptyset(sigset)
615 POSIX::SigSet sigset
616
617SysRet
618sigfillset(sigset)
619 POSIX::SigSet sigset
620
621int
622sigismember(sigset, sig)
623 POSIX::SigSet sigset
624 int sig
625
a0d0e21e 626MODULE = Termios PACKAGE = POSIX::Termios PREFIX = cf
627
628POSIX::Termios
629new(packname = "POSIX::Termios", ...)
d3f5e399 630 const char * packname
a0d0e21e 631 CODE:
632 {
633#ifdef I_TERMIOS
a02a5408 634 Newx(RETVAL, 1, struct termios);
a0d0e21e 635#else
636 not_here("termios");
640cc986 637 RETVAL = 0;
a0d0e21e 638#endif
639 }
640 OUTPUT:
641 RETVAL
642
643void
644DESTROY(termios_ref)
645 POSIX::Termios termios_ref
646 CODE:
647#ifdef I_TERMIOS
01667c76 648 Safefree(termios_ref);
a0d0e21e 649#else
650 not_here("termios");
651#endif
652
653SysRet
654getattr(termios_ref, fd = 0)
655 POSIX::Termios termios_ref
656 int fd
657 CODE:
658 RETVAL = tcgetattr(fd, termios_ref);
659 OUTPUT:
660 RETVAL
661
662SysRet
663setattr(termios_ref, fd = 0, optional_actions = 0)
664 POSIX::Termios termios_ref
665 int fd
666 int optional_actions
667 CODE:
668 RETVAL = tcsetattr(fd, optional_actions, termios_ref);
669 OUTPUT:
670 RETVAL
671
672speed_t
673cfgetispeed(termios_ref)
674 POSIX::Termios termios_ref
675
676speed_t
677cfgetospeed(termios_ref)
678 POSIX::Termios termios_ref
679
680tcflag_t
681getiflag(termios_ref)
682 POSIX::Termios termios_ref
683 CODE:
684#ifdef I_TERMIOS /* References a termios structure member so ifdef it out. */
685 RETVAL = termios_ref->c_iflag;
686#else
640cc986 687 not_here("getiflag");
688 RETVAL = 0;
a0d0e21e 689#endif
690 OUTPUT:
691 RETVAL
692
693tcflag_t
694getoflag(termios_ref)
695 POSIX::Termios termios_ref
696 CODE:
697#ifdef I_TERMIOS /* References a termios structure member so ifdef it out. */
698 RETVAL = termios_ref->c_oflag;
699#else
640cc986 700 not_here("getoflag");
701 RETVAL = 0;
a0d0e21e 702#endif
703 OUTPUT:
704 RETVAL
705
706tcflag_t
707getcflag(termios_ref)
708 POSIX::Termios termios_ref
709 CODE:
710#ifdef I_TERMIOS /* References a termios structure member so ifdef it out. */
711 RETVAL = termios_ref->c_cflag;
712#else
640cc986 713 not_here("getcflag");
714 RETVAL = 0;
a0d0e21e 715#endif
716 OUTPUT:
717 RETVAL
718
719tcflag_t
720getlflag(termios_ref)
721 POSIX::Termios termios_ref
722 CODE:
723#ifdef I_TERMIOS /* References a termios structure member so ifdef it out. */
724 RETVAL = termios_ref->c_lflag;
725#else
640cc986 726 not_here("getlflag");
727 RETVAL = 0;
a0d0e21e 728#endif
729 OUTPUT:
730 RETVAL
731
732cc_t
733getcc(termios_ref, ccix)
734 POSIX::Termios termios_ref
b56fc9ec 735 unsigned int ccix
a0d0e21e 736 CODE:
737#ifdef I_TERMIOS /* References a termios structure member so ifdef it out. */
738 if (ccix >= NCCS)
739 croak("Bad getcc subscript");
740 RETVAL = termios_ref->c_cc[ccix];
741#else
640cc986 742 not_here("getcc");
743 RETVAL = 0;
a0d0e21e 744#endif
745 OUTPUT:
746 RETVAL
747
748SysRet
749cfsetispeed(termios_ref, speed)
750 POSIX::Termios termios_ref
751 speed_t speed
752
753SysRet
754cfsetospeed(termios_ref, speed)
755 POSIX::Termios termios_ref
756 speed_t speed
757
758void
759setiflag(termios_ref, iflag)
760 POSIX::Termios termios_ref
761 tcflag_t iflag
762 CODE:
763#ifdef I_TERMIOS /* References a termios structure member so ifdef it out. */
764 termios_ref->c_iflag = iflag;
765#else
766 not_here("setiflag");
767#endif
768
769void
770setoflag(termios_ref, oflag)
771 POSIX::Termios termios_ref
772 tcflag_t oflag
773 CODE:
774#ifdef I_TERMIOS /* References a termios structure member so ifdef it out. */
775 termios_ref->c_oflag = oflag;
776#else
777 not_here("setoflag");
778#endif
779
780void
781setcflag(termios_ref, cflag)
782 POSIX::Termios termios_ref
783 tcflag_t cflag
784 CODE:
785#ifdef I_TERMIOS /* References a termios structure member so ifdef it out. */
786 termios_ref->c_cflag = cflag;
787#else
788 not_here("setcflag");
789#endif
790
791void
792setlflag(termios_ref, lflag)
793 POSIX::Termios termios_ref
794 tcflag_t lflag
795 CODE:
796#ifdef I_TERMIOS /* References a termios structure member so ifdef it out. */
797 termios_ref->c_lflag = lflag;
798#else
799 not_here("setlflag");
800#endif
801
802void
803setcc(termios_ref, ccix, cc)
804 POSIX::Termios termios_ref
b56fc9ec 805 unsigned int ccix
a0d0e21e 806 cc_t cc
807 CODE:
808#ifdef I_TERMIOS /* References a termios structure member so ifdef it out. */
809 if (ccix >= NCCS)
810 croak("Bad setcc subscript");
811 termios_ref->c_cc[ccix] = cc;
812#else
813 not_here("setcc");
814#endif
815
816
a0d0e21e 817MODULE = POSIX PACKAGE = POSIX
818
1cb0fb50 819INCLUDE: const-xs.inc
a290f238 820
821void
822int_macro_int(sv, iv)
823 PREINIT:
824 dXSTARG;
825 STRLEN len;
826 int type;
827 INPUT:
828 SV * sv;
829 const char * s = SvPV(sv, len);
830 IV iv;
831 PPCODE:
832 /* Change this to int_macro_int(s, len, &iv, &nv);
833 if you need to return both NVs and IVs */
834 type = int_macro_int(s, len, &iv);
835 /* Return 1 or 2 items. First is error message, or undef if no error.
836 Second, if present, is found value */
837 switch (type) {
838 case PERL_constant_NOTFOUND:
839 sv = sv_2mortal(newSVpvf("%s is not a valid POSIX macro", s));
840 EXTEND(SP, 1);
841 PUSHs(&PL_sv_undef);
842 PUSHs(sv);
843 break;
844 case PERL_constant_NOTDEF:
845 sv = sv_2mortal(newSVpvf(
846 "Your vendor has not defined POSIX macro %s, used", s));
847 EXTEND(SP, 1);
848 PUSHs(&PL_sv_undef);
849 PUSHs(sv);
850 break;
851 case PERL_constant_ISIV:
852 PUSHi(iv);
853 break;
854 default:
855 sv = sv_2mortal(newSVpvf(
856 "Unexpected return type %d while processing POSIX macro %s, used",
857 type, s));
858 EXTEND(SP, 1);
859 PUSHs(&PL_sv_undef);
860 PUSHs(sv);
861 }
2304df62 862
863int
864isalnum(charstring)
767bb2e0 865 SV * charstring
866 PREINIT:
867 STRLEN len;
2304df62 868 CODE:
767bb2e0 869 unsigned char *s = (unsigned char *) SvPV(charstring, len);
870 unsigned char *e = s + len;
5344da4e 871 for (RETVAL = 1; RETVAL && s < e; s++)
2304df62 872 if (!isalnum(*s))
873 RETVAL = 0;
874 OUTPUT:
875 RETVAL
876
877int
878isalpha(charstring)
767bb2e0 879 SV * charstring
880 PREINIT:
881 STRLEN len;
2304df62 882 CODE:
767bb2e0 883 unsigned char *s = (unsigned char *) SvPV(charstring, len);
884 unsigned char *e = s + len;
5344da4e 885 for (RETVAL = 1; RETVAL && s < e; s++)
2304df62 886 if (!isalpha(*s))
887 RETVAL = 0;
888 OUTPUT:
889 RETVAL
890
891int
892iscntrl(charstring)
767bb2e0 893 SV * charstring
894 PREINIT:
895 STRLEN len;
2304df62 896 CODE:
767bb2e0 897 unsigned char *s = (unsigned char *) SvPV(charstring, len);
898 unsigned char *e = s + len;
5344da4e 899 for (RETVAL = 1; RETVAL && s < e; s++)
2304df62 900 if (!iscntrl(*s))
901 RETVAL = 0;
902 OUTPUT:
903 RETVAL
904
905int
906isdigit(charstring)
767bb2e0 907 SV * charstring
908 PREINIT:
909 STRLEN len;
2304df62 910 CODE:
767bb2e0 911 unsigned char *s = (unsigned char *) SvPV(charstring, len);
912 unsigned char *e = s + len;
5344da4e 913 for (RETVAL = 1; RETVAL && s < e; s++)
2304df62 914 if (!isdigit(*s))
915 RETVAL = 0;
916 OUTPUT:
917 RETVAL
918
919int
920isgraph(charstring)
767bb2e0 921 SV * charstring
922 PREINIT:
923 STRLEN len;
2304df62 924 CODE:
767bb2e0 925 unsigned char *s = (unsigned char *) SvPV(charstring, len);
926 unsigned char *e = s + len;
5344da4e 927 for (RETVAL = 1; RETVAL && s < e; s++)
2304df62 928 if (!isgraph(*s))
929 RETVAL = 0;
930 OUTPUT:
931 RETVAL
932
933int
934islower(charstring)
767bb2e0 935 SV * charstring
936 PREINIT:
937 STRLEN len;
2304df62 938 CODE:
767bb2e0 939 unsigned char *s = (unsigned char *) SvPV(charstring, len);
940 unsigned char *e = s + len;
5344da4e 941 for (RETVAL = 1; RETVAL && s < e; s++)
2304df62 942 if (!islower(*s))
943 RETVAL = 0;
944 OUTPUT:
945 RETVAL
946
947int
948isprint(charstring)
767bb2e0 949 SV * charstring
950 PREINIT:
951 STRLEN len;
2304df62 952 CODE:
767bb2e0 953 unsigned char *s = (unsigned char *) SvPV(charstring, len);
954 unsigned char *e = s + len;
5344da4e 955 for (RETVAL = 1; RETVAL && s < e; s++)
2304df62 956 if (!isprint(*s))
957 RETVAL = 0;
958 OUTPUT:
959 RETVAL
960
961int
962ispunct(charstring)
767bb2e0 963 SV * charstring
964 PREINIT:
965 STRLEN len;
2304df62 966 CODE:
767bb2e0 967 unsigned char *s = (unsigned char *) SvPV(charstring, len);
968 unsigned char *e = s + len;
5344da4e 969 for (RETVAL = 1; RETVAL && s < e; s++)
2304df62 970 if (!ispunct(*s))
971 RETVAL = 0;
972 OUTPUT:
973 RETVAL
974
975int
976isspace(charstring)
767bb2e0 977 SV * charstring
978 PREINIT:
979 STRLEN len;
2304df62 980 CODE:
767bb2e0 981 unsigned char *s = (unsigned char *) SvPV(charstring, len);
982 unsigned char *e = s + len;
5344da4e 983 for (RETVAL = 1; RETVAL && s < e; s++)
2304df62 984 if (!isspace(*s))
985 RETVAL = 0;
986 OUTPUT:
987 RETVAL
8990e307 988
989int
2304df62 990isupper(charstring)
767bb2e0 991 SV * charstring
992 PREINIT:
993 STRLEN len;
2304df62 994 CODE:
767bb2e0 995 unsigned char *s = (unsigned char *) SvPV(charstring, len);
996 unsigned char *e = s + len;
5344da4e 997 for (RETVAL = 1; RETVAL && s < e; s++)
2304df62 998 if (!isupper(*s))
999 RETVAL = 0;
1000 OUTPUT:
1001 RETVAL
8990e307 1002
1003int
2304df62 1004isxdigit(charstring)
767bb2e0 1005 SV * charstring
1006 PREINIT:
1007 STRLEN len;
2304df62 1008 CODE:
767bb2e0 1009 unsigned char *s = (unsigned char *) SvPV(charstring, len);
1010 unsigned char *e = s + len;
5344da4e 1011 for (RETVAL = 1; RETVAL && s < e; s++)
2304df62 1012 if (!isxdigit(*s))
1013 RETVAL = 0;
1014 OUTPUT:
1015 RETVAL
1016
1017SysRet
1018open(filename, flags = O_RDONLY, mode = 0666)
1019 char * filename
1020 int flags
a0d0e21e 1021 Mode_t mode
748a9306 1022 CODE:
1023 if (flags & (O_APPEND|O_CREAT|O_TRUNC|O_RDWR|O_WRONLY|O_EXCL))
1024 TAINT_PROPER("open");
1025 RETVAL = open(filename, flags, mode);
1026 OUTPUT:
1027 RETVAL
1028
2304df62 1029
1030HV *
1031localeconv()
1032 CODE:
a0d0e21e 1033#ifdef HAS_LOCALECONV
2304df62 1034 struct lconv *lcbuf;
1035 RETVAL = newHV();
c4e79b56 1036 sv_2mortal((SV*)RETVAL);
8063af02 1037 if ((lcbuf = localeconv())) {
2304df62 1038 /* the strings */
1039 if (lcbuf->decimal_point && *lcbuf->decimal_point)
1040 hv_store(RETVAL, "decimal_point", 13,
1041 newSVpv(lcbuf->decimal_point, 0), 0);
1042 if (lcbuf->thousands_sep && *lcbuf->thousands_sep)
1043 hv_store(RETVAL, "thousands_sep", 13,
1044 newSVpv(lcbuf->thousands_sep, 0), 0);
28e8609d 1045#ifndef NO_LOCALECONV_GROUPING
2304df62 1046 if (lcbuf->grouping && *lcbuf->grouping)
1047 hv_store(RETVAL, "grouping", 8,
1048 newSVpv(lcbuf->grouping, 0), 0);
28e8609d 1049#endif
2304df62 1050 if (lcbuf->int_curr_symbol && *lcbuf->int_curr_symbol)
1051 hv_store(RETVAL, "int_curr_symbol", 15,
1052 newSVpv(lcbuf->int_curr_symbol, 0), 0);
1053 if (lcbuf->currency_symbol && *lcbuf->currency_symbol)
1054 hv_store(RETVAL, "currency_symbol", 15,
1055 newSVpv(lcbuf->currency_symbol, 0), 0);
1056 if (lcbuf->mon_decimal_point && *lcbuf->mon_decimal_point)
1057 hv_store(RETVAL, "mon_decimal_point", 17,
1058 newSVpv(lcbuf->mon_decimal_point, 0), 0);
39e571d4 1059#ifndef NO_LOCALECONV_MON_THOUSANDS_SEP
2304df62 1060 if (lcbuf->mon_thousands_sep && *lcbuf->mon_thousands_sep)
1061 hv_store(RETVAL, "mon_thousands_sep", 17,
1062 newSVpv(lcbuf->mon_thousands_sep, 0), 0);
3609ea0d 1063#endif
28e8609d 1064#ifndef NO_LOCALECONV_MON_GROUPING
2304df62 1065 if (lcbuf->mon_grouping && *lcbuf->mon_grouping)
1066 hv_store(RETVAL, "mon_grouping", 12,
1067 newSVpv(lcbuf->mon_grouping, 0), 0);
28e8609d 1068#endif
2304df62 1069 if (lcbuf->positive_sign && *lcbuf->positive_sign)
1070 hv_store(RETVAL, "positive_sign", 13,
1071 newSVpv(lcbuf->positive_sign, 0), 0);
1072 if (lcbuf->negative_sign && *lcbuf->negative_sign)
1073 hv_store(RETVAL, "negative_sign", 13,
1074 newSVpv(lcbuf->negative_sign, 0), 0);
1075 /* the integers */
1076 if (lcbuf->int_frac_digits != CHAR_MAX)
1077 hv_store(RETVAL, "int_frac_digits", 15,
1078 newSViv(lcbuf->int_frac_digits), 0);
1079 if (lcbuf->frac_digits != CHAR_MAX)
1080 hv_store(RETVAL, "frac_digits", 11,
1081 newSViv(lcbuf->frac_digits), 0);
1082 if (lcbuf->p_cs_precedes != CHAR_MAX)
1083 hv_store(RETVAL, "p_cs_precedes", 13,
1084 newSViv(lcbuf->p_cs_precedes), 0);
1085 if (lcbuf->p_sep_by_space != CHAR_MAX)
1086 hv_store(RETVAL, "p_sep_by_space", 14,
1087 newSViv(lcbuf->p_sep_by_space), 0);
1088 if (lcbuf->n_cs_precedes != CHAR_MAX)
1089 hv_store(RETVAL, "n_cs_precedes", 13,
1090 newSViv(lcbuf->n_cs_precedes), 0);
1091 if (lcbuf->n_sep_by_space != CHAR_MAX)
1092 hv_store(RETVAL, "n_sep_by_space", 14,
1093 newSViv(lcbuf->n_sep_by_space), 0);
1094 if (lcbuf->p_sign_posn != CHAR_MAX)
1095 hv_store(RETVAL, "p_sign_posn", 11,
1096 newSViv(lcbuf->p_sign_posn), 0);
1097 if (lcbuf->n_sign_posn != CHAR_MAX)
1098 hv_store(RETVAL, "n_sign_posn", 11,
1099 newSViv(lcbuf->n_sign_posn), 0);
1100 }
a0d0e21e 1101#else
1102 localeconv(); /* A stub to call not_here(). */
1103#endif
2304df62 1104 OUTPUT:
1105 RETVAL
1106
1107char *
c28ee57b 1108setlocale(category, locale = 0)
2304df62 1109 int category
1110 char * locale
1ba01ae3 1111 PREINIT:
1112 char * retval;
c28ee57b 1113 CODE:
1ba01ae3 1114 retval = setlocale(category, locale);
1115 if (retval) {
1116 /* Save retval since subsequent setlocale() calls
1117 * may overwrite it. */
1118 RETVAL = savepv(retval);
36477c24 1119#ifdef USE_LOCALE_CTYPE
bbce6d69 1120 if (category == LC_CTYPE
1121#ifdef LC_ALL
1122 || category == LC_ALL
1123#endif
1124 )
1125 {
1126 char *newctype;
1127#ifdef LC_ALL
1128 if (category == LC_ALL)
1129 newctype = setlocale(LC_CTYPE, NULL);
1130 else
1131#endif
1132 newctype = RETVAL;
864dbfa3 1133 new_ctype(newctype);
bbce6d69 1134 }
36477c24 1135#endif /* USE_LOCALE_CTYPE */
1136#ifdef USE_LOCALE_COLLATE
bbce6d69 1137 if (category == LC_COLLATE
1138#ifdef LC_ALL
1139 || category == LC_ALL
1140#endif
1141 )
1142 {
1143 char *newcoll;
1144#ifdef LC_ALL
1145 if (category == LC_ALL)
1146 newcoll = setlocale(LC_COLLATE, NULL);
1147 else
1148#endif
1149 newcoll = RETVAL;
864dbfa3 1150 new_collate(newcoll);
bbce6d69 1151 }
36477c24 1152#endif /* USE_LOCALE_COLLATE */
1153#ifdef USE_LOCALE_NUMERIC
bbce6d69 1154 if (category == LC_NUMERIC
1155#ifdef LC_ALL
1156 || category == LC_ALL
1157#endif
1158 )
1159 {
1160 char *newnum;
1161#ifdef LC_ALL
1162 if (category == LC_ALL)
1163 newnum = setlocale(LC_NUMERIC, NULL);
1164 else
1165#endif
1166 newnum = RETVAL;
864dbfa3 1167 new_numeric(newnum);
bbce6d69 1168 }
36477c24 1169#endif /* USE_LOCALE_NUMERIC */
bbce6d69 1170 }
1ba01ae3 1171 else
1172 RETVAL = NULL;
c28ee57b 1173 OUTPUT:
1174 RETVAL
1ba01ae3 1175 CLEANUP:
1176 if (RETVAL)
1177 Safefree(RETVAL);
2304df62 1178
e1ca407b 1179NV
2304df62 1180acos(x)
e1ca407b 1181 NV x
2304df62 1182
e1ca407b 1183NV
2304df62 1184asin(x)
e1ca407b 1185 NV x
2304df62 1186
e1ca407b 1187NV
2304df62 1188atan(x)
e1ca407b 1189 NV x
2304df62 1190
e1ca407b 1191NV
2304df62 1192ceil(x)
e1ca407b 1193 NV x
2304df62 1194
e1ca407b 1195NV
2304df62 1196cosh(x)
e1ca407b 1197 NV x
2304df62 1198
e1ca407b 1199NV
2304df62 1200floor(x)
e1ca407b 1201 NV x
2304df62 1202
e1ca407b 1203NV
2304df62 1204fmod(x,y)
e1ca407b 1205 NV x
1206 NV y
2304df62 1207
1208void
1209frexp(x)
e1ca407b 1210 NV x
2304df62 1211 PPCODE:
1212 int expvar;
2304df62 1213 /* (We already know stack is long enough.) */
1214 PUSHs(sv_2mortal(newSVnv(frexp(x,&expvar))));
1215 PUSHs(sv_2mortal(newSViv(expvar)));
1216
e1ca407b 1217NV
2304df62 1218ldexp(x,exp)
e1ca407b 1219 NV x
2304df62 1220 int exp
1221
e1ca407b 1222NV
2304df62 1223log10(x)
e1ca407b 1224 NV x
2304df62 1225
1226void
1227modf(x)
e1ca407b 1228 NV x
2304df62 1229 PPCODE:
e1ca407b 1230 NV intvar;
2304df62 1231 /* (We already know stack is long enough.) */
bf4acbe4 1232 PUSHs(sv_2mortal(newSVnv(Perl_modf(x,&intvar))));
2304df62 1233 PUSHs(sv_2mortal(newSVnv(intvar)));
1234
e1ca407b 1235NV
2304df62 1236sinh(x)
e1ca407b 1237 NV x
2304df62 1238
e1ca407b 1239NV
3b35bae3 1240tan(x)
e1ca407b 1241 NV x
3b35bae3 1242
e1ca407b 1243NV
2304df62 1244tanh(x)
e1ca407b 1245 NV x
2304df62 1246
1247SysRet
1dfe7606 1248sigaction(sig, optaction, oldaction = 0)
2304df62 1249 int sig
1dfe7606 1250 SV * optaction
2304df62 1251 POSIX::SigAction oldaction
1252 CODE:
2986a63f 1253#if defined(WIN32) || defined(NETWARE)
6dead956 1254 RETVAL = not_here("sigaction");
1255#else
2304df62 1256# This code is really grody because we're trying to make the signal
1257# interface look beautiful, which is hard.
1258
2304df62 1259 {
27da23d5 1260 dVAR;
1dfe7606 1261 POSIX__SigAction action;
f4c556ac 1262 GV *siggv = gv_fetchpv("SIG", TRUE, SVt_PVHV);
2304df62 1263 struct sigaction act;
1264 struct sigaction oact;
1dfe7606 1265 sigset_t sset;
183bde56 1266 SV *osset_sv;
27c1a449 1267 sigset_t osset;
2304df62 1268 POSIX__SigSet sigset;
1269 SV** svp;
1d81eac9 1270 SV** sigsvp;
3609ea0d 1271
516d25e8 1272 if (sig < 0) {
1273 croak("Negative signals are not allowed");
1274 }
1275
1d81eac9 1276 if (sig == 0 && SvPOK(ST(0))) {
aa07b2f6 1277 const char *s = SvPVX_const(ST(0));
1d81eac9 1278 int i = whichsig(s);
1279
1280 if (i < 0 && memEQ(s, "SIG", 3))
1281 i = whichsig(s + 3);
1282 if (i < 0) {
1283 if (ckWARN(WARN_SIGNAL))
1284 Perl_warner(aTHX_ packWARN(WARN_SIGNAL),
1285 "No such signal: SIG%s", s);
1286 XSRETURN_UNDEF;
1287 }
1288 else
1289 sig = i;
1290 }
3609ea0d 1291#ifdef NSIG
1292 if (sig > NSIG) { /* NSIG - 1 is still okay. */
1293 Perl_warner(aTHX_ packWARN(WARN_SIGNAL),
1294 "No such signal: %d", sig);
1295 XSRETURN_UNDEF;
1296 }
1297#endif
1d81eac9 1298 sigsvp = hv_fetch(GvHVn(siggv),
1299 PL_sig_name[sig],
1300 strlen(PL_sig_name[sig]),
1301 TRUE);
2304df62 1302
1dfe7606 1303 /* Check optaction and set action */
1304 if(SvTRUE(optaction)) {
1305 if(sv_isa(optaction, "POSIX::SigAction"))
1306 action = (HV*)SvRV(optaction);
1307 else
1308 croak("action is not of type POSIX::SigAction");
1309 }
1310 else {
1311 action=0;
1312 }
1313
1314 /* sigaction() is supposed to look atomic. In particular, any
1315 * signal handler invoked during a sigaction() call should
1316 * see either the old or the new disposition, and not something
1317 * in between. We use sigprocmask() to make it so.
1318 */
1319 sigfillset(&sset);
1320 RETVAL=sigprocmask(SIG_BLOCK, &sset, &osset);
1321 if(RETVAL == -1)
15c0d34a 1322 XSRETURN_UNDEF;
1dfe7606 1323 ENTER;
1324 /* Restore signal mask no matter how we exit this block. */
183bde56 1325 osset_sv = newSVpv((char *)(&osset), sizeof(sigset_t));
1326 SAVEFREESV( osset_sv );
40b7a5f5 1327 SAVEDESTRUCTOR_X(restore_sigmask, osset_sv);
1dfe7606 1328
1329 RETVAL=-1; /* In case both oldaction and action are 0. */
1330
1331 /* Remember old disposition if desired. */
2304df62 1332 if (oldaction) {
017a3ce5 1333 svp = hv_fetchs(oldaction, "HANDLER", TRUE);
1dfe7606 1334 if(!svp)
1335 croak("Can't supply an oldaction without a HANDLER");
1336 if(SvTRUE(*sigsvp)) { /* TBD: what if "0"? */
1337 sv_setsv(*svp, *sigsvp);
1338 }
1339 else {
1340 sv_setpv(*svp, "DEFAULT");
1341 }
1342 RETVAL = sigaction(sig, (struct sigaction *)0, & oact);
1343 if(RETVAL == -1)
15c0d34a 1344 XSRETURN_UNDEF;
1dfe7606 1345 /* Get back the mask. */
017a3ce5 1346 svp = hv_fetchs(oldaction, "MASK", TRUE);
1dfe7606 1347 if (sv_isa(*svp, "POSIX::SigSet")) {
1348 IV tmp = SvIV((SV*)SvRV(*svp));
1349 sigset = INT2PTR(sigset_t*, tmp);
1350 }
1351 else {
a02a5408 1352 Newx(sigset, 1, sigset_t);
1dfe7606 1353 sv_setptrobj(*svp, sigset, "POSIX::SigSet");
1354 }
1355 *sigset = oact.sa_mask;
1356
1357 /* Get back the flags. */
017a3ce5 1358 svp = hv_fetchs(oldaction, "FLAGS", TRUE);
1dfe7606 1359 sv_setiv(*svp, oact.sa_flags);
d36b6582 1360
1361 /* Get back whether the old handler used safe signals. */
017a3ce5 1362 svp = hv_fetchs(oldaction, "SAFE", TRUE);
e91e3b10 1363 sv_setiv(*svp,
1364 /* compare incompatible pointers by casting to integer */
1365 PTR2nat(oact.sa_handler) == PTR2nat(PL_csighandlerp));
2304df62 1366 }
1367
1368 if (action) {
d36b6582 1369 /* Safe signals use "csighandler", which vectors through the
1370 PL_sighandlerp pointer when it's safe to do so.
1371 (BTW, "csighandler" is very different from "sighandler".) */
017a3ce5 1372 svp = hv_fetchs(action, "SAFE", FALSE);
e91e3b10 1373 act.sa_handler =
1374 DPTR2FPTR(
87d46f97 1375 void (*)(int),
e91e3b10 1376 (*svp && SvTRUE(*svp))
1377 ? PL_csighandlerp : PL_sighandlerp
1378 );
d36b6582 1379
1380 /* Vector new Perl handler through %SIG.
1381 (The core signal handlers read %SIG to dispatch.) */
017a3ce5 1382 svp = hv_fetchs(action, "HANDLER", FALSE);
2304df62 1383 if (!svp)
1384 croak("Can't supply an action without a HANDLER");
1dfe7606 1385 sv_setsv(*sigsvp, *svp);
d36b6582 1386
1387 /* This call actually calls sigaction() with almost the
1388 right settings, including appropriate interpretation
1389 of DEFAULT and IGNORE. However, why are we doing
1390 this when we're about to do it again just below? XXX */
1391 mg_set(*sigsvp);
1392
1393 /* And here again we duplicate -- DEFAULT/IGNORE checking. */
1dfe7606 1394 if(SvPOK(*svp)) {
aa07b2f6 1395 const char *s=SvPVX_const(*svp);
1dfe7606 1396 if(strEQ(s,"IGNORE")) {
1397 act.sa_handler = SIG_IGN;
1398 }
1399 else if(strEQ(s,"DEFAULT")) {
1400 act.sa_handler = SIG_DFL;
1401 }
1dfe7606 1402 }
2304df62 1403
1404 /* Set up any desired mask. */
017a3ce5 1405 svp = hv_fetchs(action, "MASK", FALSE);
2304df62 1406 if (svp && sv_isa(*svp, "POSIX::SigSet")) {
ac634a9a 1407 IV tmp = SvIV((SV*)SvRV(*svp));
1dfe7606 1408 sigset = INT2PTR(sigset_t*, tmp);
2304df62 1409 act.sa_mask = *sigset;
1410 }
1411 else
85e6fe83 1412 sigemptyset(& act.sa_mask);
2304df62 1413
1414 /* Set up any desired flags. */
017a3ce5 1415 svp = hv_fetchs(action, "FLAGS", FALSE);
2304df62 1416 act.sa_flags = svp ? SvIV(*svp) : 0;
2304df62 1417
1dfe7606 1418 /* Don't worry about cleaning up *sigsvp if this fails,
1419 * because that means we tried to disposition a
1420 * nonblockable signal, in which case *sigsvp is
1421 * essentially meaningless anyway.
1422 */
6c418a22 1423 RETVAL = sigaction(sig, & act, (struct sigaction *)0);
a7aad5de 1424 if(RETVAL == -1)
1425 XSRETURN_UNDEF;
2304df62 1426 }
1dfe7606 1427
1428 LEAVE;
2304df62 1429 }
6dead956 1430#endif
2304df62 1431 OUTPUT:
1432 RETVAL
1433
1434SysRet
1435sigpending(sigset)
1436 POSIX::SigSet sigset
1437
1438SysRet
1439sigprocmask(how, sigset, oldsigset = 0)
1440 int how
b13bbac7 1441 POSIX::SigSet sigset = NO_INIT
33c27489 1442 POSIX::SigSet oldsigset = NO_INIT
1443INIT:
a3b811a7 1444 if (! SvOK(ST(1))) {
b13bbac7 1445 sigset = NULL;
a3b811a7 1446 } else if (sv_isa(ST(1), "POSIX::SigSet")) {
b13bbac7 1447 IV tmp = SvIV((SV*)SvRV(ST(1)));
1448 sigset = INT2PTR(POSIX__SigSet,tmp);
1449 } else {
1450 croak("sigset is not of type POSIX::SigSet");
33c27489 1451 }
b13bbac7 1452
194cfca0 1453 if (items < 3 || ! SvOK(ST(2))) {
b13bbac7 1454 oldsigset = NULL;
a3b811a7 1455 } else if (sv_isa(ST(2), "POSIX::SigSet")) {
33c27489 1456 IV tmp = SvIV((SV*)SvRV(ST(2)));
56431972 1457 oldsigset = INT2PTR(POSIX__SigSet,tmp);
b13bbac7 1458 } else {
1459 croak("oldsigset is not of type POSIX::SigSet");
33c27489 1460 }
2304df62 1461
1462SysRet
1463sigsuspend(signal_mask)
1464 POSIX::SigSet signal_mask
1465
2304df62 1466void
1467_exit(status)
1468 int status
8990e307 1469
85e6fe83 1470SysRet
8990e307 1471close(fd)
1472 int fd
1473
85e6fe83 1474SysRet
8990e307 1475dup(fd)
1476 int fd
1477
85e6fe83 1478SysRet
8990e307 1479dup2(fd1, fd2)
1480 int fd1
1481 int fd2
1482
4a9d6100 1483SV *
a0d0e21e 1484lseek(fd, offset, whence)
85e6fe83 1485 int fd
1486 Off_t offset
1487 int whence
4a9d6100 1488 CODE:
1489 Off_t pos = PerlLIO_lseek(fd, offset, whence);
1490 RETVAL = sizeof(Off_t) > sizeof(IV)
1491 ? newSVnv((NV)pos) : newSViv((IV)pos);
1492 OUTPUT:
1493 RETVAL
8990e307 1494
c5661c80 1495void
8990e307 1496nice(incr)
1497 int incr
15f0f28a 1498 PPCODE:
1499 errno = 0;
1500 if ((incr = nice(incr)) != -1 || errno == 0) {
1501 if (incr == 0)
1502 XPUSHs(sv_2mortal(newSVpvn("0 but true", 10)));
1503 else
1504 XPUSHs(sv_2mortal(newSViv(incr)));
1505 }
8990e307 1506
8063af02 1507void
8990e307 1508pipe()
85e6fe83 1509 PPCODE:
1510 int fds[2];
85e6fe83 1511 if (pipe(fds) != -1) {
924508f0 1512 EXTEND(SP,2);
85e6fe83 1513 PUSHs(sv_2mortal(newSViv(fds[0])));
1514 PUSHs(sv_2mortal(newSViv(fds[1])));
1515 }
8990e307 1516
85e6fe83 1517SysRet
a0d0e21e 1518read(fd, buffer, nbytes)
7747499c 1519 PREINIT:
1520 SV *sv_buffer = SvROK(ST(1)) ? SvRV(ST(1)) : ST(1);
1521 INPUT:
1522 int fd
1523 size_t nbytes
1524 char * buffer = sv_grow( sv_buffer, nbytes+1 );
a0d0e21e 1525 CLEANUP:
7747499c 1526 if (RETVAL >= 0) {
b162af07 1527 SvCUR_set(sv_buffer, RETVAL);
7747499c 1528 SvPOK_only(sv_buffer);
1529 *SvEND(sv_buffer) = '\0';
bbce6d69 1530 SvTAINTED_on(sv_buffer);
7747499c 1531 }
8990e307 1532
85e6fe83 1533SysRet
8990e307 1534setpgid(pid, pgid)
86200d5c 1535 pid_t pid
1536 pid_t pgid
8990e307 1537
86200d5c 1538pid_t
8990e307 1539setsid()
1540
86200d5c 1541pid_t
8990e307 1542tcgetpgrp(fd)
1543 int fd
1544
85e6fe83 1545SysRet
8990e307 1546tcsetpgrp(fd, pgrp_id)
1547 int fd
86200d5c 1548 pid_t pgrp_id
8990e307 1549
8063af02 1550void
8990e307 1551uname()
2304df62 1552 PPCODE:
a0d0e21e 1553#ifdef HAS_UNAME
85e6fe83 1554 struct utsname buf;
85e6fe83 1555 if (uname(&buf) >= 0) {
924508f0 1556 EXTEND(SP, 5);
85e6fe83 1557 PUSHs(sv_2mortal(newSVpv(buf.sysname, 0)));
1558 PUSHs(sv_2mortal(newSVpv(buf.nodename, 0)));
1559 PUSHs(sv_2mortal(newSVpv(buf.release, 0)));
1560 PUSHs(sv_2mortal(newSVpv(buf.version, 0)));
1561 PUSHs(sv_2mortal(newSVpv(buf.machine, 0)));
8990e307 1562 }
a0d0e21e 1563#else
1564 uname((char *) 0); /* A stub to call not_here(). */
1565#endif
8990e307 1566
85e6fe83 1567SysRet
a0d0e21e 1568write(fd, buffer, nbytes)
1569 int fd
1570 char * buffer
1571 size_t nbytes
1572
33f01dd1 1573SV *
1574tmpnam()
1575 PREINIT:
1576 STRLEN i;
1577 int len;
1578 CODE:
1579 RETVAL = newSVpvn("", 0);
1580 SvGROW(RETVAL, L_tmpnam);
1581 len = strlen(tmpnam(SvPV(RETVAL, i)));
1582 SvCUR_set(RETVAL, len);
1583 OUTPUT:
1584 RETVAL
a0d0e21e 1585
1586void
1587abort()
1588
1589int
1590mblen(s, n)
1591 char * s
1592 size_t n
1593
1594size_t
1595mbstowcs(s, pwcs, n)
1596 wchar_t * s
1597 char * pwcs
1598 size_t n
1599
1600int
1601mbtowc(pwc, s, n)
1602 wchar_t * pwc
1603 char * s
1604 size_t n
1605
1606int
1607wcstombs(s, pwcs, n)
1608 char * s
1609 wchar_t * pwcs
1610 size_t n
1611
1612int
1613wctomb(s, wchar)
1614 char * s
1615 wchar_t wchar
1616
1617int
1618strcoll(s1, s2)
1619 char * s1
1620 char * s2
1621
a89d8a78 1622void
1623strtod(str)
1624 char * str
1625 PREINIT:
1626 double num;
1627 char *unparsed;
1628 PPCODE:
36477c24 1629 SET_NUMERIC_LOCAL();
a89d8a78 1630 num = strtod(str, &unparsed);
1631 PUSHs(sv_2mortal(newSVnv(num)));
1632 if (GIMME == G_ARRAY) {
924508f0 1633 EXTEND(SP, 1);
a89d8a78 1634 if (unparsed)
1635 PUSHs(sv_2mortal(newSViv(strlen(unparsed))));
1636 else
6b88bc9c 1637 PUSHs(&PL_sv_undef);
a89d8a78 1638 }
1639
1640void
1641strtol(str, base = 0)
1642 char * str
1643 int base
1644 PREINIT:
1645 long num;
1646 char *unparsed;
1647 PPCODE:
1648 num = strtol(str, &unparsed, base);
42718184 1649#if IVSIZE <= LONGSIZE
1650 if (num < IV_MIN || num > IV_MAX)
a89d8a78 1651 PUSHs(sv_2mortal(newSVnv((double)num)));
42718184 1652 else
1653#endif
1654 PUSHs(sv_2mortal(newSViv((IV)num)));
a89d8a78 1655 if (GIMME == G_ARRAY) {
924508f0 1656 EXTEND(SP, 1);
a89d8a78 1657 if (unparsed)
1658 PUSHs(sv_2mortal(newSViv(strlen(unparsed))));
1659 else
6b88bc9c 1660 PUSHs(&PL_sv_undef);
a89d8a78 1661 }
1662
1663void
1664strtoul(str, base = 0)
1665 char * str
1666 int base
1667 PREINIT:
1668 unsigned long num;
1669 char *unparsed;
1670 PPCODE:
1671 num = strtoul(str, &unparsed, base);
84c133a0 1672#if IVSIZE <= LONGSIZE
1673 if (num > IV_MAX)
a89d8a78 1674 PUSHs(sv_2mortal(newSVnv((double)num)));
84c133a0 1675 else
1676#endif
1677 PUSHs(sv_2mortal(newSViv((IV)num)));
a89d8a78 1678 if (GIMME == G_ARRAY) {
924508f0 1679 EXTEND(SP, 1);
a89d8a78 1680 if (unparsed)
1681 PUSHs(sv_2mortal(newSViv(strlen(unparsed))));
1682 else
6b88bc9c 1683 PUSHs(&PL_sv_undef);
a89d8a78 1684 }
1685
8063af02 1686void
a0d0e21e 1687strxfrm(src)
1688 SV * src
85e6fe83 1689 CODE:
a0d0e21e 1690 {
1691 STRLEN srclen;
1692 STRLEN dstlen;
1693 char *p = SvPV(src,srclen);
1694 srclen++;
561b68a9 1695 ST(0) = sv_2mortal(newSV(srclen*4+1));
a0d0e21e 1696 dstlen = strxfrm(SvPVX(ST(0)), p, (size_t)srclen);
1697 if (dstlen > srclen) {
1698 dstlen++;
1699 SvGROW(ST(0), dstlen);
1700 strxfrm(SvPVX(ST(0)), p, (size_t)dstlen);
1701 dstlen--;
1702 }
b162af07 1703 SvCUR_set(ST(0), dstlen);
a0d0e21e 1704 SvPOK_only(ST(0));
1705 }
1706
1707SysRet
1708mkfifo(filename, mode)
1709 char * filename
1710 Mode_t mode
748a9306 1711 CODE:
1712 TAINT_PROPER("mkfifo");
1713 RETVAL = mkfifo(filename, mode);
1714 OUTPUT:
1715 RETVAL
a0d0e21e 1716
1717SysRet
1718tcdrain(fd)
1719 int fd
1720
1721
1722SysRet
1723tcflow(fd, action)
1724 int fd
1725 int action
1726
1727
1728SysRet
1729tcflush(fd, queue_selector)
1730 int fd
1731 int queue_selector
1732
1733SysRet
1734tcsendbreak(fd, duration)
1735 int fd
1736 int duration
1737
1738char *
c1646883 1739asctime(sec, min, hour, mday, mon, year, wday = 0, yday = 0, isdst = -1)
a0d0e21e 1740 int sec
1741 int min
1742 int hour
1743 int mday
1744 int mon
1745 int year
1746 int wday
1747 int yday
1748 int isdst
1749 CODE:
1750 {
1751 struct tm mytm;
7747499c 1752 init_tm(&mytm); /* XXX workaround - see init_tm() above */
a0d0e21e 1753 mytm.tm_sec = sec;
1754 mytm.tm_min = min;
1755 mytm.tm_hour = hour;
1756 mytm.tm_mday = mday;
1757 mytm.tm_mon = mon;
1758 mytm.tm_year = year;
1759 mytm.tm_wday = wday;
1760 mytm.tm_yday = yday;
1761 mytm.tm_isdst = isdst;
1762 RETVAL = asctime(&mytm);
1763 }
1764 OUTPUT:
1765 RETVAL
1766
1767long
1768clock()
1769
1770char *
1771ctime(time)
748a9306 1772 Time_t &time
8990e307 1773
37120919 1774void
1775times()
1776 PPCODE:
1777 struct tms tms;
1778 clock_t realtime;
1779 realtime = times( &tms );
924508f0 1780 EXTEND(SP,5);
9607fc9c 1781 PUSHs( sv_2mortal( newSViv( (IV) realtime ) ) );
1782 PUSHs( sv_2mortal( newSViv( (IV) tms.tms_utime ) ) );
1783 PUSHs( sv_2mortal( newSViv( (IV) tms.tms_stime ) ) );
1784 PUSHs( sv_2mortal( newSViv( (IV) tms.tms_cutime ) ) );
1785 PUSHs( sv_2mortal( newSViv( (IV) tms.tms_cstime ) ) );
37120919 1786
a0d0e21e 1787double
1788difftime(time1, time2)
1789 Time_t time1
1790 Time_t time2
1791
1792SysRetLong
c1646883 1793mktime(sec, min, hour, mday, mon, year, wday = 0, yday = 0, isdst = -1)
a0d0e21e 1794 int sec
1795 int min
1796 int hour
1797 int mday
1798 int mon
1799 int year
1800 int wday
1801 int yday
1802 int isdst
1803 CODE:
1804 {
1805 struct tm mytm;
7747499c 1806 init_tm(&mytm); /* XXX workaround - see init_tm() above */
a0d0e21e 1807 mytm.tm_sec = sec;
1808 mytm.tm_min = min;
1809 mytm.tm_hour = hour;
1810 mytm.tm_mday = mday;
1811 mytm.tm_mon = mon;
1812 mytm.tm_year = year;
1813 mytm.tm_wday = wday;
1814 mytm.tm_yday = yday;
1815 mytm.tm_isdst = isdst;
aebaba0b 1816 RETVAL = (SysRetLong) mktime(&mytm);
a0d0e21e 1817 }
85e6fe83 1818 OUTPUT:
1819 RETVAL
a0d0e21e 1820
8063af02 1821#XXX: if $xsubpp::WantOptimize is always the default
1822# sv_setpv(TARG, ...) could be used rather than
1823# ST(0) = sv_2mortal(newSVpv(...))
1824void
e44f695e 1825strftime(fmt, sec, min, hour, mday, mon, year, wday = -1, yday = -1, isdst = -1)
a0d0e21e 1826 char * fmt
1827 int sec
1828 int min
1829 int hour
1830 int mday
1831 int mon
1832 int year
1833 int wday
1834 int yday
1835 int isdst
1836 CODE:
1837 {
b3c85772 1838 char *buf = my_strftime(fmt, sec, min, hour, mday, mon, year, wday, yday, isdst);
2a74cb2d 1839 if (buf) {
1840 ST(0) = sv_2mortal(newSVpv(buf, 0));
bf8afc63 1841 Safefree(buf);
2a74cb2d 1842 }
a0d0e21e 1843 }
1844
1845void
1846tzset()
1847
1848void
1849tzname()
1850 PPCODE:
924508f0 1851 EXTEND(SP,2);
79cb57f6 1852 PUSHs(sv_2mortal(newSVpvn(tzname[0],strlen(tzname[0]))));
1853 PUSHs(sv_2mortal(newSVpvn(tzname[1],strlen(tzname[1]))));
a0d0e21e 1854
1855SysRet
1856access(filename, mode)
1857 char * filename
1858 Mode_t mode
1859
1860char *
1861ctermid(s = 0)
3ab23a19 1862 char * s = 0;
1863 CODE:
1864#ifdef HAS_CTERMID_R
e02b9112 1865 s = (char *) safemalloc((size_t) L_ctermid);
3ab23a19 1866#endif
1867 RETVAL = ctermid(s);
1868 OUTPUT:
1869 RETVAL
d1fd7089 1870 CLEANUP:
3ab23a19 1871#ifdef HAS_CTERMID_R
d1fd7089 1872 Safefree(s);
3ab23a19 1873#endif
a0d0e21e 1874
1875char *
1876cuserid(s = 0)
1877 char * s = 0;
1878
1879SysRetLong
1880fpathconf(fd, name)
1881 int fd
1882 int name
1883
1884SysRetLong
1885pathconf(filename, name)
1886 char * filename
1887 int name
1888
1889SysRet
1890pause()
1891
a043a685 1892SysRet
1893setgid(gid)
1894 Gid_t gid
13ec70af 1895 CLEANUP:
e9df3e1a 1896#ifndef WIN32
13ec70af 1897 if (RETVAL >= 0) {
1898 PL_gid = getgid();
1899 PL_egid = getegid();
1900 }
e9df3e1a 1901#endif
a043a685 1902
1903SysRet
1904setuid(uid)
1905 Uid_t uid
13ec70af 1906 CLEANUP:
e9df3e1a 1907#ifndef WIN32
13ec70af 1908 if (RETVAL >= 0) {
1909 PL_uid = getuid();
1910 PL_euid = geteuid();
1911 }
e9df3e1a 1912#endif
a043a685 1913
a0d0e21e 1914SysRetLong
1915sysconf(name)
1916 int name
1917
1918char *
1919ttyname(fd)
1920 int fd
a043a685 1921
c6c619a9 1922void
b5846a0b 1923getcwd()
8f95b30d 1924 PPCODE:
1925 {
1926 dXSTARG;
89423764 1927 getcwd_sv(TARG);
8f95b30d 1928 XSprePUSH; PUSHTARG;
1929 }
1930
0d7021f5 1931SysRet
1932lchown(uid, gid, path)
1933 Uid_t uid
1934 Gid_t gid
1935 char * path
1936 CODE:
1937#ifdef HAS_LCHOWN
1938 /* yes, the order of arguments is different,
1939 * but consistent with CORE::chown() */
1940 RETVAL = lchown(path, uid, gid);
1941#else
1942 RETVAL = not_here("lchown");
1943#endif
1944 OUTPUT:
1945 RETVAL