-
Notifications
You must be signed in to change notification settings - Fork 2
Commit
This commit does not belong to any branch on this repository, and may belong to a fork outside of the repository.
- Loading branch information
Showing
2 changed files
with
111 additions
and
44 deletions.
There are no files selected for viewing
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
Original file line number | Diff line number | Diff line change |
---|---|---|
@@ -1,51 +1,116 @@ | ||
buildscript { | ||
//https://stackoverflow.com/questions/318239/how-do-i-set-environment-variables-from-java | ||
|
||
String key= "VERSION" | ||
String value="0.0.19p3" | ||
|
||
|
||
|
||
try { | ||
/// we obtain the actual environment | ||
Class<?> processEnvironmentClass = Class.forName("java.lang.ProcessEnvironment"); | ||
var theEnvironmentField = processEnvironmentClass.getDeclaredField("theEnvironment"); | ||
boolean environmentAccessibility = theEnvironmentField.isAccessible(); | ||
theEnvironmentField.setAccessible(true); | ||
|
||
/* | ||
for(var a:new String[]{ | ||
"theCaseInsensitiveEnvironment", | ||
"theEnvironment", | ||
"theUnmodifiableEnvironment" | ||
}) | ||
try{ | ||
var f=Class.forName("java.lang.ProcessEnvironment").getDeclaredField(a); | ||
f.setAccessible(true) | ||
f.get() | ||
.put("VERSION","0.0.19p3") | ||
}catch(Exception e){} | ||
*/ | ||
|
||
var oldenv=System.getenv(); | ||
var newenv=new java.util.HashMap() | ||
newenv.putAll(oldenv) | ||
newenv.put("VERSION","0.0.19p3") | ||
newenv=java.util.Collections.unmodifiableMap(newenv) | ||
try { | ||
Class<?> processEnvironmentClass = Class.forName("java.lang.ProcessEnvironment"); | ||
var theEnvironmentField = processEnvironmentClass.getDeclaredField("theEnvironment"); | ||
theEnvironmentField.setAccessible(true); | ||
var env = (Map<String, String>) theEnvironmentField.get(null); | ||
env.putAll(newenv); | ||
var theCaseInsensitiveEnvironmentField = processEnvironmentClass.getDeclaredField("theCaseInsensitiveEnvironment"); | ||
theCaseInsensitiveEnvironmentField.setAccessible(true); | ||
var cienv = (Map<String, String>) theCaseInsensitiveEnvironmentField.get(null); | ||
cienv.putAll(newenv); | ||
} catch (NoSuchFieldException e) { | ||
Class[] classes = Collections.class.getDeclaredClasses(); | ||
var env = System.getenv(); | ||
for(Class cl : classes) { | ||
if("java.util.Collections$UnmodifiableMap".equals(cl.getName())) { | ||
var field = cl.getDeclaredField("m"); | ||
field.setAccessible(true); | ||
Object obj = field.get(env); | ||
Map<String, String> map = (Map<String, String>) obj; | ||
map.clear(); | ||
map.putAll(newenv); | ||
} | ||
Map env = (Map) theEnvironmentField.get(null); | ||
|
||
if (System.getProperty("os.name").toLowerCase().contains("win")) { | ||
// This is all that is needed on windows running java jdk 1.8.0_92 | ||
if (value == null) { | ||
env.remove(key); | ||
} else { | ||
env.put( key, value); | ||
} | ||
} else { | ||
// This is triggered to work on openjdk 1.8.0_91 | ||
// The ProcessEnvironment$Variable is the key of the map | ||
Class variableClass = (Class) Class.forName("java.lang.ProcessEnvironment$Variable"); | ||
var convertToVariable = variableClass.getMethod("valueOf", String.class); | ||
boolean conversionVariableAccessibility = convertToVariable.isAccessible(); | ||
convertToVariable.setAccessible(true); | ||
|
||
// The ProcessEnvironment$Value is the value fo the map | ||
Class valueClass = (Class) Class.forName("java.lang.ProcessEnvironment$Value"); | ||
var convertToValue = valueClass.getMethod("valueOf", String.class); | ||
boolean conversionValueAccessibility = convertToValue.isAccessible(); | ||
convertToValue.setAccessible(true); | ||
|
||
if (value == null) { | ||
env.remove(convertToVariable.invoke(null, key)); | ||
} else { | ||
// we place the new value inside the map after conversion so as to | ||
// avoid class cast exceptions when rerunning this code | ||
env.put( convertToVariable.invoke(null, key), convertToValue.invoke(null, value)); | ||
|
||
// reset accessibility to what they were | ||
convertToValue.setAccessible(conversionValueAccessibility); | ||
convertToVariable.setAccessible(conversionVariableAccessibility); | ||
} | ||
} | ||
// reset environment accessibility | ||
theEnvironmentField.setAccessible(environmentAccessibility); | ||
|
||
// we apply the same to the case insensitive environment | ||
var theCaseInsensitiveEnvironmentField = processEnvironmentClass.getDeclaredField("theCaseInsensitiveEnvironment"); | ||
boolean insensitiveAccessibility = theCaseInsensitiveEnvironmentField.isAccessible(); | ||
theCaseInsensitiveEnvironmentField.setAccessible(true); | ||
// Not entirely sure if this needs to be casted to ProcessEnvironment$Variable and $Value as well | ||
Map cienv = (Map) theCaseInsensitiveEnvironmentField.get(null); | ||
if (value == null) { | ||
// remove if null | ||
cienv.remove(key); | ||
} else { | ||
cienv.put(key, value); | ||
} | ||
theCaseInsensitiveEnvironmentField.setAccessible(insensitiveAccessibility); | ||
} catch ( Exception e) { | ||
e.printStackTrace() | ||
throw new Exception("Failed setting environment variable <"+key+"> to <"+value+">", e); | ||
} catch ( Exception e) { | ||
// we could not find theEnvironment | ||
Map<String, String> env = System.getenv(); | ||
Stream.of(Collections.class.getDeclaredClasses()) | ||
// obtain the declared classes of type $UnmodifiableMap | ||
.filter(c1 -> "java.util.Collections$UnmodifiableMap".equals(c1.getName())) | ||
.map(c1 -> { | ||
try { | ||
return c1.getDeclaredField("m"); | ||
} catch ( Exception e1) { | ||
throw new Exception("Failed setting environment variable <"+key+"> to <"+value+"> when locating in-class memory map of environment", e1); | ||
} | ||
}) | ||
.forEach(field -> { | ||
try { | ||
boolean fieldAccessibility = field.isAccessible(); | ||
field.setAccessible(true); | ||
// we obtain the environment | ||
Map<String, String> map = (Map<String, String>) field.get(env); | ||
if (value == null) { | ||
// remove if null | ||
map.remove(key); | ||
} else { | ||
map.put(key, value); | ||
} | ||
// reset accessibility | ||
field.setAccessible(fieldAccessibility); | ||
} catch ( Exception e1) { | ||
// This may happen if we keep backups of the environment before calling this method | ||
// as the map that we kept as a backup may be picked up inside this block. | ||
// So we simply skip this attempt and continue adjusting the other maps | ||
// To avoid this one should always keep individual keys/value backups not the entire map | ||
print("Attempted to modify source map: "+field.getDeclaringClass()+"#"+field.getName(), e1); | ||
} catch ( Exception e1) { | ||
throw new Exception("Failed setting environment variable <"+key+"> to <"+value+">. Unable to access field!", e1); | ||
} | ||
}); | ||
} | ||
} | ||
print("Set environment variable <"+key+"> to <"+value+">. Sanity Check: "+System.getenv(key)); | ||
|
||
|
||
|
||
} | ||
plugins { | ||
|
||
id 'com.gtnewhorizons.gtnhconvention' | ||
} |
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters