summaryrefslogtreecommitdiff
path: root/ext/POSIX
diff options
context:
space:
mode:
Diffstat (limited to 'ext/POSIX')
-rw-r--r--ext/POSIX/POSIX.pm64
-rw-r--r--ext/POSIX/POSIX.xs60
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. */