summaryrefslogtreecommitdiff
diff options
context:
space:
mode:
authorruki <[email protected]>2025-12-10 00:36:41 +0800
committerruki <[email protected]>2025-12-10 00:36:41 +0800
commit19859fd57908ea9b08b8b6baa426051d2e7c7814 (patch)
tree0737cade757c7f259bb6ea5e73ec3b7785bbe271
parent4f042fbca4fa2417a3ea69925df49e9cb30915ac (diff)
improve macho magic
-rw-r--r--core/src/xmake/binutils/macho/prefix.h34
-rw-r--r--core/src/xmake/binutils/macho/readsyms.c27
2 files changed, 38 insertions, 23 deletions
diff --git a/core/src/xmake/binutils/macho/prefix.h b/core/src/xmake/binutils/macho/prefix.h
index fc1023356..f3c6e2302 100644
--- a/core/src/xmake/binutils/macho/prefix.h
+++ b/core/src/xmake/binutils/macho/prefix.h
@@ -325,6 +325,40 @@ static __tb_inline__ tb_uint32_t xm_binutils_macho_parse_version(tb_char_t const
* readsyms inline implementation
*/
+/* detect Mach-O format from magic bytes
+ *
+ * @param magic_bytes the magic bytes (4 bytes)
+ * @param is_32bit output: tb_true if 32-bit, tb_false if 64-bit
+ * @param swap_bytes output: tb_true if byte-swapping needed (big-endian), tb_false otherwise
+ * @return tb_true if valid Mach-O magic, tb_false otherwise
+ */
+static __tb_inline__ tb_bool_t xm_binutils_macho_detect_format(tb_uint8_t const *magic_bytes, tb_bool_t *is_32bit, tb_bool_t *swap_bytes) {
+ tb_assert_and_check_return_val(magic_bytes && is_32bit && swap_bytes, tb_false);
+
+ // check for little-endian magic numbers
+ if (magic_bytes[0] == 0xce && magic_bytes[1] == 0xfa && magic_bytes[2] == 0xed && magic_bytes[3] == 0xfe) {
+ *is_32bit = tb_true;
+ *swap_bytes = tb_false;
+ return tb_true;
+ } else if (magic_bytes[0] == 0xcf && magic_bytes[1] == 0xfa && magic_bytes[2] == 0xed && magic_bytes[3] == 0xfe) {
+ *is_32bit = tb_false;
+ *swap_bytes = tb_false;
+ return tb_true;
+ }
+ // check for big-endian magic numbers
+ else if (magic_bytes[0] == 0xfe && magic_bytes[1] == 0xed && magic_bytes[2] == 0xfa && magic_bytes[3] == 0xce) {
+ *is_32bit = tb_true;
+ *swap_bytes = tb_true;
+ return tb_true;
+ } else if (magic_bytes[0] == 0xfe && magic_bytes[1] == 0xed && magic_bytes[2] == 0xfa && magic_bytes[3] == 0xcf) {
+ *is_32bit = tb_false;
+ *swap_bytes = tb_true;
+ return tb_true;
+ }
+
+ return tb_false;
+}
+
/* read string from Mach-O string table
*
* @param istream the input stream
diff --git a/core/src/xmake/binutils/macho/readsyms.c b/core/src/xmake/binutils/macho/readsyms.c
index f1bb9511e..fac925d22 100644
--- a/core/src/xmake/binutils/macho/readsyms.c
+++ b/core/src/xmake/binutils/macho/readsyms.c
@@ -319,37 +319,18 @@ tb_bool_t xm_binutils_macho_read_symbols(tb_stream_ref_t istream, lua_State *lua
return tb_false;
}
- // check magic bytes directly (byte order independent)
- tb_bool_t swap_bytes = tb_false;
+ // detect Mach-O format
tb_bool_t is_32bit = tb_false;
- tb_bool_t is_64bit = tb_false;
-
- // check for little-endian magic numbers
- if (magic_bytes[0] == 0xce && magic_bytes[1] == 0xfa && magic_bytes[2] == 0xed && magic_bytes[3] == 0xfe) {
- is_32bit = tb_true;
- swap_bytes = tb_false;
- } else if (magic_bytes[0] == 0xcf && magic_bytes[1] == 0xfa && magic_bytes[2] == 0xed && magic_bytes[3] == 0xfe) {
- is_64bit = tb_true;
- swap_bytes = tb_false;
- }
- // check for big-endian magic numbers
- else if (magic_bytes[0] == 0xfe && magic_bytes[1] == 0xed && magic_bytes[2] == 0xfa && magic_bytes[3] == 0xce) {
- is_32bit = tb_true;
- swap_bytes = tb_true;
- } else if (magic_bytes[0] == 0xfe && magic_bytes[1] == 0xed && magic_bytes[2] == 0xfa && magic_bytes[3] == 0xcf) {
- is_64bit = tb_true;
- swap_bytes = tb_true;
- } else {
+ tb_bool_t swap_bytes = tb_false;
+ if (!xm_binutils_macho_detect_format(magic_bytes, &is_32bit, &swap_bytes)) {
return tb_false;
}
if (is_32bit) {
return xm_binutils_macho_read_symbols_32(istream, lua, swap_bytes);
- } else if (is_64bit) {
+ } else {
return xm_binutils_macho_read_symbols_64(istream, lua, swap_bytes);
}
-
- return tb_false;
}