|
4 | 4 | use core::{mem, pin::Pin};
|
5 | 5 |
|
6 | 6 | use pin_project::pin_project;
|
7 |
| -use static_assertions::const_assert; |
8 | 7 |
|
9 | 8 | use crate::{
|
10 | 9 | list::{List, ListEntry, ListNode},
|
@@ -56,6 +55,12 @@ unsafe impl ListNode for Run {
|
56 | 55 | /// # Safety
|
57 | 56 | ///
|
58 | 57 | /// The address of each `Run` in `runs` can become a `Page` by `Page::from_usize`.
|
| 58 | +// This implementation defers from xv6. Kmem of xv6 uses intrusive singly linked list, while this |
| 59 | +// Kmem uses List, which is a intrusive doubly linked list type of rv6. In a intrusive singly |
| 60 | +// linked list, it is impossible to automatically remove an entry from a list when it is dropped. |
| 61 | +// Therefore, it is nontrivial to make a general intrusive singly linked list type in a safe way. |
| 62 | +// For this reason, we use a doubly linked list instead. It adds runtime overhead, but the overhead |
| 63 | +// seems negligible. |
59 | 64 | #[pin_project]
|
60 | 65 | pub struct Kmem {
|
61 | 66 | #[pin]
|
@@ -100,11 +105,7 @@ impl Kmem {
|
100 | 105 | // Fill with junk to catch dangling refs.
|
101 | 106 | page.write_bytes(1);
|
102 | 107 |
|
103 |
| - const_assert!(mem::size_of::<Run>() <= PGSIZE); |
104 |
| - const_assert!(PGSIZE % mem::align_of::<Run>() == 0); |
105 |
| - |
106 |
| - // SAFETY: the above `const_assert`s. |
107 |
| - let run = unsafe { page.as_uninit_mut() }; |
| 108 | + let run = page.as_uninit_mut(); |
108 | 109 | // SAFETY: `run` will be initialized by the following `init`.
|
109 | 110 | let run = run.write(unsafe { Run::new() });
|
110 | 111 | let mut run = unsafe { Pin::new_unchecked(run) };
|
|
0 commit comments