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
pub mod entities;
pub mod formats;
pub mod immediates;
pub mod instructions;
pub mod legalize;
pub mod settings;
pub mod types;
use crate::cdsl::formats::{FormatStructure, InstructionFormat};
use crate::cdsl::instructions::{AllInstructions, InstructionGroup};
use crate::cdsl::settings::SettingGroup;
use crate::cdsl::xform::TransformGroups;
use crate::shared::entities::EntityRefs;
use crate::shared::formats::Formats;
use crate::shared::immediates::Immediates;
use std::collections::HashMap;
use std::iter::FromIterator;
use std::rc::Rc;
pub(crate) struct Definitions {
pub settings: SettingGroup,
pub all_instructions: AllInstructions,
pub instructions: InstructionGroup,
pub imm: Immediates,
pub formats: Formats,
pub transform_groups: TransformGroups,
pub entities: EntityRefs,
}
pub(crate) fn define() -> Definitions {
let mut all_instructions = AllInstructions::new();
let immediates = Immediates::new();
let entities = EntityRefs::new();
let formats = Formats::new(&immediates, &entities);
let instructions =
instructions::define(&mut all_instructions, &formats, &immediates, &entities);
let transform_groups = legalize::define(&instructions, &immediates);
Definitions {
settings: settings::define(),
all_instructions,
instructions,
imm: immediates,
formats,
transform_groups,
entities,
}
}
impl Definitions {
pub fn verify_instruction_formats(&self) -> Vec<&InstructionFormat> {
let mut format_names: HashMap<&'static str, &Rc<InstructionFormat>> = HashMap::new();
let mut format_structures: HashMap<FormatStructure, &InstructionFormat> = HashMap::new();
for inst in self.all_instructions.values() {
if let Some(existing_format) = format_names.get(&inst.format.name) {
assert!(
Rc::ptr_eq(&existing_format, &inst.format),
"formats must uniquely named; there's a\
conflict on the name '{}', please make sure it is used only once.",
existing_format.name
);
} else {
format_names.insert(inst.format.name, &inst.format);
}
let key = inst.format.structure();
if let Some(existing_format) = format_structures.get(&key) {
assert_eq!(
existing_format.name, inst.format.name,
"duplicate instruction formats {} and {}; please remove one.",
existing_format.name, inst.format.name
);
} else {
format_structures.insert(key, &inst.format);
}
}
let mut result = Vec::from_iter(format_structures.into_iter().map(|(_, v)| v));
result.sort_by_key(|format| format.name);
result
}
}