Получение искаженного имени из раскрученного имени
Есть ли способ вернуть искаженное имя из освобожденного имени в g++.
Например, у меня есть расколотое имя func(char*, int)
что я должен сделать, чтобы получить искаженное имя, т.е. _Z4funcPci
назад?
Мой вопрос специфичен для g++.
3 ответа
Вы можете просто использовать g++, чтобы скомпилировать пустую функцию с нужной вам подписью и извлечь из нее имя. Например:
echo "int f1(char *, int) {} " | g++ -x c++ -S - -o- | grep "^_.*:$" | sed -e 's/:$//'
дает вывод
_Z2f1Pci
что я думаю, что вам нужно. Убедитесь, что вы включили все соответствующие заголовочные файлы, так как они будут влиять на то, как символы будут искажены.
Основываясь на подходе Бояна Николича, вот лучший сценарий:
mangle.bash:
IFS='::' read -a array <<< "$1"
indexes=("${!array[@]}")
prefix=""
middle=""
suffix=""
rettype=""
if [ -z "$2" ]; then
rettype="void"
fi
for index in "${indexes[@]}"
do
#echo "$index ${array[index]}"
if [ $index == ${indexes[-1]} ]; then
#echo "last"
middle="$rettype ${array[index]};"
elif [ -n "${array[index]}" ]; then
#echo "not empty"
prefix="${prefix}struct ${array[index]}{"
suffix="${suffix}};"
fi
done
#echo "$prefix$middle$suffix $rettype $1{}"
echo "$prefix$middle$suffix $rettype $1{}" | g++ -x c++ -S - -o- | grep "^_.*:$" | sed -e 's/:$//'
Использование:
$ ./mangle.bash "abc::def::ghi()"
_ZN3abc3def3ghiEv
$ ./mangle.bash "abc::def::ghi(int i, char c)"
_ZN3abc3def3ghiEic
$ ./mangle.bash "abc::def::def(int i, char c)" constr
_ZN3abc3defC2Eic
$ ./mangle.bash "abc::def::~def()" destr
_ZN3abc3defD2Ev
Но что касается конструкторов и деструкторов, помните, что есть C0 C1 C2 и D0 D1 D2.
Что еще хуже, иногда вы не можете исказить имя, потому что вы должны получить более одного результата.
См. https://reverseengineering.stackexchange.com/q/4323/4398 (в VFT есть несколько деструкторов, и все они разбиты на ClassName::~ClassName()
). (То же самое относится и к конструкторам, я видел конструкторы C0 и C2.)
С другой стороны, этот ответ ссылается на Itanium ABI: https://refspecs.linuxbase.org/cxxabi-1.75.html, где указывается искажение.
Пакет itanium-abi Haskell: у меня он не работал (май 2014)
Существует пакет Haskell http://hackage.haskell.org/package/itanium-abi который обещает как разборку, так и искажение, но я мог запустить только разборку:
Установка на Ubuntu Precise:
sudo aptitude install ghc
sudo aptitude install cabal-install
cabal update
cabal install itanium-abi
Тогда ты бежишь ghci
и после import ABI.Itanium
а также import Data.Either
ты получаешь:
Prelude ABI.Itanium Data.Either> cxxNameToText $ head (rights [ demangleName "_ZTI13QSystemLocale" ])
"typeinfo for QSystemLocale"
Есть mangleName
, но требуется DecodedName
которая является структурой данных, а не строкой, и эта структура данных создается только demangleName
(если я что-то не заметил). Надеюсь, это будет лучше в будущем выпуске.
Код лязг
Я не пробовал код лязга.