Skip to content

Commit a5164b0

Browse files
hoshinolinaherrnst
authored andcommitted
drm/asahi: pgtable: Add helpers for decoding PTE perms
Signed-off-by: Asahi Lina <[email protected]>
1 parent 06a3769 commit a5164b0

1 file changed

Lines changed: 74 additions & 7 deletions

File tree

drivers/gpu/drm/asahi/pgtable.rs

Lines changed: 74 additions & 7 deletions
Original file line numberDiff line numberDiff line change
@@ -23,6 +23,11 @@ use kernel::{
2323
#[cfg(CONFIG_DEV_COREDUMP)]
2424
use kernel::{
2525
types::Owned,
26+
uapi::{
27+
PF_R,
28+
PF_W,
29+
PF_X, //
30+
},
2631
};
2732

2833
use crate::debug::*;
@@ -64,8 +69,8 @@ const PTE_TYPE_LEAF_TABLE: u64 = 3;
6469
const UAT_NON_GLOBAL: u64 = 1 << 11;
6570
const UAT_AP_SHIFT: u32 = 6;
6671
const UAT_AP_BITS: u64 = 3 << UAT_AP_SHIFT;
67-
const UAT_HIGH_BITS_SHIFT: u32 = 53;
68-
const UAT_HIGH_BITS: u64 = 7 << UAT_HIGH_BITS_SHIFT;
72+
const UAT_HIGH_BITS_SHIFT: u32 = 52;
73+
const UAT_HIGH_BITS: u64 = 0xfff << UAT_HIGH_BITS_SHIFT;
6974
const UAT_MEMATTR_SHIFT: u32 = 2;
7075
const UAT_MEMATTR_BITS: u64 = 7 << UAT_MEMATTR_SHIFT;
7176

@@ -81,15 +86,18 @@ const AP_FW_GPU: u8 = 0;
8186
const AP_FW: u8 = 1;
8287
const AP_GPU: u8 = 2;
8388

84-
const HIGH_BITS_PXN: u8 = 1 << 0;
85-
const HIGH_BITS_UXN: u8 = 1 << 1;
86-
const HIGH_BITS_GPU_ACCESS: u8 = 1 << 2;
89+
const HIGH_BITS_PXN: u16 = 1 << 1;
90+
const HIGH_BITS_UXN: u16 = 1 << 2;
91+
const HIGH_BITS_GPU_ACCESS: u16 = 1 << 3;
92+
93+
#[cfg(CONFIG_DEV_COREDUMP)]
94+
pub(crate) const PTE_ADDR_BITS: u64 = (!UAT_PGMSK as u64) & (!UAT_HIGH_BITS);
8795

8896
#[derive(Debug, Copy, Clone)]
8997
pub(crate) struct Prot {
9098
memattr: u8,
9199
ap: u8,
92-
high_bits: u8,
100+
high_bits: u16,
93101
}
94102

95103
// Firmware + GPU access
@@ -110,6 +118,27 @@ const PROT_GPU_WO: Prot = Prot::from_bits(AP_GPU, 0, 1);
110118
const PROT_GPU_RW: Prot = Prot::from_bits(AP_GPU, 1, 0);
111119
const _PROT_GPU_NA: Prot = Prot::from_bits(AP_GPU, 1, 1);
112120

121+
#[cfg(CONFIG_DEV_COREDUMP)]
122+
const PF_RW: u32 = PF_R | PF_W;
123+
#[cfg(CONFIG_DEV_COREDUMP)]
124+
const PF_RX: u32 = PF_R | PF_X;
125+
126+
// For crash dumps
127+
#[cfg(CONFIG_DEV_COREDUMP)]
128+
const PROT_TO_PERMS_FW: [[u32; 4]; 4] = [
129+
[0, 0, 0, PF_RW],
130+
[0, PF_RW, 0, PF_RW],
131+
[PF_RX, PF_RX, 0, PF_R],
132+
[PF_RX, PF_RW, 0, PF_R],
133+
];
134+
#[cfg(CONFIG_DEV_COREDUMP)]
135+
const PROT_TO_PERMS_OS: [[u32; 4]; 4] = [
136+
[0, PF_R, PF_W, PF_RW],
137+
[PF_R, 0, PF_RW, PF_RW],
138+
[0, 0, 0, 0],
139+
[0, 0, 0, 0],
140+
];
141+
113142
pub(crate) mod prot {
114143
pub(crate) use super::Prot;
115144
use super::*;
@@ -139,7 +168,7 @@ pub(crate) mod prot {
139168
}
140169

141170
impl Prot {
142-
const fn from_bits(ap: u8, uxn: u8, pxn: u8) -> Self {
171+
const fn from_bits(ap: u8, uxn: u16, pxn: u16) -> Self {
143172
assert!(uxn <= 1);
144173
assert!(pxn <= 1);
145174
assert!(ap <= 3);
@@ -151,6 +180,44 @@ impl Prot {
151180
}
152181
}
153182

183+
#[cfg(CONFIG_DEV_COREDUMP)]
184+
pub(crate) const fn from_pte(pte: u64) -> Self {
185+
Prot {
186+
high_bits: (pte >> UAT_HIGH_BITS_SHIFT) as u16,
187+
ap: ((pte & UAT_AP_BITS) >> UAT_AP_SHIFT) as u8,
188+
memattr: ((pte & UAT_MEMATTR_BITS) >> UAT_MEMATTR_SHIFT) as u8,
189+
}
190+
}
191+
192+
#[cfg(CONFIG_DEV_COREDUMP)]
193+
pub(crate) const fn elf_flags(&self) -> u32 {
194+
let ap = (self.ap & 3) as usize;
195+
let uxn = if self.high_bits & HIGH_BITS_UXN != 0 {
196+
1
197+
} else {
198+
0
199+
};
200+
let pxn = if self.high_bits & HIGH_BITS_PXN != 0 {
201+
1
202+
} else {
203+
0
204+
};
205+
let gpu = self.high_bits & HIGH_BITS_GPU_ACCESS != 0;
206+
207+
// Format:
208+
// [12 top bits of PTE] [12 bottom bits of PTE] [5 bits pad] [ELF RWX]
209+
let mut perms = if gpu {
210+
PROT_TO_PERMS_OS[ap][(uxn << 1) | pxn]
211+
} else {
212+
PROT_TO_PERMS_FW[ap][(uxn << 1) | pxn]
213+
};
214+
215+
perms |= ((self.as_pte() >> 52) << 20) as u32;
216+
perms |= ((self.as_pte() & 0xfff) << 8) as u32;
217+
218+
perms
219+
}
220+
154221
const fn memattr(&self, memattr: u8) -> Self {
155222
Self { memattr, ..*self }
156223
}

0 commit comments

Comments
 (0)