Introduce a generic global variable storage mechanism and switch the
printk buffer management to it. Build tested and boot tested and result tested on Qemu. Adding a new global variable is not as easy as it looks, but the comments in the code should be good enough to tell you how. Signed-off-by: Carl-Daniel Hailfinger <c-d.hailfinger.devel.2006@gmx.net> Acked-by: Ronald G. Minnich <rminnich@gmail.com> git-svn-id: svn://coreboot.org/repository/coreboot-v3@760 f3766cd6-281f-0410-b1cd-43a5c92072e9
This commit is contained in:
parent
3cff5b912d
commit
07f3009f43
4 changed files with 31 additions and 13 deletions
|
|
@ -70,10 +70,19 @@ void init_archive(struct mem_file *archive)
|
|||
|
||||
}
|
||||
|
||||
/*
|
||||
* The name is slightly misleading because this is the initial stack pointer,
|
||||
* not the address of the first element on the stack.
|
||||
*/
|
||||
void *bottom_of_stack(void)
|
||||
{
|
||||
/* -4-4 because CONFIG_CARBASE + CONFIG_CARSIZE - 4 is initial %esp */
|
||||
return (void *)(CONFIG_CARBASE + CONFIG_CARSIZE - 4 - 4);
|
||||
/* -4 because CONFIG_CARBASE + CONFIG_CARSIZE - 4 is initial %esp */
|
||||
return (void *)(CONFIG_CARBASE + CONFIG_CARSIZE - 4);
|
||||
}
|
||||
|
||||
struct global_vars *global_vars(void)
|
||||
{
|
||||
return (struct global_vars *)(bottom_of_stack() - sizeof(struct global_vars));
|
||||
}
|
||||
|
||||
void dump_mem_range(int msg_level, unsigned char *buf, int size)
|
||||
|
|
|
|||
|
|
@ -202,6 +202,7 @@ static inline __attribute__((always_inline)) void hlt(void)
|
|||
}
|
||||
|
||||
SHARED(bottom_of_stack, void *, void);
|
||||
SHARED(global_vars, struct global_vars *, void);
|
||||
|
||||
#ifdef CONFIG_CONSOLE_BUFFER
|
||||
#define PRINTK_BUF_SIZE_CAR (CONFIG_CARSIZE / 2)
|
||||
|
|
|
|||
|
|
@ -59,6 +59,18 @@ struct printk_buffer {
|
|||
};
|
||||
#endif
|
||||
|
||||
/*
|
||||
* If you change struct global_vars in any way, you have to fix all stage0 asm
|
||||
* code. The stage0 asm code modification is nontrivial (size of the struct,
|
||||
* alignment, initialization, order of struct members, initialization).
|
||||
* Depending on your compiler, real breakage may happen.
|
||||
*/
|
||||
struct global_vars {
|
||||
#ifdef CONFIG_CONSOLE_BUFFER
|
||||
struct printk_buffer *printk_buffer;
|
||||
#endif
|
||||
};
|
||||
|
||||
SHARED_WITH_ATTRIBUTES(printk, int, __attribute__((format (printf, 2, 3))),
|
||||
int msg_level, const char *fmt, ...);
|
||||
SHARED(banner, void, int msg_level, const char *msg);
|
||||
|
|
|
|||
|
|
@ -35,13 +35,16 @@ static unsigned int console_loglevel(void)
|
|||
}
|
||||
|
||||
#ifdef CONFIG_CONSOLE_BUFFER
|
||||
struct printk_buffer *printk_buffer_addr(void)
|
||||
{
|
||||
return global_vars()->printk_buffer;
|
||||
}
|
||||
|
||||
void printk_buffer_move(void *newaddr, int newsize)
|
||||
{
|
||||
struct printk_buffer **p;
|
||||
struct printk_buffer *oldbuf, *newbuf;
|
||||
int copylen;
|
||||
p = bottom_of_stack();
|
||||
oldbuf = *p;
|
||||
oldbuf = printk_buffer_addr();
|
||||
newbuf = newaddr;
|
||||
newbuf->len = newsize;
|
||||
newbuf->readoffset = 0;
|
||||
|
|
@ -68,17 +71,10 @@ void printk_buffer_move(void *newaddr, int newsize)
|
|||
&oldbuf->buffer[0], copylen);
|
||||
newbuf->writeoffset += copylen;
|
||||
}
|
||||
*p = newbuf;
|
||||
global_vars()->printk_buffer = newbuf;
|
||||
return;
|
||||
}
|
||||
|
||||
struct printk_buffer *printk_buffer_addr(void)
|
||||
{
|
||||
struct printk_buffer **p;
|
||||
p = bottom_of_stack();
|
||||
return *p;
|
||||
}
|
||||
|
||||
void printk_buffer_init(void)
|
||||
{
|
||||
struct printk_buffer *buf = printk_buffer_addr();
|
||||
|
|
|
|||
Loading…
Add table
Add a link
Reference in a new issue