aboutsummaryrefslogtreecommitdiff
path: root/src/northbridge/intel/i82830/smihandler.c
diff options
context:
space:
mode:
Diffstat (limited to 'src/northbridge/intel/i82830/smihandler.c')
-rw-r--r--src/northbridge/intel/i82830/smihandler.c387
1 files changed, 0 insertions, 387 deletions
diff --git a/src/northbridge/intel/i82830/smihandler.c b/src/northbridge/intel/i82830/smihandler.c
deleted file mode 100644
index 569e62ec7b..0000000000
--- a/src/northbridge/intel/i82830/smihandler.c
+++ /dev/null
@@ -1,387 +0,0 @@
-/*
- * This file is part of the coreboot project.
- *
- * Copyright (C) 2010 coresystems GmbH
- *
- * This program is free software; you can redistribute it and/or
- * modify it under the terms of the GNU General Public License as
- * published by the Free Software Foundation; version 2 of
- * the License.
- *
- * This program is distributed in the hope that it will be useful,
- * but WITHOUT ANY WARRANTY; without even the implied warranty of
- * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
- * GNU General Public License for more details.
- */
-
-#include <types.h>
-#include <compiler.h>
-#include <string.h>
-#include <arch/io.h>
-#include <console/console.h>
-#include <cpu/x86/cache.h>
-#include <cpu/x86/smm.h>
-#include <device/pci_def.h>
-#include "i82830.h"
-
-extern unsigned char *mbi;
-extern u32 mbi_len;
-
-// #define DEBUG_SMI_I82830
-
-/* If YABEL is enabled and it's not running at 0x00000000, we have to add some
- * offset to all our mbi object memory accesses
- */
-#if IS_ENABLED(CONFIG_PCI_OPTION_ROM_RUN_YABEL) && !CONFIG_YABEL_DIRECTHW
-#define OBJ_OFFSET CONFIG_YABEL_VIRTMEM_LOCATION
-#else
-#define OBJ_OFFSET 0x00000
-#endif
-
-/* I830M */
-#define SMRAM 0x90
-#define D_OPEN (1 << 6)
-#define D_CLS (1 << 5)
-#define D_LCK (1 << 4)
-#define G_SMRANE (1 << 3)
-#define C_BASE_SEG ((0 << 2) | (1 << 1) | (0 << 0))
-
-
-typedef struct {
- u32 mhid;
- u32 function;
- u32 retsts;
- u32 rfu;
-} __packed banner_id_t;
-
-#define MSH_OK 0x0000
-#define MSH_OK_RESTART 0x0001
-#define MSH_FWH_ERR 0x00ff
-#define MSH_IF_BAD_ID 0x0100
-#define MSH_IF_BAD_FUNC 0x0101
-#define MSH_IF_MBI_CORRUPT 0x0102
-#define MSH_IF_BAD_HANDLE 0x0103
-#define MSH_ALRDY_ATCHED 0x0104
-#define MSH_NOT_ATCHED 0x0105
-#define MSH_IF 0x0106
-#define MSH_IF_INVADDR 0x0107
-#define MSH_IF_UKN_TYPE 0x0108
-#define MSH_IF_NOT_FOUND 0x0109
-#define MSH_IF_NO_KEY 0x010a
-#define MSH_IF_BUF_SIZE 0x010b
-#define MSH_IF_NOT_PENDING 0x010c
-
-#ifdef DEBUG_SMI_I82830
-static void
-dump(u8 * addr, u32 len)
-{
- printk(BIOS_DEBUG, "\n%s(%p, %x):\n", __func__, addr, len);
- while (len) {
- unsigned int tmpCnt = len;
- unsigned char x;
- if (tmpCnt > 8)
- tmpCnt = 8;
- printk(BIOS_DEBUG, "\n%p: ", addr);
- // print hex
- while (tmpCnt--) {
- x = *addr++;
- printk(BIOS_DEBUG, "%02x ", x);
- }
- tmpCnt = len;
- if (tmpCnt > 8)
- tmpCnt = 8;
- len -= tmpCnt;
- //reset addr ptr to print ascii
- addr = addr - tmpCnt;
- // print ascii
- while (tmpCnt--) {
- x = *addr++;
- if ((x < 32) || (x >= 127)) {
- //non-printable char
- x = '.';
- }
- printk(BIOS_DEBUG, "%c", x);
- }
- }
- printk(BIOS_DEBUG, "\n");
-}
-#endif
-
-typedef struct {
- banner_id_t banner;
- u16 versionmajor;
- u16 versionminor;
- u32 smicombuffersize;
-} __packed version_t;
-
-typedef struct {
- u16 header_id;
- u16 attributes;
- u16 size;
- u8 name_len;
- u8 reserved;
- u32 type;
- u32 header_ext;
- u8 name[0];
-} __packed mbi_header_t;
-
-typedef struct {
- banner_id_t banner;
- u64 handle;
- u32 objnum;
- mbi_header_t header;
-} __packed obj_header_t;
-
-typedef struct {
- banner_id_t banner;
- u64 handle;
- u32 objnum;
- u32 start;
- u32 numbytes;
- u32 buflen;
- u32 buffer;
-} __packed get_object_t;
-
-static void mbi_call(u8 subf, banner_id_t *banner_id)
-{
-#ifdef DEBUG_SMI_I82830
- printk(BIOS_DEBUG, "MBI\n");
- printk(BIOS_DEBUG, "|- sub function %x\n", subf);
- printk(BIOS_DEBUG, "|- banner id @ %x\n", (u32)banner_id);
- printk(BIOS_DEBUG, "| |- mhid %x\n", banner_id->mhid);
- printk(BIOS_DEBUG, "| |- function %x\n", banner_id->function);
- printk(BIOS_DEBUG, "| |- return status %x\n", banner_id->retsts);
- printk(BIOS_DEBUG, "| |- rfu %x\n", banner_id->rfu);
-#endif
-
- switch(banner_id->function) {
- case 0x0001: {
- version_t *version;
- printk(BIOS_DEBUG, "|- MBI_QueryInterface\n");
- version = (version_t *)banner_id;
- version->banner.retsts = MSH_OK;
- version->versionmajor = 1;
- version->versionminor = 3;
- version->smicombuffersize = 0x1000;
- break;
- }
- case 0x0002:
- printk(BIOS_DEBUG, "|- MBI_Attach\n");
- printk(BIOS_DEBUG, "| |- Not Implemented!\n");
- break;
- case 0x0003:
- printk(BIOS_DEBUG, "|- MBI_Detach\n");
- printk(BIOS_DEBUG, "| |- Not Implemented!\n");
- break;
- case 0x0201: {
- obj_header_t *obj_header = (obj_header_t *)banner_id;
- mbi_header_t *mbi_header = NULL;
- printk(BIOS_DEBUG, "|- MBI_GetObjectHeader\n");
- printk(BIOS_DEBUG, "| |- objnum = %d\n", obj_header->objnum);
-
- int i, count = 0;
- obj_header->banner.retsts = MSH_IF_NOT_FOUND;
-
- for (i = 0; i < mbi_len;) {
- int len;
-
- if (!(mbi[i] == 0xf0 && mbi [i+1] == 0xf6)) {
- i+=16;
- continue;
- }
-
- mbi_header = (mbi_header_t *)&mbi[i];
- len = ALIGN((mbi_header->size * 16) + sizeof(mbi_header) + ALIGN(mbi_header->name_len, 16), 16);
-
- if (obj_header->objnum == count) {
-#ifdef DEBUG_SMI_I82830
- if (mbi_header->name_len == 0xff) {
- printk(BIOS_DEBUG, "| |- corrupt.\n");
- break;
- }
-#endif
- int headerlen = ALIGN(sizeof(mbi_header) + ALIGN(mbi_header->name_len, 16), 16);
-#ifdef DEBUG_SMI_I82830
- printk(BIOS_DEBUG, "| |- headerlen = %d\n", headerlen);
-#endif
- memcpy(&obj_header->header, mbi_header, headerlen);
- obj_header->banner.retsts = MSH_OK;
- printk(BIOS_DEBUG, "| |- MBI module '");
- int j;
- for (j = 0; j < mbi_header->name_len && mbi_header->name[j]; j++)
- printk(BIOS_DEBUG, "%c", mbi_header->name[j]);
- printk(BIOS_DEBUG, "' found.\n");
-#ifdef DEBUG_SMI_I82830
- dump((u8 *)banner_id, sizeof(obj_header_t) + ALIGN(mbi_header->name_len, 16));
-#endif
- break;
- }
- i += len;
- count++;
- }
- if (obj_header->banner.retsts == MSH_IF_NOT_FOUND)
- printk(BIOS_DEBUG, "| |- MBI object #%d not found.\n", obj_header->objnum);
- break;
- }
- case 0x0203: {
- get_object_t *getobj = (get_object_t *)banner_id;
- mbi_header_t *mbi_header = NULL;
- printk(BIOS_DEBUG, "|- MBI_GetObject\n");
-#ifdef DEBUG_SMI_I82830
- printk(BIOS_DEBUG, "| |- handle = %016Lx\n", getobj->handle);
-#endif
- printk(BIOS_DEBUG, "| |- objnum = %d\n", getobj->objnum);
- printk(BIOS_DEBUG, "| |- start = %x\n", getobj->start);
- printk(BIOS_DEBUG, "| |- numbytes = %x\n", getobj->numbytes);
- printk(BIOS_DEBUG, "| |- buflen = %x\n", getobj->buflen);
- printk(BIOS_DEBUG, "| |- buffer = %x\n", getobj->buffer);
-
- int i, count = 0;
- getobj->banner.retsts = MSH_IF_NOT_FOUND;
-
- for (i = 0; i< mbi_len;) {
- int headerlen, objectlen;
-
- if (!(mbi[i] == 0xf0 && mbi [i+1] == 0xf6)) {
- i+=16;
- continue;
- }
-
- mbi_header = (mbi_header_t *)&mbi[i];
- headerlen = ALIGN(sizeof(mbi_header) + ALIGN(mbi_header->name_len, 16), 16);
- objectlen = ALIGN((mbi_header->size * 16), 16);
-
- if (getobj->objnum == count) {
- printk(BIOS_DEBUG, "| |- len = %x\n", headerlen + objectlen);
-
- memcpy((void *)(getobj->buffer + OBJ_OFFSET),
- ((char *)mbi_header) + headerlen, (objectlen > getobj->buflen) ? getobj->buflen : objectlen);
-
- getobj->banner.retsts = MSH_OK;
-#ifdef DEBUG_SMI_I82830
- dump((u8 *)banner_id, sizeof(*getobj));
- dump((u8 *)getobj->buffer + OBJ_OFFSET, objectlen);
-#endif
- break;
- }
- i += (headerlen + objectlen);
- count++;
- }
- if (getobj->banner.retsts == MSH_IF_NOT_FOUND)
- printk(BIOS_DEBUG, "MBI module %d not found.\n", getobj->objnum);
- break;
- }
- default:
- printk(BIOS_DEBUG, "|- function %x\n", banner_id->function);
- printk(BIOS_DEBUG, "| |- Unknown Function!\n");
- break;
- }
- printk(BIOS_DEBUG, "\n");
- //dump(banner_id, 0x20);
-}
-
-#define SMI_IFC_SUCCESS 1
-#define SMI_IFC_FAILURE_GENERIC 0
-#define SMI_IFC_FAILURE_INVALID 2
-#define SMI_IFC_FAILURE_CRITICAL 4
-#define SMI_IFC_FAILURE_NONCRITICAL 6
-
-#define PC10 0x10
-#define PC11 0x11
-#define PC12 0x12
-#define PC13 0x13
-
-static void smi_interface_call(void)
-{
- u8 *mmio = (u8 *)pci_read_config32(PCI_DEV(0, 0x02, 0), 0x14);
- // mmio &= 0xfff80000;
- // printk(BIOS_DEBUG, "mmio=%x\n", mmio);
- u16 swsmi = pci_read_config16(PCI_DEV(0, 0x02, 0), 0xe0);
-
- if (!(swsmi & 1))
- return;
-
- swsmi &= ~(1 << 0); // clear SMI toggle
-
- switch ((swsmi>>1) & 0xf) {
- case 0:
- printk(BIOS_DEBUG, "Interface Function Presence Test.\n");
- swsmi = 0;
- swsmi &= ~(7 << 5); // Exit: Result
- swsmi |= (SMI_IFC_SUCCESS << 5);
- swsmi &= 0xff;
- swsmi |= (PC13 << 8);
- pci_write_config16(PCI_DEV(0, 0x02, 0), 0xe0, swsmi);
- // write magic
- write32(mmio + 0x71428, 0x494e5443);
- return;
- case 4:
- printk(BIOS_DEBUG, "Get BIOS Data.\n");
- printk(BIOS_DEBUG, "swsmi=%04x\n", swsmi);
- break;
- case 5:
- printk(BIOS_DEBUG, "Call MBI Functions.\n");
- mbi_call(swsmi >> 8, (banner_id_t *)((read32(mmio + 0x71428) & 0x000fffff) + OBJ_OFFSET) );
- // swsmi = 0x0000;
- swsmi &= ~(7 << 5); // Exit: Result
- swsmi |= (SMI_IFC_SUCCESS << 5);
- pci_write_config16(PCI_DEV(0, 0x02, 0), 0xe0, swsmi);
- return;
- case 6:
- printk(BIOS_DEBUG, "System BIOS Callbacks.\n");
- printk(BIOS_DEBUG, "swsmi=%04x\n", swsmi);
- break;
- default:
- printk(BIOS_DEBUG, "Unknown SMI interface call %04x\n", swsmi);
- break;
- }
-
- swsmi &= ~(7 << 5); // Exit: Result
- swsmi |= (SMI_IFC_FAILURE_CRITICAL << 7);
- pci_write_config16(PCI_DEV(0, 0x02, 0), 0xe0, swsmi);
-}
-
-/**
- * @brief read and clear ERRSTS
- * @return ERRSTS register
- */
-static u16 reset_err_status(void)
-{
- u16 reg16;
-
- reg16 = pci_read_config16(PCI_DEV(0, 0x00, 0), ERRSTS);
- /* set status bits are cleared by writing 1 to them */
- pci_write_config16(PCI_DEV(0, 0x00, 0), ERRSTS, reg16);
-
- return reg16;
-}
-
-static void dump_err_status(u32 errsts)
-{
- printk(BIOS_DEBUG, "ERRSTS: ");
- if (errsts & (1 << 12)) printk(BIOS_DEBUG, "MBI ");
- if (errsts & (1 << 9)) printk(BIOS_DEBUG, "LCKF ");
- if (errsts & (1 << 8)) printk(BIOS_DEBUG, "DTF ");
- if (errsts & (1 << 5)) printk(BIOS_DEBUG, "UNSC ");
- if (errsts & (1 << 4)) printk(BIOS_DEBUG, "OOGF ");
- if (errsts & (1 << 3)) printk(BIOS_DEBUG, "IAAF ");
- if (errsts & (1 << 2)) printk(BIOS_DEBUG, "ITTEF ");
- printk(BIOS_DEBUG, "\n");
-}
-
-void northbridge_smi_handler(unsigned int node, smm_state_save_area_t *state_save)
-{
- u16 errsts;
-
- /* We need to clear the SMI status registers, or we won't see what's
- * happening in the following calls.
- */
- errsts = reset_err_status();
- if (errsts & (1 << 12)) {
- smi_interface_call();
- } else {
- if (errsts)
- dump_err_status(errsts);
- }
-
-}