diff options
Diffstat (limited to 'ext/POSIX')
-rw-r--r-- | ext/POSIX/POSIX.pm | 64 | ||||
-rw-r--r-- | ext/POSIX/POSIX.xs | 60 |
2 files changed, 63 insertions, 61 deletions
diff --git a/ext/POSIX/POSIX.pm b/ext/POSIX/POSIX.pm index 10a67cb630..0a3eb82f8e 100644 --- a/ext/POSIX/POSIX.pm +++ b/ext/POSIX/POSIX.pm @@ -230,32 +230,37 @@ sub import { Exporter::import($this,@list); } + +bootstrap POSIX; + +my $EINVAL = constant("EINVAL", 0); +my $EAGAIN = constant("EAGAIN", 0); + sub AUTOLOAD { if ($AUTOLOAD =~ /::(_?[a-z])/) { $AutoLoader::AUTOLOAD = $AUTOLOAD; goto &AutoLoader::AUTOLOAD } - local $constname = $AUTOLOAD; + local $! = 0; + my $constname = $AUTOLOAD; $constname =~ s/.*:://; - $val = constant($constname, $_[0]); - if ($! != 0) { - if ($! =~ /Invalid/) { - croak "$constname is not a valid POSIX macro"; - } - else { - croak "Your vendor has not defined POSIX macro $constname, used"; - } + my $val = constant($constname, $_[0]); + if ($! == 0) { + *$AUTOLOAD = sub { $val }; + } + elsif ($! == $EAGAIN) { # Not really a constant, so always call. + *$AUTOLOAD = sub { constant($constname, $_[0]) }; + } + elsif ($! == $EINVAL) { + croak "$constname is not a valid POSIX macro"; } - eval "sub $AUTOLOAD { $val }"; + else { + croak "Your vendor has not defined POSIX macro $constname, used"; + } + goto &$AUTOLOAD; } - -@liblist = (); -@liblist = split ' ', $Config::Config{"POSIX_loadlibs"} - if defined $Config::Config{"POSIX_loadlibs"}; -bootstrap POSIX @liblist; - sub usage { local ($mess) = @_; croak "Usage: POSIX::$mess"; @@ -272,16 +277,13 @@ sub unimpl { croak "Unimplemented: POSIX::$mess"; } -$gensym = "SYM000"; - sub gensym { - *{"POSIX::" . $gensym++}; + my $pkg = @_ ? ref($_[0]) || $_[0] : ""; + local *{$pkg . "::GLOB" . ++$seq}; + \delete ${$pkg . "::"}{'GLOB' . $seq}; } sub ungensym { - local($x) = shift; - $x =~ s/.*:://; - delete $POSIX::{$x}; } ############################ @@ -297,23 +299,23 @@ package FileHandle; sub new { POSIX::usage "FileHandle->new(filename, posixmode)" if @_ != 3; local($class,$filename,$mode) = @_; - local($glob) = &POSIX::gensym; + local($sym) = $class->POSIX::gensym; $mode =~ s/a.*/>>/ || $mode =~ s/w.*/>/ || ($mode = '<'); - open($glob, "$mode $filename") and - bless \$glob; + open($sym, "$mode $filename") and + bless $sym => $class; } sub new_from_fd { POSIX::usage "FileHandle->new_from_fd(fd,mode)" if @_ != 3; local($class,$fd,$mode) = @_; - local($glob) = &POSIX::gensym; + local($sym) = $class->POSIX::gensym; $mode =~ s/a.*/>>/ || $mode =~ s/w.*/>/ || ($mode = '<'); - open($glob, "$mode&=$fd") and - bless \$glob; + open($sym, "$mode&=$fd") and + bless $sym => $class; } sub clearerr { @@ -328,7 +330,6 @@ sub close { sub DESTROY { close($_[0]); - ungensym($_[0]); } sub eof { @@ -386,15 +387,14 @@ sub toupper { sub closedir { usage "closedir(dirhandle)" if @_ != 1; closedir($_[0]); - ungensym($_[0]); } sub opendir { usage "opendir(directory)" if @_ != 1; - local($dirhandle) = &gensym; + local($dirhandle) = POSIX->gensym; opendir($dirhandle, $_[0]) ? $dirhandle - : (ungensym($dirhandle), undef); + : undef; } sub readdir { diff --git a/ext/POSIX/POSIX.xs b/ext/POSIX/POSIX.xs index 2a1338200d..a303f57e32 100644 --- a/ext/POSIX/POSIX.xs +++ b/ext/POSIX/POSIX.xs @@ -1483,21 +1483,6 @@ int arg; break; } if (name[1] == '_') { -#ifdef S_ISBLK - if (strEQ(name, "S_ISBLK")) return S_ISBLK(arg); -#endif -#ifdef S_ISCHR - if (strEQ(name, "S_ISCHR")) return S_ISCHR(arg); -#endif -#ifdef S_ISDIR - if (strEQ(name, "S_ISDIR")) return S_ISDIR(arg); -#endif -#ifdef S_ISFIFO - if (strEQ(name, "S_ISFIFO")) return S_ISFIFO(arg); -#endif -#ifdef S_ISREG - if (strEQ(name, "S_ISREG")) return S_ISREG(arg); -#endif if (strEQ(name, "S_ISGID")) #ifdef S_ISGID return S_ISGID; @@ -1582,6 +1567,22 @@ int arg; #else goto not_there; #endif + errno = EAGAIN; /* the following aren't constants */ +#ifdef S_ISBLK + if (strEQ(name, "S_ISBLK")) return S_ISBLK(arg); +#endif +#ifdef S_ISCHR + if (strEQ(name, "S_ISCHR")) return S_ISCHR(arg); +#endif +#ifdef S_ISDIR + if (strEQ(name, "S_ISDIR")) return S_ISDIR(arg); +#endif +#ifdef S_ISFIFO + if (strEQ(name, "S_ISFIFO")) return S_ISFIFO(arg); +#endif +#ifdef S_ISREG + if (strEQ(name, "S_ISREG")) return S_ISREG(arg); +#endif break; } if (strEQ(name, "SEEK_CUR")) @@ -1844,6 +1845,19 @@ int arg; #else goto not_there; #endif + if (strEQ(name, "WNOHANG")) +#ifdef WNOHANG + return WNOHANG; +#else + goto not_there; +#endif + if (strEQ(name, "WUNTRACED")) +#ifdef WUNTRACED + return WUNTRACED; +#else + goto not_there; +#endif + errno = EAGAIN; /* the following aren't constants */ #ifdef WEXITSTATUS if (strEQ(name, "WEXITSTATUS")) return WEXITSTATUS(arg); #endif @@ -1856,24 +1870,12 @@ int arg; #ifdef WIFSTOPPED if (strEQ(name, "WIFSTOPPED")) return WIFSTOPPED(arg); #endif - if (strEQ(name, "WNOHANG")) -#ifdef WNOHANG - return WNOHANG; -#else - goto not_there; -#endif #ifdef WSTOPSIG if (strEQ(name, "WSTOPSIG")) return WSTOPSIG(arg); #endif #ifdef WTERMSIG if (strEQ(name, "WTERMSIG")) return WTERMSIG(arg); #endif - if (strEQ(name, "WUNTRACED")) -#ifdef WUNTRACED - return WUNTRACED; -#else - goto not_there; -#endif break; case 'X': if (strEQ(name, "X_OK")) @@ -2753,8 +2755,8 @@ sigaction(sig, action, oldaction = 0) POSIX__SigSet sigset; SV** svp; SV** sigsvp = hv_fetch(GvHVn(siggv), - whichsigname(sig), - strlen(whichsigname(sig)), + sig_name[sig], + strlen(sig_name[sig]), TRUE); /* Remember old handler name if desired. */ |