Mercurial > hg > release > icedtea7-forest-2.4 > jdk
changeset 7252:f48db95291a6
8008118: (process) Possible null pointer dereference in jdk/src/solaris/native/java/lang/UNIXProcess_md.c
Summary: Modified the path processing code so that it detects and handles out of memory errors.
Reviewed-by: chegar, martin, christos, alanb, msheppar
Contributed-by: john.zavgren@oracle.com
author | jzavgren |
---|---|
date | Thu, 11 Apr 2013 12:33:33 -0400 |
parents | c20f746699c7 |
children | c7c231608e20 |
files | make/java/java/mapfile-vers src/solaris/classes/java/lang/UNIXProcess.java.bsd src/solaris/classes/java/lang/UNIXProcess.java.linux src/solaris/classes/java/lang/UNIXProcess.java.solaris src/solaris/native/java/lang/ProcessEnvironment_md.c src/solaris/native/java/lang/UNIXProcess_md.c |
diffstat | 6 files changed, 60 insertions(+), 66 deletions(-) [+] |
line wrap: on
line diff
--- a/make/java/java/mapfile-vers Tue Dec 10 17:16:20 2013 -0800 +++ b/make/java/java/mapfile-vers Thu Apr 11 12:33:33 2013 -0400 @@ -215,7 +215,7 @@ Java_java_lang_Throwable_fillInStackTrace; Java_java_lang_Throwable_getStackTraceDepth; Java_java_lang_Throwable_getStackTraceElement; - Java_java_lang_UNIXProcess_initIDs; + Java_java_lang_UNIXProcess_init; Java_java_lang_UNIXProcess_waitForProcessExit; Java_java_lang_UNIXProcess_forkAndExec; Java_java_lang_UNIXProcess_destroyProcess;
--- a/src/solaris/classes/java/lang/UNIXProcess.java.bsd Tue Dec 10 17:16:20 2013 -0800 +++ b/src/solaris/classes/java/lang/UNIXProcess.java.bsd Thu Apr 11 12:33:33 2013 -0400 @@ -236,11 +236,10 @@ try { stderr.close(); } catch (IOException ignored) {} } - /* This routine initializes JNI field offsets for the class */ - private static native void initIDs(); + private static native void init(); static { - initIDs(); + init(); } /**
--- a/src/solaris/classes/java/lang/UNIXProcess.java.linux Tue Dec 10 17:16:20 2013 -0800 +++ b/src/solaris/classes/java/lang/UNIXProcess.java.linux Thu Apr 11 12:33:33 2013 -0400 @@ -236,11 +236,10 @@ try { stderr.close(); } catch (IOException ignored) {} } - /* This routine initializes JNI field offsets for the class */ - private static native void initIDs(); + private static native void init(); static { - initIDs(); + init(); } /**
--- a/src/solaris/classes/java/lang/UNIXProcess.java.solaris Tue Dec 10 17:16:20 2013 -0800 +++ b/src/solaris/classes/java/lang/UNIXProcess.java.solaris Thu Apr 11 12:33:33 2013 -0400 @@ -294,10 +294,9 @@ } - /* This routine initializes JNI field offsets for the class */ - private static native void initIDs(); + private static native void init(); static { - initIDs(); + init(); } }
--- a/src/solaris/native/java/lang/ProcessEnvironment_md.c Tue Dec 10 17:16:20 2013 -0800 +++ b/src/solaris/native/java/lang/ProcessEnvironment_md.c Thu Apr 11 12:33:33 2013 -0400 @@ -31,21 +31,24 @@ #ifdef __APPLE__ #include <crt_externs.h> #define environ (*_NSGetEnviron()) +#else +/* This is one of the rare times it's more portable to declare an + * external symbol explicitly, rather than via a system header. + * The declaration is standardized as part of UNIX98, but there is + * no standard (not even de-facto) header file where the + * declaration is to be found. See: + * http://www.opengroup.org/onlinepubs/009695399/functions/environ.html + * http://www.opengroup.org/onlinepubs/009695399/functions/xsh_chap02_02.html + * + * "All identifiers in this volume of IEEE Std 1003.1-2001, except + * environ, are defined in at least one of the headers" (!) + */ +extern char **environ; #endif JNIEXPORT jobjectArray JNICALL Java_java_lang_ProcessEnvironment_environ(JNIEnv *env, jclass ign) { - /* This is one of the rare times it's more portable to declare an - * external symbol explicitly, rather than via a system header. - * The declaration is standardized as part of UNIX98, but there is - * no standard (not even de-facto) header file where the - * declaration is to be found. See: - * http://www.opengroup.org/onlinepubs/007908799/xbd/envvar.html */ -#ifndef __APPLE__ - extern char ** environ; /* environ[i] looks like: VAR=VALUE\0 */ -#endif - jsize count = 0; jsize i, j; jobjectArray result;
--- a/src/solaris/native/java/lang/UNIXProcess_md.c Tue Dec 10 17:16:20 2013 -0800 +++ b/src/solaris/native/java/lang/UNIXProcess_md.c Thu Apr 11 12:33:33 2013 -0400 @@ -56,6 +56,19 @@ #ifdef __APPLE__ #include <crt_externs.h> #define environ (*_NSGetEnviron()) +#else +/* This is one of the rare times it's more portable to declare an + * external symbol explicitly, rather than via a system header. + * The declaration is standardized as part of UNIX98, but there is + * no standard (not even de-facto) header file where the + * declaration is to be found. See: + * http://www.opengroup.org/onlinepubs/009695399/functions/environ.html + * http://www.opengroup.org/onlinepubs/009695399/functions/xsh_chap02_02.html + * + * "All identifiers in this volume of IEEE Std 1003.1-2001, except + * environ, are defined in at least one of the headers" (!) + */ +extern char **environ; #endif /* @@ -156,19 +169,6 @@ } while((_result == -1) && (errno == EINTR)); \ } while(0) -/* This is one of the rare times it's more portable to declare an - * external symbol explicitly, rather than via a system header. - * The declaration is standardized as part of UNIX98, but there is - * no standard (not even de-facto) header file where the - * declaration is to be found. See: - * http://www.opengroup.org/onlinepubs/009695399/functions/environ.html - * http://www.opengroup.org/onlinepubs/009695399/functions/xsh_chap02_02.html - * - * "All identifiers in this volume of IEEE Std 1003.1-2001, except - * environ, are defined in at least one of the headers" (!) - */ -extern char **environ; - static void setSIGCHLDHandler(JNIEnv *env) @@ -245,52 +245,41 @@ } static const char * const * -splitPath(JNIEnv *env, const char *path) +effectivePathv(JNIEnv *env) { - const char *p, *q; - char **pathv; + char *p; int i; + const char *path = effectivePath(); int count = countOccurrences(path, ':') + 1; + size_t pathvsize = sizeof(const char *) * (count+1); + size_t pathsize = strlen(path) + 1; + const char **pathv = (const char **) xmalloc(env, pathvsize + pathsize); - pathv = NEW(char*, count+1); + if (pathv == NULL) + return NULL; + p = (char *) pathv + pathvsize; + memcpy(p, path, pathsize); + /* split PATH by replacing ':' with NULs; empty components => "." */ + for (i = 0; i < count; i++) { + char *q = p + strcspn(p, ":"); + pathv[i] = (p == q) ? "." : p; + *q = '\0'; + p = q + 1; + } pathv[count] = NULL; - for (p = path, i = 0; i < count; i++, p = q + 1) { - for (q = p; (*q != ':') && (*q != '\0'); q++) - ; - if (q == p) /* empty PATH component => "." */ - pathv[i] = "./"; - else { - int addSlash = ((*(q - 1)) != '/'); - pathv[i] = NEW(char, q - p + addSlash + 1); - memcpy(pathv[i], p, q - p); - if (addSlash) - pathv[i][q - p] = '/'; - pathv[i][q - p + addSlash] = '\0'; - } - } - return (const char * const *) pathv; + return pathv; } /** - * Cached value of JVM's effective PATH. + * The cached and split version of the JDK's effective PATH. * (We don't support putenv("PATH=...") in native code) */ -static const char *parentPath; - -/** - * Split, canonicalized version of parentPath - */ static const char * const *parentPathv; -static jfieldID field_exitcode; - JNIEXPORT void JNICALL -Java_java_lang_UNIXProcess_initIDs(JNIEnv *env, jclass clazz) +Java_java_lang_UNIXProcess_init(JNIEnv *env, jclass clazz) { - field_exitcode = (*env)->GetFieldID(env, clazz, "exitcode", "I"); - - parentPath = effectivePath(); - parentPathv = splitPath(env, parentPath); + parentPathv = effectivePathv(env); setSIGCHLDHandler(env); } @@ -490,6 +479,9 @@ } /* ASCII Decimal representation uses 2.4 times as many bits as binary. */ errmsg = NEW(char, strlen(format) + strlen(detail) + 3 * sizeof(errnum)); + if (errmsg == NULL) + return; + sprintf(errmsg, format, errnum, detail); s = JNU_NewStringPlatform(env, errmsg); if (s != NULL) { @@ -594,11 +586,13 @@ for (dirs = parentPathv; *dirs; dirs++) { const char * dir = *dirs; int dirlen = strlen(dir); - if (filelen + dirlen + 1 >= PATH_MAX) { + if (filelen + dirlen + 2 >= PATH_MAX) { errno = ENAMETOOLONG; continue; } memcpy(expanded_file, dir, dirlen); + if (expanded_file[dirlen - 1] != '/') + expanded_file[dirlen++] = '/'; memcpy(expanded_file + dirlen, file, filelen); expanded_file[dirlen + filelen] = '\0'; execve_with_shell_fallback(expanded_file, argv, envp);