SMM: Add support for malloc in SMM if using TSEG

This is used by the SPI driver and ELOG.

It requires SMM TSEG and a _heap/_eheap region defined in the
linker script.  The first time malloc is called in SMM the
start and end pointers to the heap region will be relocated
for the TSEG region.

Enable SPI flash and ELOG in SMM and successfully
allocate memory.  The allocated addresses are verified
to be sure they are within the TSEG heap region:

smm.elf:00014000 B _eheap
smm.elf:00010000 B _heap
TSEG base is 0xad000000

Memory allocated in ELOG:
ELOG: MEM @0xad018030

Change-Id: I5cca38e4888d597cbbfcd9983cd6a7ae3600c2a3
Signed-off-by: Duncan Laurie <dlaurie@chromium.org>
Reviewed-on: http://review.coreboot.org/1312
Tested-by: build bot (Jenkins)
Reviewed-by: Ronald G. Minnich <rminnich@gmail.com>
This commit is contained in:
Duncan Laurie 2012-06-23 13:33:32 -07:00 committed by Ronald G. Minnich
parent 7d2b81c18d
commit f5e9ac48c6
3 changed files with 11 additions and 0 deletions

View File

@ -7,6 +7,7 @@ ramstage-y += die.c
smm-y += printk.c smm-y += printk.c
smm-y += vtxprintf.c smm-y += vtxprintf.c
smm-$(CONFIG_SMM_TSEG) += die.c
romstage-y += vtxprintf.c romstage-y += vtxprintf.c
romstage-$(CONFIG_CACHE_AS_RAM) += console.c romstage-$(CONFIG_CACHE_AS_RAM) += console.c

View File

@ -32,6 +32,7 @@ endif
ramstage-y += memcmp.c ramstage-y += memcmp.c
ramstage-y += memmove.c ramstage-y += memmove.c
ramstage-y += malloc.c ramstage-y += malloc.c
smm-$(CONFIG_SMM_TSEG) += malloc.c
ramstage-y += delay.c ramstage-y += delay.c
ramstage-y += fallback_boot.c ramstage-y += fallback_boot.c
ramstage-y += compute_ip_checksum.c ramstage-y += compute_ip_checksum.c

View File

@ -1,5 +1,8 @@
#include <stdlib.h> #include <stdlib.h>
#include <console/console.h> #include <console/console.h>
#ifdef __SMM__
#include <cpu/x86/smm.h>
#endif
#if CONFIG_DEBUG_MALLOC #if CONFIG_DEBUG_MALLOC
#define MALLOCDBG(x...) printk(BIOS_SPEW, x) #define MALLOCDBG(x...) printk(BIOS_SPEW, x)
@ -43,5 +46,11 @@ void *memalign(size_t boundary, size_t size)
void *malloc(size_t size) void *malloc(size_t size)
{ {
#if CONFIG_SMM_TSEG && defined(__SMM__)
if (!free_mem_ptr) {
free_mem_ptr = &_heap + smi_get_tseg_base();
free_mem_end_ptr = &_eheap + smi_get_tseg_base();
}
#endif
return memalign(sizeof(u64), size); return memalign(sizeof(u64), size);
} }