Skip to content

Commit c518b6e

Browse files
committed
acpi_tables/srat: Add RintcAffinity structure
An ECR to add a new structure type to the SRAT for RISC-V harts has been approved, which this patch adds support for. See https://docs.google.com/document/d/12xlo-1jIPShyjMfmBAfRKccmIACXWyEuJB41_NnBxjI/edit Signed-off-by: Tim Wawrzynczak <[email protected]>
1 parent 514c5a7 commit c518b6e

File tree

1 file changed

+63
-2
lines changed

1 file changed

+63
-2
lines changed

src/srat.rs

Lines changed: 63 additions & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -3,12 +3,15 @@
33
// SPDX-License-Identifier: Apache-2.0
44
//
55

6-
use zerocopy::AsBytes;
6+
use zerocopy::{byteorder, byteorder::LE, AsBytes};
77

88
extern crate alloc;
99
use alloc::{boxed::Box, vec::Vec};
1010

11-
use crate::{u8sum, Aml, AmlSink, Checksum, TableHeader};
11+
use crate::{aml_as_bytes, u8sum, Aml, AmlSink, Checksum, TableHeader};
12+
13+
type U16 = byteorder::U16<LE>;
14+
type U32 = byteorder::U32<LE>;
1215

1316
// SRAT is the place where proximity domains are defined, and _PXM
1417
// (found in DSDT and/or SSDT) provides a mechanism to associate a
@@ -69,6 +72,11 @@ impl SRAT {
6972
self.update_header(GenericInitiator::len() as u32, st.u8sum());
7073
self.structures.push(Box::new(st));
7174
}
75+
76+
pub fn add_rintc_affinity(&mut self, ra: RintcAffinity) {
77+
self.update_header(RintcAffinity::len() as u32, ra.u8sum());
78+
self.structures.push(Box::new(ra));
79+
}
7280
}
7381

7482
impl Aml for SRAT {
@@ -90,6 +98,7 @@ impl Aml for SRAT {
9098
enum SratStructureType {
9199
MemoryAffinity = 1,
92100
GenericInitiator = 5,
101+
RintcAffinity = 7,
93102
}
94103

95104
#[repr(u32)]
@@ -280,6 +289,47 @@ impl Aml for GenericInitiator {
280289
}
281290
}
282291

292+
#[repr(C, packed)]
293+
#[derive(Clone, Copy, Debug, Default, AsBytes)]
294+
pub struct RintcAffinity {
295+
r#type: u8,
296+
length: u8,
297+
reserved: U16,
298+
acpi_processor_uid: [u8; 4],
299+
flags: U32,
300+
clock_domain: U32,
301+
}
302+
303+
impl RintcAffinity {
304+
const FLAGS_ENABLED: u32 = 1 << 0;
305+
306+
fn len() -> usize {
307+
core::mem::size_of::<Self>()
308+
}
309+
310+
pub fn new(acpi_processor_uid: [u8; 4], clock_domain: u32) -> Self {
311+
Self {
312+
r#type: SratStructureType::RintcAffinity as u8,
313+
length: 20,
314+
reserved: 0.into(),
315+
acpi_processor_uid,
316+
flags: 0.into(),
317+
clock_domain: clock_domain.into(),
318+
}
319+
}
320+
321+
pub fn enabled(mut self) -> Self {
322+
self.flags = (self.flags.get() | Self::FLAGS_ENABLED).into();
323+
self
324+
}
325+
326+
fn u8sum(&self) -> u8 {
327+
u8sum(self)
328+
}
329+
}
330+
331+
aml_as_bytes!(RintcAffinity);
332+
283333
#[cfg(test)]
284334
mod tests {
285335
use super::*;
@@ -344,4 +394,15 @@ mod tests {
344394
let sum = bytes.iter().fold(0u8, |acc, x| acc.wrapping_add(*x));
345395
assert_eq!(sum, 0);
346396
}
397+
398+
#[test]
399+
fn test_rintc_affinity() {
400+
let mut srat = SRAT::new(*b"FOOBAR", *b"SRATSRAT", 0xdead_beef);
401+
srat.add_rintc_affinity(RintcAffinity::new([0x42, 0x37, 0x58, 0xde], 0xde583742).enabled());
402+
403+
let mut bytes = Vec::new();
404+
srat.to_aml_bytes(&mut bytes);
405+
let sum = bytes.iter().fold(0u8, |acc, x| acc.wrapping_add(*x));
406+
assert_eq!(sum, 0);
407+
}
347408
}

0 commit comments

Comments
 (0)