- 236
- 4
- 22
Всем привет. Нужна помощь по редактированию байт-кода через ASM. Вообщем, предположим есть класс майнкрафта с нужным мне методом. Мне нужно "пропатчить" этот метод. Как зарегать ASM plugin, перегнать byte[] в ClassNode и вернуть обратно в byte[] - знаю, особо объяснений не требуется. Как вставить, например вызова метода в инструкции метода - тоже знаю и уже делал.
Но в этот раз мне нужно кое-что сложнее - отменяемое событие. Конкретно в случае, из-за которого пишу сейчас - мне достаточно будет вызвать кастом событие в самом начале реализации метода и просто return`уть, если ивент отменён. Как и всегда, я использую в помощь ASM ByteCode Viewer плагин IDEA, и именно тут загвостка: как я понял, ветки if-else; try-catch; циклы и подобные конструкции используют Labels (метки), которые показываются плагинов в виде L0, L1, Ln. Я попробовал скомпилить класс, где есть простенький if - и как раз, в ASM Viewer появились те самые L0 L1 и IFEQ(который, как я понимаю, отвечает за то, какую ветку нужно выбрать в зависимости от результата проверки if).
Для реализации того, что мне нужно (вставить свой отменяемый ивент в метод из майнкрафта), мне кажется нужно создать InsnList(), вставить в начало этого листа создание и пост ивента в MinecraftForge.EVENT_BUS, а затем как-то (КАК???) создать L1, где будет InsnNode(Opcodes.RETURN) и L2, куда я скопирую все инструкции метода (то есть ивент не отменился - делаем то, что в этом методе есть), затем очистить инструкции в методе через method.instructions.clear() и вставить те инструкции, которые у меня получились в InsnList(). Но вот, увы, весь вечер просидел в гугле и не смог найти, как вставить if() { } else {} с помощью ASM в код... Помогите, пожалуйста!
Но в этот раз мне нужно кое-что сложнее - отменяемое событие. Конкретно в случае, из-за которого пишу сейчас - мне достаточно будет вызвать кастом событие в самом начале реализации метода и просто return`уть, если ивент отменён. Как и всегда, я использую в помощь ASM ByteCode Viewer плагин IDEA, и именно тут загвостка: как я понял, ветки if-else; try-catch; циклы и подобные конструкции используют Labels (метки), которые показываются плагинов в виде L0, L1, Ln. Я попробовал скомпилить класс, где есть простенький if - и как раз, в ASM Viewer появились те самые L0 L1 и IFEQ(который, как я понимаю, отвечает за то, какую ветку нужно выбрать в зависимости от результата проверки if).
Для реализации того, что мне нужно (вставить свой отменяемый ивент в метод из майнкрафта), мне кажется нужно создать InsnList(), вставить в начало этого листа создание и пост ивента в MinecraftForge.EVENT_BUS, а затем как-то (КАК???) создать L1, где будет InsnNode(Opcodes.RETURN) и L2, куда я скопирую все инструкции метода (то есть ивент не отменился - делаем то, что в этом методе есть), затем очистить инструкции в методе через method.instructions.clear() и вставить те инструкции, которые у меня получились в InsnList(). Но вот, увы, весь вечер просидел в гугле и не смог найти, как вставить if() { } else {} с помощью ASM в код... Помогите, пожалуйста!