iPXE
Macros | Functions
initrd.h File Reference

Initial ramdisk (initrd) reshuffling. More...

#include <stdint.h>
#include <ipxe/memmap.h>

Go to the source code of this file.

Macros

#define INITRD_ALIGN   4096
 Initial ramdisk chunk alignment. More...
 

Functions

 FILE_LICENCE (GPL2_OR_LATER_OR_UBDL)
 
void initrd_reshuffle (void)
 Reshuffle initrds into desired order at top of memory. More...
 
int initrd_region (size_t len, struct memmap_region *region)
 Calculate post-reshuffle initrd load region. More...
 
size_t initrd_load_all (void *address)
 Load all initrds. More...
 
static size_t initrd_align (size_t len)
 Align initrd length. More...
 
static size_t initrd_len (void)
 Get required length for initrds. More...
 

Detailed Description

Initial ramdisk (initrd) reshuffling.

Definition in file initrd.h.

Macro Definition Documentation

◆ INITRD_ALIGN

#define INITRD_ALIGN   4096

Initial ramdisk chunk alignment.

Definition at line 16 of file initrd.h.

Function Documentation

◆ FILE_LICENCE()

FILE_LICENCE ( GPL2_OR_LATER_OR_UBDL  )

◆ initrd_reshuffle()

void initrd_reshuffle ( void  )

Reshuffle initrds into desired order at top of memory.

After this function returns, the initrds have been rearranged in memory and the external heap structures will have been corrupted. Reshuffling must therefore take place immediately prior to jumping to the loaded OS kernel; no further execution within iPXE is permitted.

Definition at line 229 of file initrd.c.

229  {
231  physaddr_t end;
232 
233  /* Calculate limits of reshuffle region */
234  start = uheap_limit;
236 
237  /* Debug */
238  initrd_dump();
239 
240  /* Squash initrds as high as possible in memory */
242 
243  /* Bubble-sort initrds into desired order */
244  while ( initrd_swap_any ( start, end ) ) {}
245 
246  /* Debug */
247  initrd_dump();
248 }
static physaddr_t initrd_end
End of reshuffle region.
Definition: initrd.c:42
uint32_t start
Starting offset.
Definition: netvsc.h:12
static void initrd_dump(void)
Dump initrd locations (for debug)
Definition: initrd.c:203
static void initrd_squash_high(physaddr_t start, physaddr_t end)
Squash initrds as high as possible in memory.
Definition: initrd.c:50
unsigned long physaddr_t
Definition: stdint.h:20
physaddr_t uheap_limit
Minimum possible start of external heap.
Definition: uheap.c:54
uint32_t end
Ending offset.
Definition: netvsc.h:18
static int initrd_swap_any(physaddr_t start, physaddr_t end)
Swap position of any two adjacent initrds not currently in the correct order.
Definition: initrd.c:155
physaddr_t uheap_end
End of external heap.
Definition: uheap.c:60

References end, initrd_dump(), initrd_end, initrd_squash_high(), initrd_swap_any(), start, uheap_end, and uheap_limit.

Referenced by bzimage_load_initrds(), and lkrn_exec().

◆ initrd_region()

int initrd_region ( size_t  len,
struct memmap_region region 
)

Calculate post-reshuffle initrd load region.

Parameters
lenLength of initrds (from initrd_len())
regionRegion descriptor to fill in
Return values
rcReturn status code

If successful, then any suitably aligned range within the region may be used as the load address after reshuffling. The caller does not need to call prep_segment() for a range in this region. (Calling prep_segment() would probably fail, since prior to reshuffling the region is still in use by the external heap.)

Definition at line 354 of file initrd.c.

354  {
355  physaddr_t min;
356  size_t available;
357 
358  /* Calculate limits of available space for initrds */
359  min = uheap_limit;
360  available = ( ( initrd_end ? initrd_end : uheap_end ) - min );
361  if ( available < len )
362  return -ENOSPC;
363  DBGC ( &images, "INITRD post-reshuffle region is [%#08lx,%#08lx)\n",
364  min, ( min + available ) );
365 
366  /* Populate region descriptor */
367  region->min = min;
368  region->max = ( min + available - 1 );
369  region->flags = MEMMAP_FL_MEMORY;
370  region->name = "initrd";
371 
372  return 0;
373 }
uint64_t max
Maximum address in region.
Definition: memmap.h:52
#define DBGC(...)
Definition: compiler.h:505
#define min(x, y)
Definition: ath.h:35
static physaddr_t initrd_end
End of reshuffle region.
Definition: initrd.c:42
ring len
Length.
Definition: dwmac.h:231
unsigned int flags
Region flags.
Definition: memmap.h:54
struct list_head images
List of registered images.
Definition: image.c:58
const char * name
Region name (for debug messages)
Definition: memmap.h:56
unsigned long physaddr_t
Definition: stdint.h:20
#define ENOSPC
No space left on device.
Definition: errno.h:549
physaddr_t uheap_limit
Minimum possible start of external heap.
Definition: uheap.c:54
#define MEMMAP_FL_MEMORY
Contains memory.
Definition: memmap.h:59
uint64_t min
Minimum address in region.
Definition: memmap.h:50
physaddr_t uheap_end
End of external heap.
Definition: uheap.c:60

