Advertisement
Guest User

Untitled

a guest
Aug 23rd, 2012
61
0
Never
Not a member of Pastebin yet? Sign Up, it unlocks many cool features!
text 14.35 KB | None | 0 0
  1. // Bytecode patcher for GLSL shaders.
  2. // I don't care what you do with this source but I'd like some credit if you reuse this in part or whole. - daxnitro
  3.  
  4. import javassist.*;
  5. import javassist.expr.*;
  6.  
  7. import java.io.File;
  8. import java.io.DataOutputStream;
  9. import java.io.FileOutputStream;
  10.  
  11. import java.lang.Exception;
  12.  
  13. import daxnitro.nitrous.ModHooks;
  14. import daxnitro.nitrous.PreferenceManager;
  15.  
  16. public class Hooks implements ModHooks {
  17. public boolean install(File installDir) throws Throwable {
  18.  
  19. String dirPath = installDir.getPath();
  20.  
  21. File codesign_rsa = new File(dirPath, "META-INF/CODESIGN.RSA");
  22. File codesign_sf = new File(dirPath, "META-INF/CODESIGN.SF");
  23.  
  24. if (codesign_rsa.exists() || codesign_sf.exists()) {
  25. System.out.println("Warning: This version of Nitrous is unaware of CODESIGN.RSA and CODESIGN.SF. It's recommended that you download the newest version at nitrous.daxnitro.com.");
  26. }
  27.  
  28. ClassPool pool = ClassPool.getDefault();
  29. pool.appendClassPath(dirPath);
  30. pool.appendClassPath(new File(new File(Hooks.class.getProtectionDomain().getCodeSource().getLocation().toURI()).getParentFile(), "files").getPath());
  31.  
  32. String lwjglPath = new File(new File(PreferenceManager.getStringValue(PreferenceManager.MC_JAR_PATH_KEY)).getParentFile(), "lwjgl.jar").getPath();
  33. pool.appendClassPath(lwjglPath);
  34.  
  35. // EntityRenderer.class
  36.  
  37. CtClass entityRenderer = pool.get(EntityRenderer);
  38.  
  39. CtClass floatLongParameter[] = {CtClass.floatType, CtClass.longType};
  40.  
  41. CtMethod renderWorld = entityRenderer.getDeclaredMethod(EntityRenderer_renderWorld, floatLongParameter);
  42.  
  43. final Hooks hooks = this;
  44.  
  45. renderWorld.instrument(
  46. new ExprEditor() {
  47. public void edit(MethodCall m) throws CannotCompileException {
  48. if (m.getClassName().equals("Shaders") && m.getMethodName().equals("beginRender")) {
  49. hooks.alreadyInstalled = true;
  50. }
  51. }
  52. }
  53. );
  54.  
  55. if (alreadyInstalled) {
  56. System.out.println("Already installed.");
  57. return true;
  58. }
  59.  
  60. renderWorld.insertBefore("Shaders.beginRender(" + EntityRenderer_mc +", $1, $2);");
  61.  
  62. renderWorld.insertAfter("Shaders.endRender();");
  63.  
  64. renderWorld.instrument(
  65. new ExprEditor() {
  66. public void edit(MethodCall m) throws CannotCompileException {
  67. if (m.getClassName().equals(EntityRenderer) && m.getMethodName().equals(EntityRenderer_setupCameraTransform) && m.getSignature().equals("(FI)V")) {
  68. m.replace("{ Shaders.setClearColor(" + EntityRenderer_fogColorRed + ", " + EntityRenderer_fogColorGreen + ", " + EntityRenderer_fogColorBlue + "); $_ = $proceed($$); Shaders.setCamera($1); }");
  69. } else if (m.getClassName().equals(RenderGlobal) && m.getMethodName().equals(RenderGlobal_sortAndRender) && m.getSignature().equals(RenderGlobal_sortAndRender_sig)) {
  70. m.replace("{ if ($2 == 0) { Shaders.beginTerrain(); $_ = $proceed($$); Shaders.endTerrain(); } else if ($2 == 1) { Shaders.beginWater(); $_ = $proceed($$); Shaders.endWater(); } else { $_ = $proceed($$); } }");
  71. } else if (m.getClassName().equals(RenderGlobal) && m.getMethodName().equals(RenderGlobal_renderAllRenderLists) && m.getSignature().equals("(ID)V")) {
  72. m.replace("{ Shaders.beginWater(); $_ = $proceed($$); Shaders.endWater(); }");
  73. } else if (m.getClassName().equals(EntityRenderer) && m.getMethodName().equals(EntityRenderer_renderRainSnow) && m.getSignature().equals("(F)V")) {
  74. m.replace("{ Shaders.beginWeather(); $_ = $proceed($$); Shaders.endWeather(); }");
  75. } else if (m.getClassName().equals(EntityRenderer) && m.getMethodName().equals(EntityRenderer_renderHand) && m.getSignature().equals("(FI)V")) {
  76. m.replace("{ Shaders.beginHand(); $_ = $proceed($$); Shaders.endHand(); }");
  77. }
  78. }
  79. }
  80. );
  81.  
  82. CtClass doubleParameter[] = {CtClass.doubleType};
  83.  
  84. CtMethod enableLightmap = entityRenderer.getDeclaredMethod(EntityRenderer_enableLightmap, doubleParameter);
  85.  
  86. enableLightmap.insertAfter("Shaders.enableLightmap();");
  87.  
  88. CtMethod disableLightmap = entityRenderer.getDeclaredMethod(EntityRenderer_disableLightmap, doubleParameter);
  89.  
  90. disableLightmap.insertAfter("Shaders.disableLightmap();");
  91.  
  92. // Tessellator.class
  93.  
  94. CtClass tessellator = pool.get(Tessellator);
  95.  
  96. tessellator.addField(new CtField(pool.get("java.nio.ByteBuffer"), "shadersBuffer", tessellator), "null");
  97. tessellator.addField(new CtField(pool.get("java.nio.ShortBuffer"), "shadersShortBuffer", tessellator), "null");
  98. tessellator.addField(new CtField(pool.get("short[]"), "shadersData", tessellator), "new short[]{-1, 0}");
  99.  
  100. CtClass int3Parameter[] = {CtClass.intType, CtClass.intType, CtClass.intType};
  101.  
  102. CtMethod setEntity = CtMethod.make("public void setEntity(int id) {" +
  103. "shadersData[0] = (short)id;" +
  104. "}", tessellator);
  105. tessellator.addMethod(setEntity);
  106.  
  107. CtClass intParameter[] = {CtClass.intType};
  108.  
  109. tessellator.getDeclaredConstructor(intParameter).insertAfter(
  110. "shadersBuffer = " + GLAllocation + "." + GLAllocation_createDirectByteBuffer + "($1 / 8 * 4);" +
  111. "shadersShortBuffer = shadersBuffer.asShortBuffer();"
  112. );
  113.  
  114. CtClass noParameter[] = {};
  115.  
  116. CtMethod draw = tessellator.getDeclaredMethod(Tessellator_draw, noParameter);
  117.  
  118. draw.instrument(
  119. new ExprEditor() {
  120. public void edit(MethodCall m) throws CannotCompileException {
  121. if (m.getClassName().equals("org.lwjgl.opengl.GL11") && m.getMethodName().equals("glDrawArrays")) {
  122. m.replace("{" +
  123. "if (Shaders.entityAttrib >= 0) {" +
  124. "org.lwjgl.opengl.ARBVertexProgram.glEnableVertexAttribArrayARB(Shaders.entityAttrib);" +
  125. "org.lwjgl.opengl.ARBVertexProgram.glVertexAttribPointerARB(Shaders.entityAttrib, 2, false, false, 4, (java.nio.ShortBuffer)shadersShortBuffer.position(0));" +
  126. "}" +
  127. "$_ = $proceed($$);" +
  128. "if (Shaders.entityAttrib >= 0) { org.lwjgl.opengl.ARBVertexProgram.glDisableVertexAttribArrayARB(Shaders.entityAttrib); }" +
  129. "}");
  130. }
  131. }
  132. }
  133. );
  134.  
  135. CtMethod reset = tessellator.getDeclaredMethod(Tessellator_reset, noParameter);
  136.  
  137. reset.insertBefore("shadersBuffer.clear();");
  138.  
  139. CtClass float3Parameter[] = {CtClass.floatType, CtClass.floatType, CtClass.floatType};
  140.  
  141. CtClass double3Parameter[] = {CtClass.doubleType, CtClass.doubleType, CtClass.doubleType};
  142.  
  143. CtMethod addVertex = tessellator.getDeclaredMethod(Tessellator_addVertex, double3Parameter);
  144.  
  145. addVertex.insertBefore(
  146. "if ("+Tessellator_drawMode+" == 7 && "+Tessellator_convertQuadsToTriangles+" && ("+Tessellator_addedVertices+" + 1) % 4 == 0 && "+Tessellator_hasNormals+") {" +
  147. ""+Tessellator_rawBuffer+"["+Tessellator_rawBufferIndex+" + 6] = "+Tessellator_rawBuffer+"[("+Tessellator_rawBufferIndex+" - 24) + 6];" +
  148. "shadersBuffer.putShort(shadersData[0]).putShort(shadersData[1]);" +
  149. ""+Tessellator_rawBuffer+"["+Tessellator_rawBufferIndex+" + 8 + 6] = "+Tessellator_rawBuffer+"[("+Tessellator_rawBufferIndex+" + 8 - 16) + 6];" +
  150. "shadersBuffer.putShort(shadersData[0]).putShort(shadersData[1]);" +
  151. "}" +
  152. "shadersBuffer.putShort(shadersData[0]).putShort(shadersData[1]);"
  153. );
  154.  
  155. // RenderBlocks.class
  156.  
  157. CtClass renderBlocks = pool.get(RenderBlocks);
  158.  
  159. CtClass block = pool.get(Block);
  160.  
  161. CtClass renderFaceParameter[] = {block, CtClass.doubleType, CtClass.doubleType, CtClass.doubleType, CtClass.intType};
  162.  
  163. CtMethod renderBottomFace = renderBlocks.getDeclaredMethod(RenderBlocks_renderBottomFace, renderFaceParameter);
  164. renderBottomFace.insertBefore(Tessellator+"."+Tessellator_instance+"."+Tessellator_setNormal+"(0.0F, -1.0F, 0.0F);");
  165.  
  166. CtMethod renderTopFace = renderBlocks.getDeclaredMethod(RenderBlocks_renderTopFace, renderFaceParameter);
  167. renderTopFace.insertBefore(Tessellator+"."+Tessellator_instance+"."+Tessellator_setNormal+"(0.0F, 1.0F, 0.0F);");
  168.  
  169. CtMethod renderEastFace = renderBlocks.getDeclaredMethod(RenderBlocks_renderEastFace, renderFaceParameter);
  170. renderEastFace.insertBefore(Tessellator+"."+Tessellator_instance+"."+Tessellator_setNormal+"(0.0F, 0.0F, -1.0F);");
  171.  
  172. CtMethod renderWestFace = renderBlocks.getDeclaredMethod(RenderBlocks_renderWestFace, renderFaceParameter);
  173. renderWestFace.insertBefore(Tessellator+"."+Tessellator_instance+"."+Tessellator_setNormal+"(0.0F, 0.0F, 1.0F);");
  174.  
  175. CtMethod renderNorthFace = renderBlocks.getDeclaredMethod(RenderBlocks_renderNorthFace, renderFaceParameter);
  176. renderNorthFace.insertBefore(Tessellator+"."+Tessellator_instance+"."+Tessellator_setNormal+"(-1.0F, 0.0F, 0.0F);");
  177.  
  178. CtMethod renderSouthFace = renderBlocks.getDeclaredMethod(RenderBlocks_renderSouthFace, renderFaceParameter);
  179. renderSouthFace.insertBefore(Tessellator+"."+Tessellator_instance+"."+Tessellator_setNormal+"(1.0F, 0.0F, 0.0F);");
  180.  
  181. // RenderGlobal.class
  182.  
  183. CtClass renderGlobal = pool.get(RenderGlobal);
  184.  
  185. CtClass floatParameter[] = {CtClass.floatType};
  186.  
  187. CtMethod renderSky = renderGlobal.getDeclaredMethod(RenderGlobal_renderSky, floatParameter);
  188.  
  189. renderSky.instrument(
  190. new ExprEditor() {
  191. public void edit(MethodCall m) throws CannotCompileException {
  192. if (m.getClassName().equals(World) && m.getMethodName().equals(World_getStarBrightness) && m.getSignature().equals("(F)F")) {
  193. m.replace("{ $_ = $proceed($$); Shaders.setCelestialPosition(); }");
  194. }
  195. }
  196. }
  197. );
  198.  
  199. CtMethod[] methods = renderGlobal.getDeclaredMethods();
  200.  
  201. for (CtMethod method : methods) {
  202. method.instrument(
  203. new ExprEditor() {
  204. public void edit(MethodCall m) throws CannotCompileException {
  205. if (m.getClassName().equals("org.lwjgl.opengl.GL11") && m.getMethodName().equals("glEnable")) {
  206. m.replace("{ Shaders.glEnableWrapper($$); }");
  207. } else if (m.getClassName().equals("org.lwjgl.opengl.GL11") && m.getMethodName().equals("glDisable")) {
  208. m.replace("{ Shaders.glDisableWrapper($$); }");
  209. }
  210. }
  211. }
  212. );
  213. }
  214.  
  215. // RenderLiving.class
  216.  
  217. CtClass renderLiving = pool.get(RenderLiving);
  218.  
  219. methods = renderLiving.getDeclaredMethods();
  220.  
  221. for (CtMethod method : methods) {
  222. method.instrument(
  223. new ExprEditor() {
  224. public void edit(MethodCall m) throws CannotCompileException {
  225. if (m.getClassName().equals("org.lwjgl.opengl.GL11") && m.getMethodName().equals("glEnable")) {
  226. m.replace("{ Shaders.glEnableWrapper($$); }");
  227. } else if (m.getClassName().equals("org.lwjgl.opengl.GL11") && m.getMethodName().equals("glDisable")) {
  228. m.replace("{ Shaders.glDisableWrapper($$); }");
  229. }
  230. }
  231. }
  232. );
  233. }
  234.  
  235. // WorldRenderer.class
  236.  
  237. CtClass worldRenderer = pool.get(WorldRenderer);
  238.  
  239. CtMethod updateRenderer;
  240.  
  241. try {
  242. // for optifine
  243. updateRenderer = worldRenderer.getDeclaredMethod("updateRenderer");
  244. System.out.println("Optifine detected.");
  245. } catch (Exception e) {
  246. updateRenderer = worldRenderer.getDeclaredMethod(WorldRenderer_updateRenderer, noParameter);
  247. }
  248.  
  249. updateRenderer.instrument(
  250. new ExprEditor() {
  251. public void edit(MethodCall m) throws CannotCompileException {
  252. if (m.getClassName().equals(RenderBlocks) && m.getMethodName().equals(RenderBlocks_renderBlockByRenderType) && m.getSignature().equals(RenderBlocks_renderBlockByRenderType_sig)) {
  253. m.replace("{ if (Shaders.entityAttrib >= 0) { " + Tessellator + "." + Tessellator_instance + ".setEntity($1." + Block_blockID + "); } $_ = $proceed($$); }");
  254. }
  255. }
  256. }
  257. );
  258.  
  259. updateRenderer.insertAfter("if (Shaders.entityAttrib >= 0) { " + Tessellator + "." + Tessellator_instance + ".setEntity(-1); }");
  260.  
  261. // Finish up
  262.  
  263. renderLiving.writeFile(dirPath);
  264. renderGlobal.writeFile(dirPath);
  265. entityRenderer.writeFile(dirPath);
  266. tessellator.writeFile(dirPath);
  267. renderBlocks.writeFile(dirPath);
  268. worldRenderer.writeFile(dirPath);
  269.  
  270. return true;
  271. }
  272.  
  273. public boolean alreadyInstalled = false;
  274.  
  275. // Obfuscated names.
  276.  
  277. static final String EntityRenderer = "auw";
  278. static final String EntityRenderer_mc = "r";
  279. static final String EntityRenderer_renderWorld = "a";
  280. static final String EntityRenderer_fogColorRed = "n";
  281. static final String EntityRenderer_fogColorGreen = "o";
  282. static final String EntityRenderer_fogColorBlue = "p";
  283. static final String EntityRenderer_setupCameraTransform = "a";
  284. static final String EntityRenderer_renderRainSnow = "d";
  285. static final String EntityRenderer_renderHand = "b";
  286. static final String EntityRenderer_disableLightmap = "a";
  287. static final String EntityRenderer_enableLightmap = "b";
  288.  
  289. static final String EntityLiving = "jw";
  290.  
  291. static final String RenderGlobal = "avb";
  292. static final String RenderGlobal_renderSky = "a";
  293. static final String RenderGlobal_sortAndRender = "a";
  294. static final String RenderGlobal_sortAndRender_sig = "(Ljw;ID)I";
  295. static final String RenderGlobal_renderAllRenderLists = "a";
  296.  
  297. static final String Tessellator = "ave";
  298. static final String Tessellator_instance = "a";
  299. static final String Tessellator_draw = "a";
  300. static final String Tessellator_reset = "d";
  301. static final String Tessellator_setNormal = "b";
  302. static final String Tessellator_normal = "y";
  303. static final String Tessellator_addVertex = "a";
  304. static final String Tessellator_addedVertices = "s";
  305. static final String Tessellator_drawMode = "u";
  306. static final String Tessellator_convertQuadsToTriangles = "b";
  307. static final String Tessellator_hasNormals = "q";
  308. static final String Tessellator_rawBuffer = "h";
  309. static final String Tessellator_rawBufferIndex = "r";
  310.  
  311. static final String Block = "aig";
  312. static final String Block_blockID = "ca";
  313.  
  314. static final String RenderBlocks = "avg";
  315. static final String RenderBlocks_renderBottomFace = "a";
  316. static final String RenderBlocks_renderTopFace = "b";
  317. static final String RenderBlocks_renderEastFace = "c";
  318. static final String RenderBlocks_renderWestFace = "d";
  319. static final String RenderBlocks_renderNorthFace = "e";
  320. static final String RenderBlocks_renderSouthFace = "f";
  321. static final String RenderBlocks_renderBlockByRenderType = "b";
  322. static final String RenderBlocks_renderBlockByRenderType_sig = "(Laig;III)Z";
  323.  
  324. static final String World = "up";
  325. static final String World_getStarBrightness = "h";
  326.  
  327. static final String RenderLiving = "awm";
  328.  
  329. static final String WorldRenderer = "aus";
  330. static final String WorldRenderer_updateRenderer = "a";
  331.  
  332. static final String GLAllocation = "anh";
  333. static final String GLAllocation_createDirectByteBuffer = "c";
  334. }
Advertisement
Add Comment
Please, Sign In to add comment
Advertisement