Skip to content

Commit 1fa5598

Browse files
committed
Add errors::SelectorError
This interprets the values of the selector error during #GP. Signed-off-by: Nathaniel McCallum <[email protected]>
1 parent d4023b7 commit 1fa5598

File tree

1 file changed

+70
-0
lines changed

1 file changed

+70
-0
lines changed

src/errors.rs

Lines changed: 70 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -1,5 +1,7 @@
11
//! This module contains errors and exception types.
22
3+
use bit_field::BitField;
4+
35
/// Exception Error Codes
46
///
57
/// This structure is defined by the following manual sections:
@@ -78,3 +80,71 @@ pub enum Exception {
7880
/// Security Exception
7981
Security = 0x1E,
8082
}
83+
84+
/// The index in a selector error
85+
#[derive(Copy, Clone, Debug, PartialEq, Eq)]
86+
pub enum SelectorIndex {
87+
/// An IDT selector
88+
Idt(u16),
89+
90+
/// A GDT selector
91+
Gdt(u16),
92+
93+
/// An LDT selector
94+
Ldt(u16),
95+
}
96+
97+
/// A selector error
98+
///
99+
/// This structure is defined by the following manual sections:
100+
/// * AMD Volume 2: 8.4.1
101+
/// * Intel Volume 3A: 6.13
102+
#[derive(Copy, Clone, Debug)]
103+
#[repr(transparent)]
104+
pub struct SelectorError(u32);
105+
106+
impl SelectorError {
107+
/// Whether or not the fault was external to the CPU.
108+
#[inline]
109+
pub fn external(self) -> bool {
110+
self.0.get_bit(0)
111+
}
112+
113+
/// Returns the selector index.
114+
#[inline]
115+
pub fn index(self) -> SelectorIndex {
116+
let index = self.0.get_bits(3..16) as u16;
117+
118+
if self.0.get_bit(1) {
119+
SelectorIndex::Idt(index)
120+
} else if self.0.get_bit(2) {
121+
SelectorIndex::Ldt(index)
122+
} else {
123+
SelectorIndex::Gdt(index)
124+
}
125+
}
126+
}
127+
128+
#[cfg(test)]
129+
mod test {
130+
use super::*;
131+
132+
#[test]
133+
fn selector() {
134+
let se = SelectorError(0b0101010101010101_0101010101010101);
135+
assert_eq!(se.external(), true);
136+
assert_eq!(se.index(), SelectorIndex::Ldt(0b0101010101010));
137+
138+
let se = SelectorError(0b0101010101010101_0101010101010111);
139+
assert_eq!(se.external(), true);
140+
assert_eq!(se.index(), SelectorIndex::Idt(0b0101010101010));
141+
142+
let se = SelectorError(0b0101010101010101_0101010101010011);
143+
assert_eq!(se.external(), true);
144+
assert_eq!(se.index(), SelectorIndex::Idt(0b0101010101010));
145+
146+
let se = SelectorError(0b0101010101010101_0101010101010001);
147+
assert_eq!(se.external(), true);
148+
assert_eq!(se.index(), SelectorIndex::Gdt(0b0101010101010));
149+
}
150+
}

0 commit comments

Comments
 (0)