1 /* 2 * Copyright (c) 2005, 2015, Oracle and/or its affiliates. All rights reserved. 3 * DO NOT ALTER OR REMOVE COPYRIGHT NOTICES OR THIS FILE HEADER. 4 * 5 * This code is free software; you can redistribute it and/or modify it 6 * under the terms of the GNU General Public License version 2 only, as 7 * published by the Free Software Foundation. 8 * 9 * This code is distributed in the hope that it will be useful, but WITHOUT 10 * ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or 11 * FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License 12 * version 2 for more details (a copy is included in the LICENSE file that 13 * accompanied this code). 14 * 15 * You should have received a copy of the GNU General Public License version 16 * 2 along with this work; if not, write to the Free Software Foundation, 17 * Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA. 18 * 19 * Please contact Oracle, 500 Oracle Parkway, Redwood Shores, CA 94065 USA 20 * or visit www.oracle.com if you need additional information or have any 21 * questions. 22 * 23 */ 24 25 import java.util.Enumeration; 26 import java.util.Hashtable; 27 import java.util.Vector; 28 29 class BuildConfig { 30 @SuppressWarnings("rawtypes") 31 Hashtable vars; 32 Vector<String> basicNames, basicPaths; 33 String[] context; 34 35 static CompilerInterface ci; 36 static CompilerInterface getCI() { 37 if (ci == null) { 38 String comp = (String)getField(null, "CompilerVersion"); 39 try { 40 ci = (CompilerInterface)Class.forName("CompilerInterface" + comp).newInstance(); 41 } catch (Exception cnfe) { 42 System.err.println("Cannot find support for compiler " + comp); 43 throw new RuntimeException(cnfe.toString()); 44 } 45 } 46 return ci; 47 } 48 49 @SuppressWarnings("rawtypes") 50 protected void initNames(String flavour, String build, String outDll) { 51 if (vars == null) vars = new Hashtable(); 52 53 String flavourBuild = flavour + "_" + build; 54 String platformName = getFieldString(null, "PlatformName"); 55 System.out.println(); 56 System.out.println(flavourBuild); 57 58 put("Name", getCI().makeCfgName(flavourBuild, platformName)); 59 put("Flavour", flavour); 60 put("Build", build); 61 put("PlatformName", platformName); 62 63 // ones mentioned above were needed to expand format 64 String buildBase = expandFormat(getFieldString(null, "BuildBase")); 65 String sourceBase = getFieldString(null, "SourceBase"); 66 String buildSpace = getFieldString(null, "BuildSpace"); 67 String outDir = buildBase; 68 String jdkTargetRoot = getFieldString(null, "JdkTargetRoot"); 69 70 put("Id", flavourBuild); 71 put("OutputDir", outDir); 72 put("SourceBase", sourceBase); 73 put("BuildBase", buildBase); 74 put("BuildSpace", buildSpace); 75 put("OutputDll", outDir + Util.sep + outDll); 76 put("JdkTargetRoot", jdkTargetRoot); 77 78 context = new String [] {flavourBuild, flavour, build, null}; 79 } 80 81 protected void init(Vector<String> includes, Vector<String> defines) { 82 initDefaultDefines(defines); 83 initDefaultCompilerFlags(includes); 84 initDefaultLinkerFlags(); 85 //handleDB(); 86 } 87 88 89 protected void initDefaultCompilerFlags(Vector<String> includes) { 90 Vector compilerFlags = new Vector(); 91 92 compilerFlags.addAll(getCI().getBaseCompilerFlags(getV("Define"), 93 includes, 94 get("OutputDir"))); 95 96 put("CompilerFlags", compilerFlags); 97 } 98 99 protected void initDefaultLinkerFlags() { 100 Vector linkerFlags = new Vector(); 101 102 linkerFlags.addAll(getCI().getBaseLinkerFlags( get("OutputDir"), get("OutputDll"), get("PlatformName"))); 103 104 put("LinkerFlags", linkerFlags); 105 } 106 107 public boolean matchesIgnoredPath(String path) { 108 Vector<String> rv = new Vector<String>(); 109 collectRelevantVectors(rv, "IgnorePath"); 110 for (String pathPart : rv) { 111 if (path.contains(pathPart)) { 112 return true; 113 } 114 } 115 return false; 116 } 117 118 public boolean matchesHidePath(String path) { 119 Vector<String> rv = new Vector<String>(); 120 collectRelevantVectors(rv, "HidePath"); 121 for (String pathPart : rv) { 122 if (path.contains(Util.normalize(pathPart))) { 123 return true; 124 } 125 } 126 return false; 127 } 128 129 public Vector<String> matchesAdditionalGeneratedPath(String fullPath) { 130 Vector<String> rv = new Vector<String>(); 131 Hashtable<String, String> v = (Hashtable<String, String>)BuildConfig.getField(this.toString(), "AdditionalGeneratedFile"); 132 if (v != null) { 133 for (Enumeration<String> e=v.keys(); e.hasMoreElements(); ) { 134 String key = e.nextElement(); 135 String val = v.get(key); 136 137 if (fullPath.endsWith(expandFormat(key))) { 138 rv.add(expandFormat(val)); 139 } 140 } 141 } 142 return rv; 143 } 144 145 // Returns true if the specified path refers to a relative alternate 146 // source file. RelativeAltSrcInclude is usually "src\closed". 147 public static boolean matchesRelativeAltSrcInclude(String path) { 148 String relativeAltSrcInclude = 149 getFieldString(null, "RelativeAltSrcInclude"); 150 Vector<String> v = getFieldVector(null, "AltRelativeInclude"); 151 for (String pathPart : v) { 152 if (path.contains(relativeAltSrcInclude + Util.sep + pathPart)) { 153 return true; 154 } 155 } 156 return false; 157 } 158 159 // Returns the relative alternate source file for the specified path. 160 // Null is returned if the specified path does not have a matching 161 // alternate source file. 162 public static String getMatchingRelativeAltSrcFile(String path) { 163 Vector<String> v = getFieldVector(null, "RelativeAltSrcFileList"); 164 if (v == null) { 165 return null; 166 } 167 for (String pathPart : v) { 168 if (path.endsWith(pathPart)) { 169 String relativeAltSrcInclude = 170 getFieldString(null, "RelativeAltSrcInclude"); 171 return relativeAltSrcInclude + Util.sep + pathPart; 172 } 173 } 174 return null; 175 } 176 177 // Returns true if the specified path has a matching alternate 178 // source file. 179 public static boolean matchesRelativeAltSrcFile(String path) { 180 return getMatchingRelativeAltSrcFile(path) != null; 181 } 182 183 // Track the specified alternate source file. The source file is 184 // tracked without the leading .*<sep><RelativeAltSrcFileList><sep> 185 // part to make matching regular source files easier. 186 public static void trackRelativeAltSrcFile(String path) { 187 String pattern = getFieldString(null, "RelativeAltSrcInclude") + 188 Util.sep; 189 int altSrcInd = path.indexOf(pattern); 190 if (altSrcInd == -1) { 191 // not an AltSrc path 192 return; 193 } 194 195 altSrcInd += pattern.length(); 196 if (altSrcInd >= path.length()) { 197 // not a valid AltSrc path 198 return; 199 } 200 201 String altSrcFile = path.substring(altSrcInd); 202 Vector v = getFieldVector(null, "RelativeAltSrcFileList"); 203 if (v == null || !v.contains(altSrcFile)) { 204 addFieldVector(null, "RelativeAltSrcFileList", altSrcFile); 205 } 206 } 207 208 void addTo(Hashtable ht, String key, String value) { 209 ht.put(expandFormat(key), expandFormat(value)); 210 } 211 212 void initDefaultDefines(Vector defines) { 213 Vector sysDefines = new Vector(); 214 sysDefines.add("WIN32"); 215 sysDefines.add("_WINDOWS"); 216 sysDefines.add("HOTSPOT_BUILD_USER=\\\""+System.getProperty("user.name")+"\\\""); 217 sysDefines.add("HOTSPOT_BUILD_TARGET=\\\""+get("Build")+"\\\""); 218 sysDefines.add("INCLUDE_TRACE=1"); 219 sysDefines.add("_JNI_IMPLEMENTATION_"); 220 if (vars.get("PlatformName").equals("Win32")) { 221 sysDefines.add("HOTSPOT_LIB_ARCH=\\\"i386\\\""); 222 } else { 223 sysDefines.add("HOTSPOT_LIB_ARCH=\\\"amd64\\\""); 224 } 225 sysDefines.add("DEBUG_LEVEL=\\\"" + get("Build")+"\\\""); 226 sysDefines.addAll(defines); 227 228 put("Define", sysDefines); 229 } 230 231 String get(String key) { 232 return (String)vars.get(key); 233 } 234 235 Vector getV(String key) { 236 return (Vector)vars.get(key); 237 } 238 239 Object getO(String key) { 240 return vars.get(key); 241 } 242 243 Hashtable getH(String key) { 244 return (Hashtable)vars.get(key); 245 } 246 247 Object getFieldInContext(String field) { 248 for (int i=0; i<context.length; i++) { 249 Object rv = getField(context[i], field); 250 if (rv != null) { 251 return rv; 252 } 253 } 254 return null; 255 } 256 257 Object lookupHashFieldInContext(String field, String key) { 258 for (int i=0; i<context.length; i++) { 259 Hashtable ht = (Hashtable)getField(context[i], field); 260 if (ht != null) { 261 Object rv = ht.get(key); 262 if (rv != null) { 263 return rv; 264 } 265 } 266 } 267 return null; 268 } 269 270 void put(String key, String value) { 271 vars.put(key, value); 272 } 273 274 void put(String key, Vector vvalue) { 275 vars.put(key, vvalue); 276 } 277 278 void add(String key, Vector vvalue) { 279 getV(key).addAll(vvalue); 280 } 281 282 String flavour() { 283 return get("Flavour"); 284 } 285 286 String build() { 287 return get("Build"); 288 } 289 290 Object getSpecificField(String field) { 291 return getField(get("Id"), field); 292 } 293 294 void putSpecificField(String field, Object value) { 295 putField(get("Id"), field, value); 296 } 297 298 void collectRelevantVectors(Vector rv, String field) { 299 for (String ctx : context) { 300 Vector<String> v = getFieldVector(ctx, field); 301 if (v != null) { 302 for (String val : v) { 303 rv.add(expandFormat(val).replace('/', '\\')); 304 } 305 } 306 } 307 } 308 309 void collectRelevantHashes(Hashtable rv, String field) { 310 for (String ctx : context) { 311 Hashtable v = (Hashtable)getField(ctx, field); 312 if (v != null) { 313 for (Enumeration e=v.keys(); e.hasMoreElements(); ) { 314 String key = (String)e.nextElement(); 315 String val = (String)v.get(key); 316 addTo(rv, key, val); 317 } 318 } 319 } 320 } 321 322 323 Vector getDefines() { 324 Vector rv = new Vector(); 325 collectRelevantVectors(rv, "Define"); 326 return rv; 327 } 328 329 Vector getIncludes() { 330 Vector rv = new Vector(); 331 collectRelevantVectors(rv, "AbsoluteInclude"); 332 rv.addAll(getSourceIncludes()); 333 return rv; 334 } 335 336 private Vector getSourceIncludes() { 337 Vector<String> rv = new Vector<String>(); 338 String sourceBase = getFieldString(null, "SourceBase"); 339 340 // add relative alternate source include values: 341 String relativeAltSrcInclude = 342 getFieldString(null, "RelativeAltSrcInclude"); 343 Vector<String> asri = new Vector<String>(); 344 collectRelevantVectors(asri, "AltRelativeInclude"); 345 for (String f : asri) { 346 rv.add(sourceBase + Util.sep + relativeAltSrcInclude + 347 Util.sep + f); 348 } 349 350 Vector<String> ri = new Vector<String>(); 351 collectRelevantVectors(ri, "RelativeInclude"); 352 for (String f : ri) { 353 rv.add(sourceBase + Util.sep + f); 354 } 355 return rv; 356 } 357 358 static Hashtable cfgData = new Hashtable(); 359 static Hashtable globalData = new Hashtable(); 360 361 static boolean appliesToTieredBuild(String cfg) { 362 return (cfg != null && 363 (cfg.startsWith("compiler1") || 364 cfg.startsWith("compiler2"))); 365 } 366 367 // Filters out the IgnoreFile and IgnorePaths since they are 368 // handled specially for tiered builds. 369 static boolean appliesToTieredBuild(String cfg, String key) { 370 return (appliesToTieredBuild(cfg))&& (key != null && !key.startsWith("Ignore")); 371 } 372 373 static String getTieredBuildCfg(String cfg) { 374 assert appliesToTieredBuild(cfg) : "illegal configuration " + cfg; 375 return "tiered" + cfg.substring(9); 376 } 377 378 static Object getField(String cfg, String field) { 379 if (cfg == null) { 380 return globalData.get(field); 381 } 382 383 Hashtable ht = (Hashtable)cfgData.get(cfg); 384 return ht == null ? null : ht.get(field); 385 } 386 387 static String getFieldString(String cfg, String field) { 388 return (String)getField(cfg, field); 389 } 390 391 static Vector getFieldVector(String cfg, String field) { 392 return (Vector)getField(cfg, field); 393 } 394 395 static void putField(String cfg, String field, Object value) { 396 putFieldImpl(cfg, field, value); 397 if (appliesToTieredBuild(cfg, field)) { 398 putFieldImpl(getTieredBuildCfg(cfg), field, value); 399 } 400 } 401 402 private static void putFieldImpl(String cfg, String field, Object value) { 403 if (cfg == null) { 404 globalData.put(field, value); 405 return; 406 } 407 408 Hashtable ht = (Hashtable)cfgData.get(cfg); 409 if (ht == null) { 410 ht = new Hashtable(); 411 cfgData.put(cfg, ht); 412 } 413 414 ht.put(field, value); 415 } 416 417 static Object getFieldHash(String cfg, String field, String name) { 418 Hashtable ht = (Hashtable)getField(cfg, field); 419 420 return ht == null ? null : ht.get(name); 421 } 422 423 static void putFieldHash(String cfg, String field, String name, Object val) { 424 putFieldHashImpl(cfg, field, name, val); 425 if (appliesToTieredBuild(cfg, field)) { 426 putFieldHashImpl(getTieredBuildCfg(cfg), field, name, val); 427 } 428 } 429 430 private static void putFieldHashImpl(String cfg, String field, String name, Object val) { 431 Hashtable ht = (Hashtable)getField(cfg, field); 432 433 if (ht == null) { 434 ht = new Hashtable(); 435 putFieldImpl(cfg, field, ht); 436 } 437 438 ht.put(name, val); 439 } 440 441 static void addFieldVector(String cfg, String field, String element) { 442 addFieldVectorImpl(cfg, field, element); 443 if (appliesToTieredBuild(cfg, field)) { 444 addFieldVectorImpl(getTieredBuildCfg(cfg), field, element); 445 } 446 } 447 448 private static void addFieldVectorImpl(String cfg, String field, String element) { 449 Vector v = (Vector)getField(cfg, field); 450 451 if (v == null) { 452 v = new Vector(); 453 putFieldImpl(cfg, field, v); 454 } 455 456 v.add(element); 457 } 458 459 String expandFormat(String format) { 460 if (format == null) { 461 return null; 462 } 463 464 if (format.indexOf('%') == -1) { 465 return format; 466 } 467 468 StringBuffer sb = new StringBuffer(); 469 int len = format.length(); 470 for (int i=0; i<len; i++) { 471 char ch = format.charAt(i); 472 if (ch == '%') { 473 char ch1 = format.charAt(i+1); 474 switch (ch1) { 475 case '%': 476 sb.append(ch1); 477 break; 478 case 'b': 479 sb.append(build()); 480 break; 481 case 'f': 482 sb.append(flavour()); 483 break; 484 default: 485 sb.append(ch); 486 sb.append(ch1); 487 } 488 i++; 489 } else { 490 sb.append(ch); 491 } 492 } 493 494 return sb.toString(); 495 } 496 } 497 498 abstract class GenericDebugConfig extends BuildConfig { 499 abstract String getOptFlag(); 500 501 protected void init(Vector includes, Vector defines) { 502 defines.add("_DEBUG"); 503 defines.add("ASSERT"); 504 505 super.init(includes, defines); 506 507 getV("CompilerFlags").addAll(getCI().getDebugCompilerFlags(getOptFlag(), get("PlatformName"))); 508 getV("LinkerFlags").addAll(getCI().getDebugLinkerFlags()); 509 } 510 } 511 512 abstract class GenericDebugNonKernelConfig extends GenericDebugConfig { 513 protected void init(Vector includes, Vector defines) { 514 super.init(includes, defines); 515 if (get("PlatformName").equals("Win32")) { 516 getCI().getAdditionalNonKernelLinkerFlags(getV("LinkerFlags")); 517 } 518 } 519 } 520 521 class C1DebugConfig extends GenericDebugNonKernelConfig { 522 String getOptFlag() { 523 return getCI().getNoOptFlag(); 524 } 525 526 C1DebugConfig() { 527 initNames("compiler1", "debug", "jvm.dll"); 528 init(getIncludes(), getDefines()); 529 } 530 } 531 532 class C1FastDebugConfig extends GenericDebugNonKernelConfig { 533 String getOptFlag() { 534 return getCI().getOptFlag(); 535 } 536 537 C1FastDebugConfig() { 538 initNames("compiler1", "fastdebug", "jvm.dll"); 539 init(getIncludes(), getDefines()); 540 } 541 } 542 543 class TieredDebugConfig extends GenericDebugNonKernelConfig { 544 String getOptFlag() { 545 return getCI().getNoOptFlag(); 546 } 547 548 TieredDebugConfig() { 549 initNames("tiered", "debug", "jvm.dll"); 550 init(getIncludes(), getDefines()); 551 } 552 } 553 554 class TieredFastDebugConfig extends GenericDebugNonKernelConfig { 555 String getOptFlag() { 556 return getCI().getOptFlag(); 557 } 558 559 TieredFastDebugConfig() { 560 initNames("tiered", "fastdebug", "jvm.dll"); 561 init(getIncludes(), getDefines()); 562 } 563 } 564 565 abstract class ProductConfig extends BuildConfig { 566 protected void init(Vector includes, Vector defines) { 567 defines.add("NDEBUG"); 568 defines.add("PRODUCT"); 569 570 super.init(includes, defines); 571 572 getV("CompilerFlags").addAll(getCI().getProductCompilerFlags()); 573 getV("LinkerFlags").addAll(getCI().getProductLinkerFlags()); 574 } 575 } 576 577 class C1ProductConfig extends ProductConfig { 578 C1ProductConfig() { 579 initNames("compiler1", "product", "jvm.dll"); 580 init(getIncludes(), getDefines()); 581 } 582 } 583 584 class TieredProductConfig extends ProductConfig { 585 TieredProductConfig() { 586 initNames("tiered", "product", "jvm.dll"); 587 init(getIncludes(), getDefines()); 588 } 589 } 590 591 592 abstract class CompilerInterface { 593 abstract Vector getBaseCompilerFlags(Vector defines, Vector includes, String outDir); 594 abstract Vector getBaseLinkerFlags(String outDir, String outDll, String platformName); 595 abstract Vector getDebugCompilerFlags(String opt, String platformName); 596 abstract Vector getDebugLinkerFlags(); 597 abstract void getAdditionalNonKernelLinkerFlags(Vector rv); 598 abstract Vector getProductCompilerFlags(); 599 abstract Vector getProductLinkerFlags(); 600 abstract String getOptFlag(); 601 abstract String getNoOptFlag(); 602 abstract String makeCfgName(String flavourBuild, String platformName); 603 604 void addAttr(Vector receiver, String attr, String value) { 605 receiver.add(attr); receiver.add(value); 606 } 607 void extAttr(Vector receiver, String attr, String value) { 608 int attr_pos=receiver.indexOf(attr) ; 609 if ( attr_pos == -1) { 610 // If attr IS NOT present in the Vector - add it 611 receiver.add(attr); receiver.add(value); 612 } else { 613 // If attr IS present in the Vector - append value to it 614 receiver.set(attr_pos+1,receiver.get(attr_pos+1)+value); 615 } 616 } 617 }