mirror of
https://github.com/openjdk/jdk.git
synced 2025-08-27 14:54:52 +02:00
6924920: Class Data Sharing limit on the java version string can create failures
Truncate the java version string and add a hash value if it is too long. Reviewed-by: dholmes, coleenp
This commit is contained in:
parent
8c32bcb315
commit
ef28e7a277
1 changed files with 35 additions and 10 deletions
|
@ -25,6 +25,7 @@
|
|||
#include "precompiled.hpp"
|
||||
#include "classfile/classLoader.hpp"
|
||||
#include "classfile/symbolTable.hpp"
|
||||
#include "classfile/altHashing.hpp"
|
||||
#include "memory/filemap.hpp"
|
||||
#include "runtime/arguments.hpp"
|
||||
#include "runtime/java.hpp"
|
||||
|
@ -82,9 +83,38 @@ void FileMapInfo::fail_continue(const char *msg, ...) {
|
|||
close();
|
||||
}
|
||||
|
||||
|
||||
// Fill in the fileMapInfo structure with data about this VM instance.
|
||||
|
||||
// This method copies the vm version info into header_version. If the version is too
|
||||
// long then a truncated version, which has a hash code appended to it, is copied.
|
||||
//
|
||||
// Using a template enables this method to verify that header_version is an array of
|
||||
// length JVM_IDENT_MAX. This ensures that the code that writes to the CDS file and
|
||||
// the code that reads the CDS file will both use the same size buffer. Hence, will
|
||||
// use identical truncation. This is necessary for matching of truncated versions.
|
||||
template <int N> static void get_header_version(char (&header_version) [N]) {
|
||||
assert(N == JVM_IDENT_MAX, "Bad header_version size");
|
||||
|
||||
const char *vm_version = VM_Version::internal_vm_info_string();
|
||||
const int version_len = (int)strlen(vm_version);
|
||||
|
||||
if (version_len < (JVM_IDENT_MAX-1)) {
|
||||
strcpy(header_version, vm_version);
|
||||
|
||||
} else {
|
||||
// Get the hash value. Use a static seed because the hash needs to return the same
|
||||
// value over multiple jvm invocations.
|
||||
unsigned int hash = AltHashing::murmur3_32(8191, (const jbyte*)vm_version, version_len);
|
||||
|
||||
// Truncate the ident, saving room for the 8 hex character hash value.
|
||||
strncpy(header_version, vm_version, JVM_IDENT_MAX-9);
|
||||
|
||||
// Append the hash code as eight hex digits.
|
||||
sprintf(&header_version[JVM_IDENT_MAX-9], "%08x", hash);
|
||||
header_version[JVM_IDENT_MAX-1] = 0; // Null terminate.
|
||||
}
|
||||
}
|
||||
|
||||
void FileMapInfo::populate_header(size_t alignment) {
|
||||
_header._magic = 0xf00baba2;
|
||||
_header._version = _current_version;
|
||||
|
@ -95,13 +125,7 @@ void FileMapInfo::populate_header(size_t alignment) {
|
|||
// invoked with.
|
||||
|
||||
// JVM version string ... changes on each build.
|
||||
const char *vm_version = VM_Version::internal_vm_info_string();
|
||||
if (strlen(vm_version) < (JVM_IDENT_MAX-1)) {
|
||||
strcpy(_header._jvm_ident, vm_version);
|
||||
} else {
|
||||
fail_stop("JVM Ident field for shared archive is too long"
|
||||
" - truncated to <%s>", _header._jvm_ident);
|
||||
}
|
||||
get_header_version(_header._jvm_ident);
|
||||
|
||||
// Build checks on classpath and jar files
|
||||
_header._num_jars = 0;
|
||||
|
@ -434,8 +458,9 @@ bool FileMapInfo::validate() {
|
|||
fail_continue("The shared archive file has a bad magic number.");
|
||||
return false;
|
||||
}
|
||||
if (strncmp(_header._jvm_ident, VM_Version::internal_vm_info_string(),
|
||||
JVM_IDENT_MAX-1) != 0) {
|
||||
char header_version[JVM_IDENT_MAX];
|
||||
get_header_version(header_version);
|
||||
if (strncmp(_header._jvm_ident, header_version, JVM_IDENT_MAX-1) != 0) {
|
||||
fail_continue("The shared archive file was created by a different"
|
||||
" version or build of HotSpot.");
|
||||
return false;
|
||||
|
|
Loading…
Add table
Add a link
Reference in a new issue