1 /* 2 * Common Option ROM Functions 3 * 4 * This program is free software; you can redistribute it and/or modify 5 * it under the terms of the GNU General Public License as published by 6 * the Free Software Foundation; either version 2 of the License, or 7 * (at your option) any later version. 8 * 9 * This program is distributed in the hope that it will be useful, 10 * but WITHOUT ANY WARRANTY; without even the implied warranty of 11 * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the 12 * GNU General Public License for more details. 13 * 14 * You should have received a copy of the GNU General Public License 15 * along with this program; if not, see <http://www.gnu.org/licenses/>. 16 * 17 * Copyright Novell Inc, 2009 18 * Authors: Alexander Graf <agraf@suse.de> 19 */ 20 21 22 #include "../../include/hw/nvram/fw_cfg_keys.h" 23 24 #define BIOS_CFG_IOPORT_CFG 0x510 25 #define BIOS_CFG_IOPORT_DATA 0x511 26 27 /* Break the translation block flow so -d cpu shows us values */ 28 #define DEBUG_HERE \ 29 jmp 1f; \ 30 1: 31 32 /* 33 * Read a variable from the fw_cfg device. 34 * Clobbers: %edx 35 * Out: %eax 36 */ 37 .macro read_fw VAR 38 mov $\VAR, %ax 39 mov $BIOS_CFG_IOPORT_CFG, %dx 40 outw %ax, (%dx) 41 mov $BIOS_CFG_IOPORT_DATA, %dx 42 inb (%dx), %al 43 shl $8, %eax 44 inb (%dx), %al 45 shl $8, %eax 46 inb (%dx), %al 47 shl $8, %eax 48 inb (%dx), %al 49 bswap %eax 50 .endm 51 52 #define read_fw_blob_pre(var) \ 53 read_fw var ## _SIZE; \ 54 mov %eax, %ecx; \ 55 mov $var ## _DATA, %ax; \ 56 mov $BIOS_CFG_IOPORT_CFG, %edx; \ 57 outw %ax, (%dx); \ 58 mov $BIOS_CFG_IOPORT_DATA, %dx; \ 59 cld 60 61 /* 62 * Read a blob from the fw_cfg device. 63 * Requires _ADDR, _SIZE and _DATA values for the parameter. 64 * 65 * Clobbers: %eax, %edx, %es, %ecx, %edi 66 */ 67 #define read_fw_blob(var) \ 68 read_fw var ## _ADDR; \ 69 mov %eax, %edi; \ 70 read_fw_blob_pre(var); \ 71 /* old as(1) doesn't like this insn so emit the bytes instead: \ 72 rep insb (%dx), %es:(%edi); \ 73 */ \ 74 .dc.b 0xf3,0x6c 75 76 /* 77 * Read a blob from the fw_cfg device in forced addr32 mode. 78 * Requires _ADDR, _SIZE and _DATA values for the parameter. 79 * 80 * Clobbers: %eax, %edx, %es, %ecx, %edi 81 */ 82 #define read_fw_blob_addr32(var) \ 83 read_fw var ## _ADDR; \ 84 mov %eax, %edi; \ 85 read_fw_blob_pre(var); \ 86 /* old as(1) doesn't like this insn so emit the bytes instead: \ 87 addr32 rep insb (%dx), %es:(%edi); \ 88 */ \ 89 .dc.b 0x67,0xf3,0x6c 90 91 /* 92 * Read a blob from the fw_cfg device in forced addr32 mode, address is in %edi. 93 * Requires _SIZE and _DATA values for the parameter. 94 * 95 * Clobbers: %eax, %edx, %edi, %es, %ecx 96 */ 97 #define read_fw_blob_addr32_edi(var) \ 98 read_fw_blob_pre(var); \ 99 /* old as(1) doesn't like this insn so emit the bytes instead: \ 100 addr32 rep insb (%dx), %es:(%edi); \ 101 */ \ 102 .dc.b 0x67,0xf3,0x6c 103 104 #define OPTION_ROM_START \ 105 .code16; \ 106 .text; \ 107 .global _start; \ 108 _start:; \ 109 .short 0xaa55; \ 110 .byte (_end - _start) / 512; 111 112 #define BOOT_ROM_START \ 113 OPTION_ROM_START \ 114 lret; \ 115 .org 0x18; \ 116 .short 0; \ 117 .short _pnph; \ 118 _pnph: \ 119 .ascii "$PnP"; \ 120 .byte 0x01; \ 121 .byte ( _pnph_len / 16 ); \ 122 .short 0x0000; \ 123 .byte 0x00; \ 124 .byte 0x00; \ 125 .long 0x00000000; \ 126 .short _manufacturer; \ 127 .short _product; \ 128 .long 0x00000000; \ 129 .short 0x0000; \ 130 .short 0x0000; \ 131 .short _bev; \ 132 .short 0x0000; \ 133 .short 0x0000; \ 134 .equ _pnph_len, . - _pnph; \ 135 _bev:; \ 136 /* DS = CS */ \ 137 movw %cs, %ax; \ 138 movw %ax, %ds; 139 140 #define OPTION_ROM_END \ 141 .byte 0; \ 142 .align 512, 0; \ 143 _end: 144 145 #define BOOT_ROM_END \ 146 _manufacturer:; \ 147 .asciz "QEMU"; \ 148 _product:; \ 149 .asciz BOOT_ROM_PRODUCT; \ 150 OPTION_ROM_END 151 152