Редактировать: кажется, что-то другое, сначала прочитайте Edit2.Java Classloader: Как загрузить класс с двоичным именем, отличным от имени поиска?
Как загрузить класс с двоичным именем, отличным от имени поиска?
Я знаю, что Java Spec не позволяет этого, но у меня есть приложение передо мной, которое делает это как-то.
У меня есть собственный сервер (Windows exe, который запускает JVM), компания, которая его создала, больше не существует. Поскольку я, наконец, попал в ошибку, я начал извлекать классы, чтобы исправить это и переместить его в Linux одновременно. Занятия запутаны, но это меня не беспокоит.
Я манипулировал их загрузчиком Classloader верхнего уровня, чтобы сбрасывать каждый файл класса после вызова defineClass
(он загружает классы из зашифрованного архива). Там я вижу, что он ищет и определяет класс P.x, но файл класса dumped содержит класс с двоичным именем P.X (несоответствие случая) (есть также внутренние классы с именем P.X $ Y, поэтому они соответствуют двоичному имени). Несовпадение корпуса должно выдавать NoClassDefFoundError
в defineClass()
, но, поскольку я выгружаю класс непосредственно после defineClass()
, это явно не так.
Я немного боюсь продолжить, прежде чем я это понимаю. Потому что, возможно, они включали некоторые ловушки, такие как классы, которые не должны загружаться и проверять их позже. Поэтому, возможно, сервер вернет неправильные результаты, если я просто продолжу, не понимая подробно, как это работает.
От того, как они упаковали JVM, я предполагаю, что они не манипулировали JVM. От взгляда на код OpenJDK такие вещи находятся в части C++, поэтому они не могут просто заменить некоторый файл класса для достижения этого.
я могу думать только 3 способами без взлома JVM:
- Я надеялся, что, может быть, есть какой-то секрет VM Arg, но я ничего не нашел до сих пор: https://web.archive.org/web/20100130070337/http://www.md.pp.ru/~eu/jdk6options.html
- Заменить
java.lang.ClassLoader
и установить принятый в name to null , так что имеет значение только двоичное имя. Но будет ли это работать? - Использование
ClassFileTransformer
как-то. Но будет ли это работать?
Я не нашел подсказки, что они делают 2) или 3). И я не вижу, как это будет работать, потому что код ищет P.x, поэтому даже если PX будет загружен, так что не уверен, что это поможет.
Есть ли у кого-нибудь идеи, как это можно сделать? Они используют 32-битный JRE Hotspot 1.6.0_01-b06, смешанный режим в Windows.
Юридическое примечание. В моей стране мне разрешено ремонтировать программное обеспечение, за которое я заплатил много денег и который больше не поддерживается.
Редактировать 1:
Теперь я ввел свой маленький образец, который делает то же самое в коде. Он не работает с NoClassDefFoundError
, поэтому они не манипулируют JVM или java.lang.ClassLoader, так что этот тест не выполняется глобально.
Редактировать2:
Это, вероятно, файловая система, но наоборот, как предложено в комментариях (я перезаписываю файлы).
Так как теперь я могу приложить отладчик, я увидел что-то странное: byte[]
, который входит в defineClass()
, содержит правильное двоичное имя.
Если P/x и P/X существуют, я бы переопределил их, потому что Windows FS нечувствительна к регистру. Doh. Вернусь, если я уверен, что это так.
Просто интересно. В какой стране это? – tbodt
Обратите внимание, что всевозможные вещи возможны через интерфейс отладчика. –
На самом деле, нормальный загрузчик классов также ведет себя в файловой системе без учета регистра (иногда вызывает проблемы на компьютерах Mac). Может быть, этот «зашифрованный архив» не чувствителен к регистру? – Thilo