[SeaBIOS] [PATCH] make seabios 386/486 friendly

Kevin O'Connor kevin at koconnor.net
Sun Jan 22 22:46:56 CET 2012


On Sun, Jan 22, 2012 at 10:04:33PM +0100, Rudolf Marek wrote:
> Hello,
> 
> Following patch makes seabios friendly to 386/486 CPUs, providing a
> way how to emulate the CPUID instruction and using TSC only if CPU
> actually supports the TSC. Otherwise it uses TSC emulation mode
> which is similar to what is used in Xenomai except we use timer0
> here.

Thanks - please see my comments below.

> With this patch it is able to run on 486SX class system aka
> bifferboard together with coreboot.

It would be preferable if this was in two patches - one to check for
cpuid and one to check for the tsc.

[...]
> --- a/src/biosvar.h
> +++ b/src/biosvar.h
> @@ -238,6 +238,10 @@ struct extended_bios_data_area_s {
>  
>      u16 boot_sequence;
>  
> +    /* TSC emulation timekeepers */
> +    u64 tsc_8254;
> +    int last_tsc_8254;

Can't the existing timer_counter in the BDA be used instead?

[...]
> --- a/src/clock.c
> +++ b/src/clock.c
> @@ -57,6 +57,24 @@
>  #define CALIBRATE_COUNT 0x800   // Approx 1.7ms
>  
>  u32 cpu_khz VAR16VISIBLE;
> +u8 no_tsc VAR16VISIBLE;
> +
> +u64 emulate_tsc(void) {
> +	int cnt, d;
> +	u16 ebda_seg = get_ebda_seg();
> +	u64 ret;
> +	/* read timer 0 current count */
> +	ret = GET_EBDA2(ebda_seg, tsc_8254);
> +	/* readback mode has slightly shifted registers, works on all 8254, readback PIT0 latch */
> +	outb(PM_SEL_READBACK | 0x10 | 0x2, PORT_PIT_MODE);

BTW, what's the impact of writing to the PORT_PIT_MODE?  Will it
corrupt the old value?  (Not an issue for the patch, as obviously
something is better than nothing for your board.)

[...]
> +    SET_GLOBAL(no_tsc, 0);

FYI - SET_GLOBAL(x,y) is the same as writing "x=y".  The macro is only
available in 32bit mode, so it's not really any different.

[...]
> --- a/src/post.c
> +++ b/src/post.c
> @@ -360,6 +360,9 @@ handle_post(void)
>      // Enable CPU caching
>      setcr0(getcr0() & ~(CR0_CD|CR0_NW));
>  
> +    // Emulate the CPUID if 386/486
> +    detect_cpuid();

This is too early (can't assign global variables here on QEmu).  I
suggest you put in maininit() after the malloc_fixup() call.

[...]
> --- a/src/util.h
> +++ b/src/util.h
> @@ -7,6 +7,10 @@
>  #define __UTIL_H
>  
>  #include "types.h" // u32
> +#include "biosvar.h" // GET_GLOBAL
> +
> +#define likely(x)  __builtin_expect(!!(x), 1)
> +#define unlikely(x) __builtin_expect(!!(x), 0)

These already exist in types.h.

-Kevin



More information about the SeaBIOS mailing list