comparison src/share/vm/runtime/vm_version.cpp @ 24226:abc19eb35547

allow java.vm.name and java.vm.version to be initialized from a vm.properties file next to libjvm
author Doug Simon <doug.simon@oracle.com>
date Thu, 24 Aug 2017 22:20:40 +0200
parents 719853999215
children b5a90e4a6c26
comparison
equal deleted inserted replaced
24225:a2dbb6fcc923 24226:abc19eb35547
40 #endif 40 #endif
41 #ifdef TARGET_ARCH_ppc 41 #ifdef TARGET_ARCH_ppc
42 # include "vm_version_ppc.hpp" 42 # include "vm_version_ppc.hpp"
43 #endif 43 #endif
44 44
45 const char* Abstract_VM_Version::_s_vm_release = Abstract_VM_Version::vm_release(); 45 const char* Abstract_VM_Version::_s_vm_release = NULL;
46 const char* Abstract_VM_Version::_s_vm_name = NULL;
47 int Abstract_VM_Version::_vm_properties_initialized_from_file =
48 Abstract_VM_Version::init_vm_properties(Abstract_VM_Version::_s_vm_name, Abstract_VM_Version::_s_vm_release);
46 const char* Abstract_VM_Version::_s_internal_vm_info_string = Abstract_VM_Version::internal_vm_info_string(); 49 const char* Abstract_VM_Version::_s_internal_vm_info_string = Abstract_VM_Version::internal_vm_info_string();
47 bool Abstract_VM_Version::_supports_cx8 = false; 50 bool Abstract_VM_Version::_supports_cx8 = false;
48 bool Abstract_VM_Version::_supports_atomic_getset4 = false; 51 bool Abstract_VM_Version::_supports_atomic_getset4 = false;
49 bool Abstract_VM_Version::_supports_atomic_getset8 = false; 52 bool Abstract_VM_Version::_supports_atomic_getset8 = false;
50 bool Abstract_VM_Version::_supports_atomic_getadd4 = false; 53 bool Abstract_VM_Version::_supports_atomic_getadd4 = false;
130 #ifndef HOTSPOT_VM_DISTRO 133 #ifndef HOTSPOT_VM_DISTRO
131 #error HOTSPOT_VM_DISTRO must be defined 134 #error HOTSPOT_VM_DISTRO must be defined
132 #endif 135 #endif
133 #define VMNAME HOTSPOT_VM_DISTRO " " VMLP EMBEDDED_ONLY("Embedded ") VMTYPE " VM" 136 #define VMNAME HOTSPOT_VM_DISTRO " " VMLP EMBEDDED_ONLY("Embedded ") VMTYPE " VM"
134 137
138 int Abstract_VM_Version::init_vm_properties(const char*& name, const char*& version) {
139 int non_defaults = 0;
140 name = VMNAME;
141 version = VM_RELEASE;
142 char filename[JVM_MAXPATHLEN];
143 os::jvm_path(filename, JVM_MAXPATHLEN);
144 char *end = strrchr(filename, *os::file_separator());
145 if (end == NULL) {
146 warning("Could not find '%c' in %s", *os::file_separator(), filename);
147 } else {
148 snprintf(end, JVM_MAXPATHLEN - (end - filename), "%svm.properties", os::file_separator());
149 struct stat statbuf;
150
151 if (os::stat(filename, &statbuf) == 0) {
152 FILE* stream = fopen(filename, "r");
153 if (stream != NULL) {
154 char* buffer = NEW_C_HEAP_ARRAY(char, statbuf.st_size + 1, mtInternal);
155 int num_read = fread(buffer, 1, statbuf.st_size, stream);
156 int err = ferror(stream);
157 fclose(stream);
158 if (num_read != statbuf.st_size) {
159 warning("Only read %d of " SIZE_FORMAT " characters from %s", num_read, statbuf.st_size, filename);
160 FREE_C_HEAP_ARRAY(char, buffer, mtInternal);
161 } else if (err != 0) {
162 warning("Error reading from %s (errno = %d)", filename, err);
163 FREE_C_HEAP_ARRAY(char, buffer, mtInternal);
164 } else {
165 char* last = buffer + statbuf.st_size;
166 *last = '\0';
167 // Strip trailing new lines at end of file
168 while (--last >= buffer && (*last == '\r' || *last == '\n')) {
169 *last = '\0';
170 }
171
172 char* line = buffer;
173 int line_no = 1;
174 while (line - buffer < statbuf.st_size) {
175 // find line end (\r, \n or \r\n)
176 char* nextline = NULL;
177 char* cr = strchr(line, '\r');
178 char* lf = strchr(line, '\n');
179 if (cr != NULL && lf != NULL) {
180 char* min = MIN2(cr, lf);
181 *min = '\0';
182 if (lf == cr + 1) {
183 nextline = lf + 1;
184 } else {
185 nextline = min + 1;
186 }
187 } else if (cr != NULL) {
188 *cr = '\0';
189 nextline = cr + 1;
190 } else if (lf != NULL) {
191 *lf = '\0';
192 nextline = lf + 1;
193 }
194
195 char* sep = strchr(line, '=');
196 if (sep == NULL) {
197 warning("%s:%d: could not find '='", filename, line_no);
198 return non_defaults;
199 }
200 if (sep == line) {
201 warning("%s:%d: empty property name", filename, line_no);
202 return non_defaults;
203 }
204 *sep = '\0';
205 const char* key = line;
206 char* value = sep + 1;
207 if (strcmp(key, "name") == 0) {
208 if (name == VMNAME) {
209 non_defaults++;
210 }
211 name = value;
212 } else if (strcmp(key, "version") == 0) {
213 if (version == VM_RELEASE) {
214 non_defaults++;
215 }
216 version = value;
217 } else {
218 warning("%s:%d: property must be \"name\" or \"version\", not \"%s\"", filename, line_no, key);
219 return non_defaults;
220 }
221
222 if (nextline == NULL) {
223 return true;
224 }
225 line = nextline;
226 line_no++;
227 }
228 }
229 } else {
230 warning("Error reading from %s (errno = %d)", filename, errno);
231 }
232 }
233 }
234 return non_defaults;
235 }
236
135 const char* Abstract_VM_Version::vm_name() { 237 const char* Abstract_VM_Version::vm_name() {
136 return VMNAME; 238 return _s_vm_name;
137 } 239 }
138
139 240
140 const char* Abstract_VM_Version::vm_vendor() { 241 const char* Abstract_VM_Version::vm_vendor() {
141 #ifdef VENDOR 242 #ifdef VENDOR
142 return XSTR(VENDOR); 243 return XSTR(VENDOR);
143 #else 244 #else
162 263
163 // NOTE: do *not* use stringStream. this function is called by 264 // NOTE: do *not* use stringStream. this function is called by
164 // fatal error handler. if the crash is in native thread, 265 // fatal error handler. if the crash is in native thread,
165 // stringStream cannot get resource allocated and will SEGV. 266 // stringStream cannot get resource allocated and will SEGV.
166 const char* Abstract_VM_Version::vm_release() { 267 const char* Abstract_VM_Version::vm_release() {
167 return VM_RELEASE; 268 return _s_vm_release;
168 } 269 }
169 270
170 // NOTE: do *not* use stringStream. this function is called by 271 // NOTE: do *not* use stringStream. this function is called by
171 // fatal error handlers. if the crash is in native thread, 272 // fatal error handlers. if the crash is in native thread,
172 // stringStream cannot get resource allocated and will SEGV. 273 // stringStream cannot get resource allocated and will SEGV.