* Correctly put cpus and memories for adoption

* Test on x86_64 (works)
This commit is contained in:
R Aadarsh
2026-06-15 09:32:15 +05:30
parent 16c59588b0
commit 9ecc75029c
4 changed files with 25 additions and 18 deletions
+1 -4
View File
@@ -27,15 +27,12 @@ impl Slit {
for i in 0..ndom {
for j in i..ndom {
// ignore distances from a domain to itself, since it is always 10
if i != j {
unsafe {
numa::set_distance(i, j, unsafe { *address.add((i + ndom * j) as usize) });
numa::set_distance(j, i, unsafe { *address.add((i + ndom * j) as usize) });
}
} else {
unsafe {
numa::set_distance(i, j, 10);
}
}
}
}
+4 -2
View File
@@ -76,7 +76,7 @@ impl<'a> Iterator for SratIter<'a> {
assert!(entry_len as usize == size_of::<GiccAffinity>() + 2);
*(entry.add(2) as *const GiccAffinity)
}),
// ignore ITS Affinity and Generic Initiator Affinity
// ignore GIC ITS Affinity and Generic Initiator Affinity
4 | 5 => {
self.i += entry_len as u32;
continue;
@@ -96,7 +96,9 @@ pub enum SratEntry {
MemoryAffinity(MemoryAffinity),
ProcessorLocalAffinity(ProcessorLocalAffinity),
GiccAffinity(GiccAffinity),
Unknown(u8), // unimplemented: Generic Initiator Affinity; our current focus is only on memory and cpus
// unimplemented: Gic Its Affinity and Generic Initiator Affinity
// our current focus is only on memory and cpus
Unknown(u8),
}
#[repr(C, packed)]
-1
View File
@@ -61,5 +61,4 @@ pub fn init_srat(srat: &Srat) {
_ => continue,
}
}
println!("{:?}", NUMA_NODES.get().unwrap());
}
+20 -11
View File
@@ -39,6 +39,7 @@ pub struct NumaNode {
pub fn init() {
NUMA_NODES.call_once(|| HashMap::new());
let mut flag = false;
#[cfg(all(
feature = "acpi",
@@ -47,12 +48,14 @@ pub fn init() {
{
acpi::srat::init();
acpi::slit::init();
return;
flag = true;
}
#[cfg(any(target_arch = "riscv64", target_arch = "aarch64"))]
{
todo!()
if !flag {
todo!()
}
}
unsafe {
@@ -68,7 +71,6 @@ pub fn init() {
pub unsafe fn add_cpu(id: u32, node_id: u32) {
let numa_nodes = NUMA_NODES.get().unwrap();
/* 💀💀💀 HIGHLY UNSAFE 💀💀💀 */
let numa_nodes = unsafe { &mut *(&raw const *numa_nodes as *mut HashMap<u32, NumaNode>) };
if let Some(node) = numa_nodes.get_mut(&id) {
@@ -90,7 +92,6 @@ pub unsafe fn add_cpu(id: u32, node_id: u32) {
pub unsafe fn add_memory(node_id: u32, start: usize, length: usize) {
let numa_nodes = NUMA_NODES.get().unwrap();
/* 💀💀💀 HIGHLY UNSAFE 💀💀💀 */
let numa_nodes = unsafe { &mut *(&raw const *numa_nodes as *mut HashMap<u32, NumaNode>) };
if let Some(node) = numa_nodes.get_mut(&node_id) {
@@ -110,7 +111,6 @@ pub unsafe fn add_memory(node_id: u32, start: usize, length: usize) {
}
pub unsafe fn set_distance(src: u32, target: u32, distance: u8) {
/* 💀💀💀 HIGHLY UNSAFE 💀💀💀 */
let nodes =
unsafe { &mut *(&raw const *(NUMA_NODES.get().unwrap()) as *mut HashMap<u32, NumaNode>) };
@@ -119,7 +119,6 @@ pub unsafe fn set_distance(src: u32, target: u32, distance: u8) {
}
unsafe fn shrink() {
/* 💀💀💀 HIGHLY UNSAFE 💀💀💀 */
let nodes =
unsafe { &mut *(&raw const *(NUMA_NODES.get().unwrap()) as *mut HashMap<u32, NumaNode>) };
@@ -138,7 +137,6 @@ unsafe fn shrink() {
///
/// See the comment above the definition of `NumaNode`.
unsafe fn reorganise() {
/* 💀💀💀 HIGHLY UNSAFE 💀💀💀 */
let nodes =
unsafe { &mut *(&raw const *(NUMA_NODES.get().unwrap()) as *mut HashMap<u32, NumaNode>) };
let ids = nodes.keys().map(|e| *e).collect::<Vec<u32>>();
@@ -147,7 +145,10 @@ unsafe fn reorganise() {
let node = nodes.remove(&id).unwrap();
if node.cpus.len() == 0 {
put_for_adoption(nodes, node.distances, Some(node.memory), None);
assert!(node.memory.len() != 0);
put_for_adoption(nodes, node.distances, Some(node.memory), None, id);
} else if node.memory.len() == 0 {
put_for_adoption(nodes, node.distances, None, Some(node.cpus), id);
} else {
nodes.insert(id, node);
}
@@ -159,22 +160,30 @@ fn put_for_adoption(
distances: Vec<(u32, u8)>,
memories: Option<Vec<NumaMemory>>,
cpus: Option<Vec<NumaCpu>>,
orphan_node_id: u32,
) {
if let Some(memories) = memories {
assert!(cpus.is_none());
let (nearest_node_id, _) = distances.first().unwrap();
let (nearest_node_id, distance) = distances.first().unwrap();
let nearest_node = nodes.get_mut(nearest_node_id).unwrap();
nearest_node.memory.extend(memories);
} else if let Some(cpus) = cpus {
assert!(memories.is_none());
let (nearest_node_id, _) = distances.first().unwrap();
let (nearest_node_id, distance) = distances.first().unwrap();
let nearest_node = nodes.get_mut(nearest_node_id).unwrap();
nearest_node.cpus.extend(cpus);
} else {
panic!()
};
for (_, node) in nodes {
if let Some(idx) = node.distances.iter().position(|e| e.0 == orphan_node_id) {
let _ = node.distances.remove(idx);
}
}
}
unsafe fn sort_by_distances() {
/* 💀💀💀 HIGHLY UNSAFE 💀💀💀 */
let nodes =
unsafe { &mut *(&raw const *(NUMA_NODES.get().unwrap()) as *mut HashMap<u32, NumaNode>) };