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
88
89
90
91
92
93
94
95
96
97
98
99
100
101
102
103
104
105
106
107
108
109
110
111
112
113
114
115
116
117
118
119
120
121
122
123
124
125
126
127
128
129
130
131
132
133
134
135
136
137
138
139
140
141
142
143
144
145
146
147
148
149
150
151
152
153
154
155
156
157
158
159
160
161
162
163
164
165
166
167
168
169
170
171
172
173
174
175
176
177
178
179
180
181
182
183
184
185
186
187
188
189
190
191
192
193
194
195
196
197
//! This module corresponds to `mach/i386/_structs.h` and `mach/arm/_structs.h`.

use core::mem::size_of;

use crate::message::mach_msg_type_number_t;

// re-export if compile for aarch64/arm64 CPUs
#[cfg(target_arch = "aarch64")]
pub use arm::*;

// re-export if compile for x86 or x86-64 CPUs
#[cfg(any(target_arch = "x86", target_arch = "x86_64"))]
pub use x86::*;

/* 
 * but these `mod` both always exists whatever which target arch.
 *
 * in some cases, this maybe helps for cross-platforms.
 */

pub mod arm {
    use super::{size_of, mach_msg_type_number_t};

    #[repr(C)]
    #[derive(Copy, Clone, Debug, Default, Hash, PartialOrd, PartialEq, Eq, Ord)]
    pub struct arm_state_hdr_t {
        pub flavor: u32,
        pub count:  u32,
    }
    pub type   arm_state_hdr = arm_state_hdr_t;

    // because cannot impl Debug for union types.
    #[allow(missing_debug_implementations)]
    #[repr(C)]
    #[derive(Copy, Clone)]
    pub struct arm_unified_thread_state_t {
        pub ash: arm_state_hdr_t,
        pub uts: arm_unified_thread_state__bindgen_ty_1,
    }
    pub type   arm_unified_thread_state = arm_unified_thread_state_t;

    impl arm_unified_thread_state_t {
        pub const fn from_32(flavor: u32, ts_32: arm_thread_state32_t) -> Self {
            let count = arm_thread_state32_t::count() as u32;

            let ash = arm_state_hdr_t { flavor, count };
            let uts = arm_thread_state32or64_t { ts_32 };

            Self { ash, uts }
        }
        pub const fn from_64(flavor: u32, ts_64: arm_thread_state64_t) -> Self {
            let count = arm_thread_state64_t::count() as u32;

            let ash = arm_state_hdr_t { flavor, count };
            let uts = arm_thread_state32or64_t { ts_64 };

            Self { ash, uts }
        }
    }

    // because cannot impl Debug for union types.
    #[allow(missing_debug_implementations)]
    #[repr(C)]
    #[derive(Copy, Clone)]
    pub union arm_thread_state32or64_t {
        pub ts_32: arm_thread_state32_t,
        pub ts_64: arm_thread_state64_t,
    }
    pub type arm_thread_state32or64                 = arm_thread_state32or64_t;
    pub type arm_unified_thread_state__bindgen_ty_1 = arm_thread_state32or64_t;

    #[repr(C)]
    #[derive(Copy, Clone, Debug, Default, Hash, PartialOrd, PartialEq, Eq, Ord)]
    pub struct arm_thread_state32_t {
        pub __r:   [u32; 13usize],
        pub __sp:   u32,
        pub __lr:   u32,
        pub __pc:   u32,
        pub __cpsr: u32,
    }
    pub type arm_thread_state32        = arm_thread_state32_t;
    pub type __darwin_arm_thread_state = arm_thread_state32_t;

    impl arm_thread_state32_t {
        pub const fn new() -> Self {
            Self {
                __r:   [0; 13],
                __sp:   0,
                __lr:   0,
                __pc:   0,
                __cpsr: 0,
            }
        }

        pub const fn count() -> mach_msg_type_number_t {
            let n = size_of::<Self>() / size_of::<u32>();
            n as mach_msg_type_number_t
        }
    }

    #[repr(C)]
    #[derive(Copy, Clone, Debug, Default, Hash, PartialOrd, PartialEq, Eq, Ord)]
    pub struct arm_thread_state64_t {
        pub __x:   [u64; 29usize],
        pub __fp:   u64,
        pub __lr:   u64,
        pub __sp:   u64,
        pub __pc:   u64,
        pub __cpsr: u32,
        pub __pad:  u32,
    }
    pub type arm_thread_state64          = arm_thread_state64_t;
    pub type __darwin_arm_thread_state64 = arm_thread_state64_t;

    impl arm_thread_state64_t {
        pub const fn new() -> Self {
            Self {
                __x:   [0; 29],
                __fp:   0,
                __lr:   0,
                __sp:   0,
                __pc:   0,
                __cpsr: 0,
                __pad:  0,
            }
        }

        pub const fn count() -> mach_msg_type_number_t {
            let n = size_of::<Self>() / size_of::<u64>();
            n as mach_msg_type_number_t
        }
    }
}

pub mod x86 {
    use super::{size_of, mach_msg_type_number_t};

    #[repr(C)]
    #[derive(Copy, Clone, Debug, Default, Hash, PartialOrd, PartialEq, Eq, Ord)]
    pub struct x86_thread_state64_t {
        pub __rax:    u64,
        pub __rbx:    u64,
        pub __rcx:    u64,
        pub __rdx:    u64,
        pub __rdi:    u64,
        pub __rsi:    u64,
        pub __rbp:    u64,
        pub __rsp:    u64,
        pub __r8:     u64,
        pub __r9:     u64,
        pub __r10:    u64,
        pub __r11:    u64,
        pub __r12:    u64,
        pub __r13:    u64,
        pub __r14:    u64,
        pub __r15:    u64,
        pub __rip:    u64,
        pub __rflags: u64,
        pub __cs:     u64,
        pub __fs:     u64,
        pub __gs:     u64,
    }

    impl x86_thread_state64_t {
        pub const fn new() -> Self {
            Self {
                __rax:    0,
                __rbx:    0,
                __rcx:    0,
                __rdx:    0,
                __rdi:    0,
                __rsi:    0,
                __rbp:    0,
                __rsp:    0,
                __r8:     0,
                __r9:     0,
                __r10:    0,
                __r11:    0,
                __r12:    0,
                __r13:    0,
                __r14:    0,
                __r15:    0,
                __rip:    0,
                __rflags: 0,
                __cs:     0,
                __fs:     0,
                __gs:     0,
            }
        }

        pub const fn count() -> mach_msg_type_number_t {
            let n = size_of::<Self>() / size_of::<u64>();
            n as mach_msg_type_number_t
        }
    }
}