References DBGC, ENOSPC, memmap_region::flags, images, initrd_end, len, memmap_region::max, MEMMAP_FL_MEMORY, min, memmap_region::min, memmap_region::name, uheap_end, and uheap_limit.

Referenced by bzimage_check_initrds(), and lkrn_exec().

◆ initrd_load_all()

size_t initrd_load_all ( void *  address)

Load all initrds.

Parameters
addressLoad address, or NULL
Return values
lenLength

This function is called after the point of no return, when the external heap has been corrupted by reshuffling and there is no way to resume normal execution. The caller must have previously ensured that there is no way for installation to this address to fail.

Definition at line 317 of file initrd.c.

317  {
318  struct image *initrd;
319  size_t len = 0;
320  size_t pad_len;
321  void *dest;
322 
323  /* Load all initrds */
324  for_each_image ( initrd ) {
325 
326  /* Zero-pad to next INITRD_ALIGN boundary */
327  pad_len = ( ( -len ) & ( INITRD_ALIGN - 1 ) );
328  if ( address )
329  memset ( ( address + len ), 0, pad_len );
330  len += pad_len;
331  assert ( len == initrd_align ( len ) );
332 
333  /* Load initrd */
334  dest = ( address ? ( address + len ) : NULL );
335  len += initrd_load ( initrd, dest );
336  }
337 
338  return len;
339 }
uint64_t address
Base address.
Definition: ena.h:24
static size_t initrd_load(struct image *initrd, void *address)
Load initrd.
Definition: initrd.c:257
An executable image.
Definition: image.h:23
static size_t initrd_align(size_t len)
Align initrd length.
Definition: initrd.h:29
#define INITRD_ALIGN
Initial ramdisk chunk alignment.
Definition: initrd.h:16
assert((readw(&hdr->flags) &(GTF_reading|GTF_writing))==0)
ring len
Length.
Definition: dwmac.h:231
#define for_each_image(image)
Iterate over all registered images.
Definition: image.h:190
long pad_len
Definition: bigint.h:30
if(len >=6 *4) __asm__ __volatile__("movsl" if(len >=5 *4) __asm__ __volatile__("movsl" if(len >=4 *4) __asm__ __volatile__("movsl" if(len >=3 *4) __asm__ __volatile__("movsl" if(len >=2 *4) __asm__ __volatile__("movsl" if(len >=1 *4) __asm__ __volatile__("movsl" if((len % 4) >=2) __asm__ __volatile__("movsw" if((len % 2) >=1) __asm__ __volatile__("movsb" return dest
Definition: string.h:150
#define NULL
NULL pointer (VOID *)
Definition: Base.h:321
void * memset(void *dest, int character, size_t len) __nonnull

References address, assert(), dest, for_each_image, INITRD_ALIGN, initrd_align(), initrd_load(), len, memset(), NULL, and pad_len.

Referenced by bzimage_load_initrds(), initrd_len(), and lkrn_exec().

◆ initrd_align()

static size_t initrd_align ( size_t  len)
inlinestatic

Align initrd length.

Parameters
lenLength
Return values
lenAligned length

Definition at line 29 of file initrd.h.

29  {
30 
31  return ( ( len + INITRD_ALIGN - 1 ) & ~( INITRD_ALIGN - 1 ) );
32 }
#define INITRD_ALIGN
Initial ramdisk chunk alignment.
Definition: initrd.h:16
ring len
Length.
Definition: dwmac.h:231

References INITRD_ALIGN, and len.

Referenced by initrd_load_all(), initrd_squash_high(), initrd_swap(), initrd_swap_any(), and lkrn_exec().

◆ initrd_len()

static size_t initrd_len ( void  )
inlinestatic

Get required length for initrds.

Return values
lenRequired length

Definition at line 40 of file initrd.h.

40  {
41 
42  return initrd_load_all ( NULL );
43 }
size_t initrd_load_all(void *address)
Load all initrds.
Definition: initrd.c:317
#define NULL
NULL pointer (VOID *)
Definition: Base.h:321

References initrd_load_all(), and NULL.