xabc_lib/
header.rs

1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
75
76
77
78
79
80
81
82
83
84
85
86
87
use getset::CopyGetters;
use std::fmt;

use super::uint32_t;

use scroll::Pread;

/// ABC file header
/// 12*4 + 8 + 4 = 60
#[derive(Debug, Pread, CopyGetters, Default)]
#[get_copy = "pub"]
pub struct Header {
    /// 文件头魔数,值必须是'P' 'A' 'N' 'D' 'A' '\0' '\0' '\0'。
    magic: [u8; 8],
    /// 字节码文件除文件头魔数和本校验字段之外的内容的 adler32 校验和。
    checksum: [u8; 4],
    /// 字节码文件的版本号 (Version) 。
    version: [u8; 4],
    /// 字节码文件的大小,以字节为单位。
    file_size: uint32_t,
    /// 一个偏移量,指向外部区域。外部区域中仅包含类型为 ForeignClass 或ForeignMethod的元素。foreign_off指向该区域的第一个元素。
    foreign_off: uint32_t,
    /// 外部区域的大小,以字节为单位。
    foreign_size: uint32_t,
    /// ClassIndex结构中元素的数量,即文件中定义的Class的数量。
    classes_size: uint32_t,
    /// 一个偏移量,指向ClassIndex。
    class_idx_off: uint32_t,
    /// LineNumberProgramIndex结构中元素的数量,即文件中定义的Line number program的数量。
    num_lnps: uint32_t,
    /// 一个偏移量,指向LineNumberProgramIndex。
    lnp_idx_off: uint32_t,
    /// LiteralArrayIndex 的数量
    literalarrays_size: uint32_t,
    /// 指向 LiteralArrayIndex 的偏移量
    literalarray_idx_off: uint32_t,
    /// RegionIndex 的数量
    region_size: uint32_t,
    /// 一个偏移量,指向第一个 RegionIndex
    region_off: uint32_t,
}

impl fmt::Display for Header {
    fn fmt(&self, f: &mut fmt::Formatter<'_>) -> fmt::Result {
        let magic = String::from_utf8_lossy(&self.magic);
        let version = self
            .version
            .iter()
            .map(|x| x.to_string())
            .collect::<Vec<_>>()
            .join(".");

        write!(
            f,
            "
magic: {}
checksum: {:?}
版本: {}
文件大小: {}
外部区域偏移: {}
外部区域大小: {}
类的数量: {}
类索引的偏移: {}
行号索引数量: {}
行号索引偏移: {}
字面量数组的数量: {}
字面量数组的偏移: {}
索引头的数量: {}
索引头的偏移: {}
",
            magic,
            self.checksum,
            version,
            self.file_size,
            self.foreign_off,
            self.foreign_size,
            self.classes_size,
            self.class_idx_off,
            self.num_lnps,
            self.lnp_idx_off,
            self.literalarrays_size,
            self.literalarray_idx_off,
            self.region_size,
            self.region_off,
        )
    }
}