From patchwork Thu Jan 27 14:07:42 2011 Content-Type: text/plain; charset="utf-8" MIME-Version: 1.0 Content-Transfer-Encoding: 7bit Subject: [5/6] Move CMOS handling into separate files in accessors. No API change yet Date: Thu, 27 Jan 2011 14:07:42 -0000 From: Patrick Georgi X-Patchwork-Id: 2564 Message-Id: <20110127141004.259728300@secunet.com> To: coreboot@coreboot.org Cc: Patrick Georgi Signed-off-by: Patrick Georgi Acked-by: Stefan Reinauer Index: nvramtool/accessors/cmos-mem.c =================================================================== --- /dev/null +++ nvramtool/accessors/cmos-mem.c @@ -0,0 +1,37 @@ +#include +#include "cmos_lowlevel.h" + +static void mem_hal_init(void* data); +static unsigned char mem_hal_read(unsigned addr); +static void mem_hal_write(unsigned addr, unsigned char value); +static void mem_set_iopl(int level); + +static unsigned char* mem_hal_data = (unsigned char*)-1; +static void mem_hal_init(void *data) +{ + mem_hal_data = data; +} + +static unsigned char mem_hal_read(unsigned index) +{ + assert(mem_hal_data != (unsigned char*)-1); + return mem_hal_data[index]; +} + +static void mem_hal_write(unsigned index, unsigned char value) +{ + assert(mem_hal_data != (unsigned char*)-1); + mem_hal_data[index] = value; +} + +static void mem_set_iopl(__attribute__ ((unused)) int level) +{ +} + +cmos_access_t memory_hal = { + .init = mem_hal_init, + .read = mem_hal_read, + .write = mem_hal_write, + .set_iopl = mem_set_iopl, +}; + Index: nvramtool/cmos_lowlevel.c =================================================================== --- nvramtool.orig/cmos_lowlevel.c +++ nvramtool/cmos_lowlevel.c @@ -38,98 +38,9 @@ /* Hardware Abstraction Layer: lowlevel byte-wise write access */ -typedef struct { - void (*init)(void* data); - unsigned char (*read)(unsigned addr); - void (*write)(unsigned addr, unsigned char value); - void (*set_iopl)(int level); -} cmos_access_t; - -static void cmos_hal_init(void* data); -static unsigned char cmos_hal_read(unsigned addr); -static void cmos_hal_write(unsigned addr, unsigned char value); -static void cmos_set_iopl(int level); - -static cmos_access_t cmos_hal = { - .init = cmos_hal_init, - .read = cmos_hal_read, - .write = cmos_hal_write, - .set_iopl = cmos_set_iopl, -}; - -static void mem_hal_init(void* data); -static unsigned char mem_hal_read(unsigned addr); -static void mem_hal_write(unsigned addr, unsigned char value); -static void mem_set_iopl(int level); - -static cmos_access_t memory_hal = { - .init = mem_hal_init, - .read = mem_hal_read, - .write = mem_hal_write, - .set_iopl = mem_set_iopl, -}; - +extern cmos_access_t cmos_hal, memory_hal; static cmos_access_t *current_access = &cmos_hal; -/* no need to initialize anything */ -static void cmos_hal_init(__attribute__((unused)) void *data) -{ -} - -static unsigned char cmos_hal_read(unsigned index) -{ - unsigned short port_0, port_1; - - assert(!verify_cmos_byte_index(index)); - - if (index < 128) { - port_0 = 0x70; - port_1 = 0x71; - } else { - port_0 = 0x72; - port_1 = 0x73; - } - - OUTB(index, port_0); - return INB(port_1); -} - -static void cmos_hal_write(unsigned index, unsigned char value) -{ - unsigned short port_0, port_1; - - assert(!verify_cmos_byte_index(index)); - - if (index < 128) { - port_0 = 0x70; - port_1 = 0x71; - } else { - port_0 = 0x72; - port_1 = 0x73; - } - - OUTB(index, port_0); - OUTB(value, port_1); -} - -static unsigned char* mem_hal_data = (unsigned char*)-1; -static void mem_hal_init(void *data) -{ - mem_hal_data = data; -} - -static unsigned char mem_hal_read(unsigned index) -{ - assert(mem_hal_data != (unsigned char*)-1); - return mem_hal_data[index]; -} - -static void mem_hal_write(unsigned index, unsigned char value) -{ - assert(mem_hal_data != (unsigned char*)-1); - mem_hal_data[index] = value; -} - void select_hal(hal_t hal, void *data) { switch(hal) { @@ -353,42 +264,6 @@ void set_iopl(int level) current_access->set_iopl(level); } -static void cmos_set_iopl(int level) -{ -#if defined(__FreeBSD__) - static int io_fd = -1; -#endif - - assert((level >= 0) && (level <= 3)); - -#if defined(__FreeBSD__) - if (level == 0) { - if (io_fd != -1) { - close(io_fd); - io_fd = -1; - } - } else { - if (io_fd == -1) { - io_fd = open("/dev/io", O_RDWR); - if (io_fd < 0) { - perror("/dev/io"); - exit(1); - } - } - } -#else - if (iopl(level)) { - fprintf(stderr, "%s: iopl() system call failed. " - "You must be root to do this.\n", prog_name); - exit(1); - } -#endif -} - -static void mem_set_iopl(__attribute__ ((unused)) int level) -{ -} - /**************************************************************************** * verify_cmos_op * Index: nvramtool/common.h =================================================================== --- nvramtool.orig/common.h +++ nvramtool/common.h @@ -43,30 +43,6 @@ #include #include -#if defined(__FreeBSD__) -#include -#include -#define OUTB(x, y) do { u_int tmp = (y); outb(tmp, (x)); } while (0) -#define OUTW(x, y) do { u_int tmp = (y); outw(tmp, (x)); } while (0) -#define OUTL(x, y) do { u_int tmp = (y); outl(tmp, (x)); } while (0) -#define INB(x) __extension__ ({ u_int tmp = (x); inb(tmp); }) -#define INW(x) __extension__ ({ u_int tmp = (x); inw(tmp); }) -#define INL(x) __extension__ ({ u_int tmp = (x); inl(tmp); }) -#else -#if defined(__GLIBC__) -#include -#endif -#if (defined(__MACH__) && defined(__APPLE__)) -#include -#endif -#define OUTB outb -#define OUTW outw -#define OUTL outl -#define INB inb -#define INW inw -#define INL inl -#endif - #define FALSE 0 #define TRUE 1 Index: nvramtool/Makefile =================================================================== --- nvramtool.orig/Makefile +++ nvramtool/Makefile @@ -31,7 +31,7 @@ CLI_OBJS = cli/nvramtool.o cli/opts.o OBJS = cmos_lowlevel.o cmos_ops.o common.o compute_ip_checksum.o \ hexdump.o input_file.o layout.o accessors/layout-text.o lbtable.o \ - reg_expr.o cbfs.o + reg_expr.o cbfs.o accessors/cmos-hw-unix.o accessors/cmos-mem.o OBJS += $(CLI_OBJS) Index: nvramtool/cmos_lowlevel.h =================================================================== --- nvramtool.orig/cmos_lowlevel.h +++ nvramtool/cmos_lowlevel.h @@ -34,6 +34,13 @@ #include "common.h" #include "layout.h" +typedef struct { + void (*init)(void* data); + unsigned char (*read)(unsigned addr); + void (*write)(unsigned addr, unsigned char value); + void (*set_iopl)(int level); +} cmos_access_t; + typedef enum { HAL_CMOS, HAL_MEMORY } hal_t; void select_hal(hal_t hal, void *data); Index: nvramtool/accessors/cmos-hw-unix.c =================================================================== --- /dev/null +++ nvramtool/accessors/cmos-hw-unix.c @@ -0,0 +1,122 @@ +#include +#include "cmos_lowlevel.h" + +#if defined(__FreeBSD__) +#include +#include +#define OUTB(x, y) do { u_int tmp = (y); outb(tmp, (x)); } while (0) +#define OUTW(x, y) do { u_int tmp = (y); outw(tmp, (x)); } while (0) +#define OUTL(x, y) do { u_int tmp = (y); outl(tmp, (x)); } while (0) +#define INB(x) __extension__ ({ u_int tmp = (x); inb(tmp); }) +#define INW(x) __extension__ ({ u_int tmp = (x); inw(tmp); }) +#define INL(x) __extension__ ({ u_int tmp = (x); inl(tmp); }) +#else +#if defined(__GLIBC__) +#include +#endif +#if (defined(__MACH__) && defined(__APPLE__)) +#include +#endif +#define OUTB outb +#define OUTW outw +#define OUTL outl +#define INB inb +#define INW inw +#define INL inl +#endif + +static void cmos_hal_init(void* data); +static unsigned char cmos_hal_read(unsigned addr); +static void cmos_hal_write(unsigned addr, unsigned char value); +static void cmos_set_iopl(int level); + +/* no need to initialize anything */ +static void cmos_hal_init(__attribute__((unused)) void *data) +{ +} + +static unsigned char cmos_hal_read(unsigned index) +{ + unsigned short port_0, port_1; + + assert(!verify_cmos_byte_index(index)); + + if (index < 128) { + port_0 = 0x70; + port_1 = 0x71; + } else { + port_0 = 0x72; + port_1 = 0x73; + } + + OUTB(index, port_0); + return INB(port_1); +} + +static void cmos_hal_write(unsigned index, unsigned char value) +{ + unsigned short port_0, port_1; + + assert(!verify_cmos_byte_index(index)); + + if (index < 128) { + port_0 = 0x70; + port_1 = 0x71; + } else { + port_0 = 0x72; + port_1 = 0x73; + } + + OUTB(index, port_0); + OUTB(value, port_1); +} + + +/**************************************************************************** + * cmos_set_iopl + * + * Set the I/O privilege level of the executing process. Root privileges are + * required for performing this action. A sufficient I/O privilege level + * allows the process to access x86 I/O address space and to disable/reenable + * interrupts while executing in user space. Messing with the I/O privilege + * level is therefore somewhat dangerous. + ****************************************************************************/ +static void cmos_set_iopl(int level) +{ +#if defined(__FreeBSD__) + static int io_fd = -1; +#endif + + assert((level >= 0) && (level <= 3)); + +#if defined(__FreeBSD__) + if (level == 0) { + if (io_fd != -1) { + close(io_fd); + io_fd = -1; + } + } else { + if (io_fd == -1) { + io_fd = open("/dev/io", O_RDWR); + if (io_fd < 0) { + perror("/dev/io"); + exit(1); + } + } + } +#else + if (iopl(level)) { + fprintf(stderr, "%s: iopl() system call failed. " + "You must be root to do this.\n", prog_name); + exit(1); + } +#endif +} + +cmos_access_t cmos_hal = { + .init = cmos_hal_init, + .read = cmos_hal_read, + .write = cmos_hal_write, + .set_iopl = cmos_set_iopl, +}; +