最近遇到一个CTF题。只有出错了才能够得到flag
原函数这样:
1 | int __cdecl sub_401D30(LPCCH lpMultiByteStr, int cbMultiByte, int *a3) |
逻辑先是0xFDE9u的MultiByteToWideChar也是cp65001 utf-8到0x4E4u的WideCharToMultiByte也就是cp1252。
其中utf-8遇到不认识的字符会转化为�(U+FFFD)然后转化为cp1252会变成\xFD,认识的宽字节字符也会取后面那个字节,如utf-8的 b’\xc2\x9d’ U+009D 变成’\x9d’,utf-8的b’\xc3\xbd’ U+00FD变成’\xFD’
用python模拟的时候废了很大的劲,主要是
UnicodeEncodeError: ‘charmap’ codec can’t encode character ‘\x9d’ in
position 0: character maps to
U+009D 在cp1252里面识别不了
解决方法如下:
1 | # 原始字节序列 |
根据这个帖子:https://bugs.python.org/issue45120
https://github.com/python/cpython/issues/89283#issuecomment-1093928525
WinAPI WideCharToMultiByte() uses a best-fit encoding unless the flag
WC_NO_BEST_FIT_CHARS is passed.
用了bestfit1252算法:
https://www.unicode.org/Public/MAPPINGS/VENDORS/MICSFT/WindowsBestFit/bestfit1252.txt
也可以这样模拟:
1 | import codecs |
说些什么吧!