Skip to content

Commit cbc47ab

Browse files
committed
multiboot2: Support setting the image load address
1 parent ed316cb commit cbc47ab

File tree

3 files changed

+60
-3
lines changed

3 files changed

+60
-3
lines changed

multiboot2/src/builder/information.rs

+14-2
Original file line numberDiff line numberDiff line change
@@ -3,8 +3,8 @@ use crate::builder::traits::StructAsBytes;
33
use crate::{
44
BasicMemoryInfoTag, BootInformationInner, BootLoaderNameTag, CommandLineTag,
55
EFIBootServicesNotExited, EFIImageHandle32, EFIImageHandle64, EFIMemoryMapTag, EFISdt32,
6-
EFISdt64, ElfSectionsTag, EndTag, FramebufferTag, MemoryMapTag, ModuleTag, RsdpV1Tag,
7-
RsdpV2Tag, SmbiosTag,
6+
EFISdt64, ElfSectionsTag, EndTag, FramebufferTag, ImageLoadPhysAddr, MemoryMapTag, ModuleTag,
7+
RsdpV1Tag, RsdpV2Tag, SmbiosTag,
88
};
99

1010
use alloc::boxed::Box;
@@ -25,6 +25,7 @@ pub struct Multiboot2InformationBuilder {
2525
efi_memory_map_tag: Option<Box<EFIMemoryMapTag>>,
2626
elf_sections_tag: Option<Box<ElfSectionsTag>>,
2727
framebuffer_tag: Option<Box<FramebufferTag>>,
28+
image_load_addr: Option<ImageLoadPhysAddr>,
2829
memory_map_tag: Option<Box<MemoryMapTag>>,
2930
module_tags: Vec<Box<ModuleTag>>,
3031
efisdt32: Option<EFISdt32>,
@@ -48,6 +49,7 @@ impl Multiboot2InformationBuilder {
4849
efi_memory_map_tag: None,
4950
elf_sections_tag: None,
5051
framebuffer_tag: None,
52+
image_load_addr: None,
5153
memory_map_tag: None,
5254
module_tags: Vec::new(),
5355
rsdp_v1_tag: None,
@@ -110,6 +112,9 @@ impl Multiboot2InformationBuilder {
110112
if let Some(tag) = &self.framebuffer_tag {
111113
len += Self::size_or_up_aligned(tag.byte_size())
112114
}
115+
if let Some(tag) = &self.image_load_addr {
116+
len += Self::size_or_up_aligned(tag.byte_size())
117+
}
113118
if let Some(tag) = &self.memory_map_tag {
114119
len += Self::size_or_up_aligned(tag.byte_size())
115120
}
@@ -188,6 +193,9 @@ impl Multiboot2InformationBuilder {
188193
if let Some(tag) = self.framebuffer_tag.as_ref() {
189194
Self::build_add_bytes(&mut data, &tag.struct_as_bytes(), false)
190195
}
196+
if let Some(tag) = self.image_load_addr.as_ref() {
197+
Self::build_add_bytes(&mut data, &tag.struct_as_bytes(), false)
198+
}
191199
if let Some(tag) = self.memory_map_tag.as_ref() {
192200
Self::build_add_bytes(&mut data, &tag.struct_as_bytes(), false)
193201
}
@@ -253,6 +261,10 @@ impl Multiboot2InformationBuilder {
253261
self.framebuffer_tag = Some(framebuffer_tag);
254262
}
255263

264+
pub fn image_load_addr(&mut self, image_load_addr: ImageLoadPhysAddr) {
265+
self.image_load_addr = Some(image_load_addr);
266+
}
267+
256268
pub fn memory_map_tag(&mut self, memory_map_tag: Box<MemoryMapTag>) {
257269
self.memory_map_tag = Some(memory_map_tag);
258270
}

multiboot2/src/image_load_addr.rs

+35-1
Original file line numberDiff line numberDiff line change
@@ -1,4 +1,9 @@
1-
use crate::TagTypeId;
1+
use core::convert::TryInto;
2+
use core::mem::size_of;
3+
4+
#[cfg(feature = "builder")]
5+
use crate::builder::traits::StructAsBytes;
6+
use crate::tag_type::{TagType, TagTypeId};
27

38
/// If the image has relocatable header tag, this tag contains the image's
49
/// base physical address.
@@ -11,8 +16,37 @@ pub struct ImageLoadPhysAddr {
1116
}
1217

1318
impl ImageLoadPhysAddr {
19+
#[cfg(feature = "builder")]
20+
pub fn new(load_base_addr: u32) -> Self {
21+
Self {
22+
typ: TagType::LoadBaseAddr.into(),
23+
size: size_of::<Self>().try_into().unwrap(),
24+
load_base_addr,
25+
}
26+
}
27+
1428
/// Returns the load base address.
1529
pub fn load_base_addr(&self) -> u32 {
1630
self.load_base_addr
1731
}
1832
}
33+
34+
#[cfg(feature = "builder")]
35+
impl StructAsBytes for ImageLoadPhysAddr {
36+
fn byte_size(&self) -> usize {
37+
size_of::<Self>()
38+
}
39+
}
40+
41+
#[cfg(test)]
42+
mod tests {
43+
use super::ImageLoadPhysAddr;
44+
45+
const ADDR: u32 = 0xABCDEF;
46+
47+
#[test]
48+
fn test_build_load_addr() {
49+
let tag = ImageLoadPhysAddr::new(ADDR);
50+
assert_eq!(tag.load_base_addr(), ADDR);
51+
}
52+
}

multiboot2/src/module.rs

+11
Original file line numberDiff line numberDiff line change
@@ -159,4 +159,15 @@ mod tests {
159159
assert_eq!({ tag.typ }, TagType::Module);
160160
assert_eq!(tag.cmdline().expect("must be valid UTF-8"), MSG);
161161
}
162+
163+
/// Test to generate a tag from a given string.
164+
#[test]
165+
#[cfg(feature = "builder")]
166+
fn test_build_str() {
167+
use crate::builder::traits::StructAsBytes;
168+
169+
let tag = ModuleTag::new(0, 0, MSG);
170+
let bytes = tag.struct_as_bytes();
171+
assert_eq!(bytes, get_bytes());
172+
}
162173
}

0 commit comments

Comments
 (0)