git: 9front

Download patch

ref: 06257df291d6436804790b5678f05ea0beef57e5
parent: 41de8a9ce54c59b6a9d66468c765795b1c25d1fc
author: cinap_lenrek <cinap_lenrek@gmx.de>
date: Fri May 18 21:58:40 EDT 2012

kernel: add debug driver for dumping acpi tables

--- /dev/null
+++ b/sys/src/9/pc/acpi.c
@@ -1,0 +1,219 @@
+#include "u.h"
+#include "../port/lib.h"
+#include "mem.h"
+#include "dat.h"
+#include "fns.h"
+
+typedef struct Rsd Rsd;
+typedef struct Tbl Tbl;
+
+struct Rsd {
+	uchar	sig[8];
+	uchar	csum;
+	uchar	oemid[6];
+	uchar	rev;
+	uchar	raddr[4];
+	uchar	len[4];
+	uchar	xaddr[8];
+	uchar	xcsum;
+	uchar	reserved[3];
+};
+
+struct Tbl {
+	uchar	sig[4];
+	uchar	len[4];
+	uchar	rev;
+	uchar	csum;
+	uchar	oemid[6];
+	uchar	oemtid[8];
+	uchar	oemrev[4];
+	uchar	cid[4];
+	uchar	crev[4];
+	uchar	data[];
+};
+
+static int ntbltab;
+static Tbl *tbltab[64];
+
+static ushort
+get16(uchar *p){
+	return p[1]<<8 | p[0];
+}
+
+static uint
+get32(uchar *p){
+	return p[3]<<24 | p[2]<<16 | p[1]<<8 | p[0];
+}
+
+static uvlong
+get64(uchar *p){
+	uvlong u;
+
+	u = get32(p+4);
+	return u<<32 | get32(p);
+}
+
+static int
+checksum(void *v, int n)
+{
+	uchar *p, s;
+
+	s = 0;
+	p = v;
+	while(n-- > 0)
+		s += *p++;
+	return s;
+}
+
+static void*
+rsdscan(uchar* addr, int len, char* sig)
+{
+	int sl;
+	uchar *e, *p;
+
+	e = addr+len;
+	sl = strlen(sig);
+	for(p = addr; p+sl < e; p += 16){
+		if(memcmp(p, sig, sl))
+			continue;
+		return p;
+	}
+	return nil;
+}
+
+static void*
+rsdsearch(char* sig)
+{
+	uintptr p;
+	uchar *bda;
+	Rsd *rsd;
+
+	/*
+	 * Search for the data structure signature:
+	 * 1) in the first KB of the EBDA;
+	 * 2) in the BIOS ROM between 0xE0000 and 0xFFFFF.
+	 */
+	if(strncmp((char*)KADDR(0xFFFD9), "EISA", 4) == 0){
+		bda = KADDR(0x400);
+		if((p = (bda[0x0F]<<8)|bda[0x0E]))
+			if(rsd = rsdscan(KADDR(p), 1024, sig))
+				return rsd;
+	}
+	return rsdscan(KADDR(0xE0000), 0x20000, sig);
+}
+
+static void
+maptable(uvlong xpa)
+{
+	uchar *p, *e;
+	Tbl *t, *a;
+	uintptr pa;
+	u32int l;
+	int i;
+
+	pa = xpa;
+	if((uvlong)pa != xpa || pa == 0)
+		return;
+	if(ntbltab >= nelem(tbltab))
+		return;
+	if((t = vmap(pa, 8)) == nil)
+		return;
+	l = get32(t->len);
+	if(l < sizeof(Tbl) || t->sig[0] == 0){
+		vunmap(t, 8);
+		return;
+	}
+	for(i=0; i<ntbltab; i++){
+		if(memcmp(tbltab[i]->sig, t->sig, sizeof(t->sig)) == 0)
+			break;
+	}
+	vunmap(t, 8);
+	if(i < ntbltab)
+		return;
+	if((a = malloc(l)) == nil)
+		return;
+	if((t = vmap(pa, l)) == nil){
+		free(a);
+		return;
+	}
+	if(checksum(t, l)){
+		vunmap(t, l);
+		free(a);
+		return;
+	}
+	memmove(a, t, l);
+	vunmap(t, l);
+
+	tbltab[ntbltab++] = t = a;
+
+	if(0) print("acpi: %llux %.4s %d\n", xpa, t->sig, l);
+
+	p = (uchar*)t;
+	e = p + l;
+	if(memcmp("RSDT", t->sig, 4) == 0){
+		for(p = t->data; p+3 < e; p += 4)
+			maptable(get32(p));
+		return;
+	}
+	if(memcmp("XSDT", t->sig, 4) == 0){
+		for(p = t->data; p+7 < e; p += 8)
+			maptable(get64(p));
+		return;
+	}
+	if(memcmp("FACP", t->sig, 4) == 0){
+		if(l < 44)
+			return;
+		maptable(get32(p + 40));
+		if(l < 148)
+			return;
+		maptable(get64(p + 140));
+		return;
+	}
+}
+
+static long
+readtbls(Chan*, void *v, long n, vlong o)
+{
+	int i, l, m;
+	uchar *p;
+	Tbl *t;
+
+	p = v;
+	for(i=0; n > 0 && i < ntbltab; i++){
+		t = tbltab[i];
+		l = get32(t->len);
+		if(o >= l){
+			o -= l;
+			continue;
+		}
+		m = l - o;
+		if(m > n)
+			m = n;
+		memmove(p, (uchar*)t + o, m);
+		p += m;
+		n -= m;
+		o = 0;
+	}
+	return p - (uchar*)v;
+}
+
+void
+acpilink(void)
+{
+	Rsd *r;
+
+	/*
+	 * this is a debug driver to dump the acpi tables.
+	 * do nothing unless *acpi gets explicitly enabled.
+	 */
+	if(getconf("*acpi") == nil)
+		return;
+	if((r = rsdsearch("RSD PTR ")) == nil)
+		return;
+	if(checksum(r, 20) == 0)
+		maptable(get32(r->raddr));
+	if(r->rev >= 2)
+		if(checksum(r, 36) == 0)
+			maptable(get64(r->xaddr));
+	addarchfile("acpitbls", 0444, readtbls, nil);
+}
--- a/sys/src/9/pc/pccpuf
+++ b/sys/src/9/pc/pccpuf
@@ -41,6 +41,7 @@
 	devpccard
 	devi82365
 	cputemp
+	acpi
 	apm		apmjump
 	ether2000	ether8390
 	ether2114x	pci
--- a/sys/src/9/pc/pcf
+++ b/sys/src/9/pc/pcf
@@ -42,6 +42,7 @@
 	devpccard
 	devi82365
 	cputemp
+	acpi
 	apm		apmjump
 	ether2000	ether8390
 	ether2114x	pci
--