Line data Source code
1 : use lief_ffi as ffi;
2 :
3 : use crate::common::FromFFI;
4 : use crate::dwarf::editor::types::EditorType;
5 :
6 : /// This structure represents a struct-like type which can be:
7 : ///
8 : /// - `DW_TAG_class_type`
9 : /// - `DW_TAG_structure_type`
10 : /// - `DW_TAG_union_type`
11 : pub struct Struct {
12 : ptr: cxx::UniquePtr<ffi::DWARF_editor_StructType>,
13 : }
14 :
15 : impl FromFFI<ffi::DWARF_editor_StructType> for Struct {
16 0 : fn from_ffi(cmd: cxx::UniquePtr<ffi::DWARF_editor_StructType>) -> Self {
17 0 : Self { ptr: cmd }
18 0 : }
19 : }
20 :
21 : #[allow(non_camel_case_types)]
22 0 : #[derive(Debug, Copy, Clone, PartialEq, Eq, Hash)]
23 : pub enum Kind {
24 : CLASS,
25 : STRUCT,
26 : UNION,
27 : UNKNOWN(u32),
28 : }
29 :
30 : impl From<u32> for Kind {
31 0 : fn from(value: u32) -> Self {
32 0 : match value {
33 0 : 0x00000000 => Kind::CLASS,
34 0 : 0x00000001 => Kind::STRUCT,
35 0 : 0x00000002 => Kind::UNION,
36 0 : _ => Kind::UNKNOWN(value),
37 : }
38 0 : }
39 : }
40 :
41 : impl From<Kind> for u32 {
42 0 : fn from(value: Kind) -> Self {
43 0 : match value {
44 0 : Kind::CLASS => 0,
45 0 : Kind::STRUCT => 1,
46 0 : Kind::UNION => 2,
47 0 : Kind::UNKNOWN(value) => value,
48 : }
49 0 : }
50 : }
51 :
52 : impl Struct {
53 : /// Define the overall size which is equivalent to the `sizeof` of the current
54 : /// type.
55 : ///
56 : /// This function defines the `DW_AT_byte_size` attribute
57 0 : pub fn set_size(&mut self, size: u64) {
58 0 : self.ptr.pin_mut().set_size(size);
59 0 : }
60 :
61 : /// Add a member to the current struct-like
62 0 : pub fn add_member(&mut self, name: &str, ty: &mut dyn EditorType) -> Member {
63 0 : Member::from_ffi(self.ptr.pin_mut().add_member(name, ty.get_base()))
64 0 : }
65 :
66 : /// Add a member to the current struct-like at the specified offset
67 0 : pub fn add_member_at_offset(
68 0 : &mut self,
69 0 : name: &str,
70 0 : ty: &mut dyn EditorType,
71 0 : offset: u64,
72 0 : ) -> Member {
73 0 : Member::from_ffi(
74 0 : self.ptr
75 0 : .pin_mut()
76 0 : .add_member_with_offset(name, ty.get_base(), offset),
77 0 : )
78 0 : }
79 :
80 : /// Add a bitfield to the current struct-like
81 0 : pub fn add_bitfield(&mut self, name: &str, ty: &mut dyn EditorType, bitsize: u64) -> Member {
82 0 : Member::from_ffi(
83 0 : self.ptr
84 0 : .pin_mut()
85 0 : .add_bitfield(name, ty.get_base(), bitsize),
86 0 : )
87 0 : }
88 :
89 : /// Add a bitfield to the current struct-like at the specified offset
90 0 : pub fn add_bitfield_at_offset(
91 0 : &mut self,
92 0 : name: &str,
93 0 : ty: &mut dyn EditorType,
94 0 : bitsize: u64,
95 0 : bitoffset: u64,
96 0 : ) -> Member {
97 0 : Member::from_ffi(self.ptr.pin_mut().add_bitfield_with_offset(
98 0 : name,
99 0 : ty.get_base(),
100 0 : bitsize,
101 0 : bitoffset,
102 0 : ))
103 0 : }
104 : }
105 :
106 : impl EditorType for Struct {
107 0 : fn get_base(&self) -> &ffi::DWARF_editor_Type {
108 0 : self.ptr.as_ref().unwrap().as_ref()
109 0 : }
110 : }
111 :
112 : #[allow(dead_code)]
113 : pub struct Member {
114 : ptr: cxx::UniquePtr<ffi::DWARF_editor_StructType_Member>,
115 : }
116 :
117 : impl FromFFI<ffi::DWARF_editor_StructType_Member> for Member {
118 0 : fn from_ffi(cmd: cxx::UniquePtr<ffi::DWARF_editor_StructType_Member>) -> Self {
119 0 : Self { ptr: cmd }
120 0 : }
121 : }
|