Skip to content

Instantly share code, notes, and snippets.

@Deamon5550
Last active May 15, 2017 22:32
Show Gist options
  • Star 0 You must be signed in to star a gist
  • Fork 0 You must be signed in to fork a gist
  • Save Deamon5550/266b49c0d146ae8b3ac4604de898011d to your computer and use it in GitHub Desktop.
Save Deamon5550/266b49c0d146ae8b3ac4604de898011d to your computer and use it in GitHub Desktop.
Injector
package com.voxelgenesis.test.inject;
import com.voxelgenesis.injector.Inject;
import com.voxelgenesis.injector.Injector;
import com.voxelgenesis.test.TestTarget;
@Injector(TestTarget.class)
public class MixinTestTarget {
// This injection is replacing the value of the local assignment
// with a new value. the $( val ) wraps an instruction of arbitrary
// complexity and denotes that the injection will replace the
// value of instruction.
//
// The injection token wraps the expected starting value of the
// injection target and the method must have a return type of the
// correct type.
//
// Types are specified as fully qualified names separated by forward
// slashes '/'. This is because if there is not an import specified
// (see the next example) then there is no way to determine where the
// type name ends and a string of field accesses begins.
@Inject(target = "foo()V", matcher = "String a = $(\"foo\");"
+ "java/lang/System.out.println(a);")
public String updateFoo() {
return "bar";
}
// This injection is an example of inserting new statements into the
// method. the `$$;` token denotes this type of injection.
//
// The locals of the injector are mapped the the correct (or new)
// locals and the injector statements are inlined directly into the
// target method.
//
// Here the System class is specied in the imports array so that
// its full name does not need to be included in the matcher every time.
@Inject(target = "foo()V", matcher = "String a = \"foo\";"
+ "$$;"
+ "System.out.println(a);",
imports = {System.class})
public void updateFoo2(@Local("a") String a) {
a = "bar";
}
// This injection is replacing the condition of the if statement
// it is able to do this because the injection is performed on
// the methods statements rather than its bytecode instructions
// and so it is no problem to add a new conditional jump
@Inject(target = "foo()V", matcher = "if ($(msg2 != null))")
public boolean updateBazIf(@Local("msg2") String msg2) {
return msg2 != null && !msg2.isEmpty();
}
}
package com.voxelgenesis.test;
public class TestTarget {
public void foo() {
String msg = "foo";
System.out.println(msg);
String msg2 = "";
if (msg2 != null) {
System.out.println("baz");
}
}
}
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment