--- a/UnixOperatingSystem.st Thu Apr 25 15:06:28 2013 +0200
+++ b/UnixOperatingSystem.st Thu Apr 25 15:08:04 2013 +0200
@@ -720,7 +720,7 @@
/*
* some systems do not have realpath();
- * the alternative of reading from a 'pwp'-pipe
+ * the alternative of reading from a 'pwd'-pipe
* is way too slow. Here is a realpath for the rest of us.
* define WANT_REALPATH in the xxxIntern-file to get it.
*/
@@ -744,19 +744,20 @@
# define MAXPATHLEN 1024
# endif
-static
-char *
-realpath(path, resolved_path)
- char *path;
- char resolved_path [];
+static char *
+realpath(const char *path, char *resolved_path)
{
char copy_path[MAXPATHLEN];
char link_path[MAXPATHLEN];
- char *new_path = resolved_path;
- char *max_path;
+ char *new_path, *max_path, *mallocedPath;
int readlinks = 0;
int n;
+ if (resolved_path == NULL) {
+ mallocedPath = resolved_path = malloc(MAXPATHLEN+1);
+ }
+ new_path = resolved_path;
+
/* Make a copy of the source path since we may need to modify it. */
strcpy(copy_path, path);
path = copy_path;
@@ -768,8 +769,10 @@
#else
new_path = getwd(new_path);
#endif
- if (new_path == NULL)
+ if (new_path == NULL) {
+ if (mallocedPath) free(mallocedPath);
return(NULL);
+ }
new_path += strlen(new_path);
if (new_path[-1] != '/')
@@ -808,24 +811,28 @@
/* Safely copy the next pathname component. */
while (*path != '\0' && *path != '/') {
if (path > max_path) {
- errno = ENAMETOOLONG;
- return NULL;
+ if (mallocedPath) free(mallocedPath);
+ errno = ENAMETOOLONG;
+ return NULL;
}
*new_path++ = *path++;
}
#ifdef S_IFLNK
/* Protect against infinite loops. */
if (readlinks++ > MAX_READLINKS) {
- errno = ELOOP;
- return NULL;
+ if (mallocedPath) free(mallocedPath);
+ errno = ELOOP;
+ return NULL;
}
/* See if latest pathname component is a symlink. */
*new_path = '\0';
n = readlink(resolved_path, link_path, MAXPATHLEN - 1);
if (n < 0) {
/* EINVAL means the file exists but isn't a symlink. */
- if (errno != EINVAL)
- return NULL;
+ if (errno != EINVAL) {
+ if (mallocedPath) free(mallocedPath);
+ return NULL;
+ }
}
else {
/* Note: readlink doesn't add the null byte. */
@@ -839,8 +846,9 @@
;
/* Safe sex check. */
if (strlen(path) + n >= MAXPATHLEN) {
- errno = ENAMETOOLONG;
- return NULL;
+ if (mallocedPath) free(mallocedPath);
+ errno = ENAMETOOLONG;
+ return NULL;
}
/* Insert symlink contents into path. */
strcat(link_path, path);
@@ -5034,7 +5042,7 @@
[(p size > 1)
and:[p endsWith:(self fileSeparator)]
] whileTrue:[
- p := p copyWithoutLast:1.
+ p := p copyButLast:1.
].
^ p
].
@@ -5174,17 +5182,20 @@
if (__isStringLike(pathName)) {
#ifdef HAS_REALPATH
- char *nameP = realpath(__stringVal(pathName), NULL);
+ // POSIX-2008 says, that a NULL namebuffer causes realPath to malloc()
+ // the required memory. But this does not work as of 2013-04
+ char nameBuffer[MAXPATHLEN+1];
+ char *nameP = realpath(__stringVal(pathName), nameBuffer);
if (nameP) {
OBJ ret = __MKSTRING(nameP);
- free(nameP);
+ // free(nameP);
RETURN ( ret );
}
+ // fprintf(stderr, "stx[warning]: realpath(\"%s\") failed: %s\n", __stringVal(pathName), strerror(errno));
#endif /* ! HAS_REALPATH */
} else {
error = @symbol(argument); // argument is not a string
}
- fprintf(stderr, "stx[warning]: realpath(\"%s\") failed\n", __stringVal(pathName));
%}.
"/ Does not work as of 2013-04 (UNLIMITEDSTACK problem?)
"/ error notNil ifTrue:[
@@ -5194,6 +5205,7 @@
"
self primPathNameOf:'.'
+ self primPathNameOf:'/murks/quatsch/bla/.'
self primPathNameOf:5555
"
!
@@ -6375,36 +6387,36 @@
closeLeftOverFiles
"a bad bad kludge and workaround for a big bug in the linux
getAddrInfo implementation:
- if it gets interrupted (via a timer, for example), its domain-name
- socket remains open and is NEVER closed.
- These open files collect up and lead to no-more-files eventually.
+ if it gets interrupted (via a timer, for example), its domain-name
+ socket remains open and is NEVER closed.
+ These open files collect up and lead to no-more-files eventually.
Invoking this method helps in this situation."
|p|
p := PipeStream
- readingFrom:('lsof -p ' , (OperatingSystem getProcessId printString)).
+ readingFrom:('lsof -p ' , (OperatingSystem getProcessId printString)).
p linesDo:[:line |
- |words fd|
-
- words := line asCollectionOfWords.
- "/ COMMAND PID USER FD TYPE DEVICE SIZE NODE NAME
- words first = 'stx' ifTrue:[
- words second = (OperatingSystem getProcessId printString) ifTrue:[
- (words fourth endsWith:'u') ifTrue:[
- (words fifth = 'IPv4') ifTrue:[
- (words seventh = 'UDP') ifTrue:[
- (words last endsWith:'domain') ifTrue:[
- fd := Number readFrom:(words fourth copyWithoutLast:1).
+ |words fd|
+
+ words := line asCollectionOfWords.
+ "/ COMMAND PID USER FD TYPE DEVICE SIZE NODE NAME
+ words first = 'stx' ifTrue:[
+ words second = (OperatingSystem getProcessId printString) ifTrue:[
+ (words fourth endsWith:'u') ifTrue:[
+ (words fifth = 'IPv4') ifTrue:[
+ (words seventh = 'UDP') ifTrue:[
+ (words last endsWith:'domain') ifTrue:[
+ fd := Number readFrom:(words fourth copyButLast:1).
Transcript showCR:line.
- OperatingSystem closeFd:fd.
- ]
- ]
- ]
- ]
- ]
- ]
+ OperatingSystem closeFd:fd.
+ ]
+ ]
+ ]
+ ]
+ ]
+ ]
].
p close.
@@ -13522,11 +13534,11 @@
!UnixOperatingSystem class methodsFor:'documentation'!
version
- ^ '$Header: /cvs/stx/stx/libbasic/UnixOperatingSystem.st,v 1.313 2013-04-25 11:42:17 stefan Exp $'
+ ^ '$Header: /cvs/stx/stx/libbasic/UnixOperatingSystem.st,v 1.314 2013-04-25 13:08:04 stefan Exp $'
!
version_CVS
- ^ '$Header: /cvs/stx/stx/libbasic/UnixOperatingSystem.st,v 1.313 2013-04-25 11:42:17 stefan Exp $'
+ ^ '$Header: /cvs/stx/stx/libbasic/UnixOperatingSystem.st,v 1.314 2013-04-25 13:08:04 stefan Exp $'
! !