# HG changeset patch # User dietmar.hahn@xxxxxxxxxxxxxxxxxxx # Node ID 3e3e92fb854ad6c3d92ddcec92a0cfed2eb78393 # Parent d7f7021902a2c6b5beee0abfdbdc89fce7892450 First Version of the port of mini-os to ia64. Signed-off-by: Dietmar Hahn diff -r d7f7021902a2 -r 3e3e92fb854a extras/mini-os/arch/ia64/Makefile --- /dev/null Thu Jan 1 00:00:00 1970 +0000 +++ b/extras/mini-os/arch/ia64/Makefile Tue Feb 6 07:41:50 2007 +0100 @@ -0,0 +1,60 @@ + + +include arch.mk +include ../../minios.mk + +ARCH_SRCS := sal.c +ARCH_SRCS += efi.c +ARCH_SRCS += acpi.c +ARCH_SRCS += time.c +ARCH_SRCS += ivt.S +ARCH_SRCS += fw.S +ARCH_SRCS += common.c +ARCH_SRCS += time.c +ARCH_SRCS += mm.c +ARCH_SRCS += debug.c +ARCH_SRCS += sched.c +ARCH_SRCS += xencomm.c +ARCH_SRCS += __umoddi3.S +ARCH_SRCS += __udivdi3.S +ARCH_SRCS += __divdi3.S + +ARCH_OBJS := sal.o +ARCH_OBJS += efi.o +ARCH_OBJS += acpi.o +ARCH_OBJS += time.o +ARCH_OBJS += ivt.o +ARCH_OBJS += fw.o +ARCH_OBJS += common.o +ARCH_OBJS += time.o +ARCH_OBJS += mm.o +ARCH_OBJS += debug.o +ARCH_OBJS += sched.o +ARCH_OBJS += xencomm.o +ARCH_OBJS += __umoddi3.o +ARCH_OBJS += __udivdi3.o +ARCH_OBJS += __divdi3.o + +GEN_OFF_SRC := gen_off.c +GEN_OFF_BIN := gen_off +GEN_OFF_H := $(ARCH_SPEC_INC)/offsets.h + +all: $(ARCH_LIB) + +$(GEN_OFF_BIN): $(GEN_OFF_SRC) + $(CC) -o $@ $(CPPFLAGS) $< + +$(GEN_OFF_H): $(GEN_OFF_BIN) + ./$(GEN_OFF_BIN) > $(GEN_OFF_H) + +$(ARCH_LIB): $(GEN_OFF_H) $(ARCH_OBJS) $(HEAD_ARCH_OBJ) + $(AR) rv $(ARCH_LIB) $(ARCH_OBJS) + + + +clean: + rm -f $(ARCH_LIB) $(ARCH_OBJS) + rm -f $(GEN_OFF_BIN) + rm -f $(GEN_OFF_H) + + diff -r d7f7021902a2 -r 3e3e92fb854a extras/mini-os/arch/ia64/__divdi3.S --- /dev/null Thu Jan 1 00:00:00 1970 +0000 +++ b/extras/mini-os/arch/ia64/__divdi3.S Tue Feb 6 07:41:50 2007 +0100 @@ -0,0 +1,141 @@ +.file "__divdi3.s" + +// $FreeBSD: src/sys/libkern/ia64/__divdi3.S,v 1.1 2000/10/04 17:53:03 dfr Exp $ +// +// Copyright (c) 2000, Intel Corporation +// All rights reserved. +// +// Contributed 2/15/2000 by Marius Cornea, John Harrison, Cristina Iordache, +// Ted Kubaska, Bob Norin, and Shane Story of the Computational Software Lab, +// Intel Corporation. +// +// WARRANTY DISCLAIMER +// +// THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS +// "AS IS" AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT +// LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR +// A PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL INTEL OR ITS +// CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, +// EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED TO, +// PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, DATA, OR +// PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY +// OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY OR TORT (INCLUDING +// NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF THIS +// SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE. +// +// Intel Corporation is the author of this code, and requests that all +// problem reports or change requests be submitted to it directly at +// http://developer.intel.com/opensource. +// + +.section .text +.proc __divdi3# +.align 32 +.global __divdi3# +.align 32 + +// 64-bit signed integer divide + +__divdi3: + +{ .mii + alloc r31=ar.pfs,2,0,0,0 + nop.i 0 + nop.i 0;; +} { .mmi + + // 64-BIT SIGNED INTEGER DIVIDE BEGINS HERE + + setf.sig f8=r32 + setf.sig f9=r33 + nop.i 0;; +} { .mfb + nop.m 0 + fcvt.xf f6=f8 + nop.b 0 +} { .mfb + nop.m 0 + fcvt.xf f7=f9 + nop.b 0;; +} { .mfi + nop.m 0 + // Step (1) + // y0 = 1 / b in f8 + frcpa.s1 f8,p6=f6,f7 + nop.i 0;; +} { .mfi + nop.m 0 + // Step (2) + // e0 = 1 - b * y0 in f9 + (p6) fnma.s1 f9=f7,f8,f1 + nop.i 0 +} { .mfi + nop.m 0 + // Step (3) + // q0 = a * y0 in f10 + (p6) fma.s1 f10=f6,f8,f0 + nop.i 0;; +} { .mfi + nop.m 0 + // Step (4) + // e1 = e0 * e0 in f11 + (p6) fma.s1 f11=f9,f9,f0 + nop.i 0 +} { .mfi + nop.m 0 + // Step (5) + // q1 = q0 + e0 * q0 in f10 + (p6) fma.s1 f10=f9,f10,f10 + nop.i 0;; +} { .mfi + nop.m 0 + // Step (6) + // y1 = y0 + e0 * y0 in f8 + (p6) fma.s1 f8=f9,f8,f8 + nop.i 0;; +} { .mfi + nop.m 0 + // Step (7) + // q2 = q1 + e1 * q1 in f9 + (p6) fma.s1 f9=f11,f10,f10 + nop.i 0;; +} { .mfi + nop.m 0 + // Step (8) + // y2 = y1 + e1 * y1 in f8 + (p6) fma.s1 f8=f11,f8,f8 + nop.i 0;; +} { .mfi + nop.m 0 + // Step (9) + // r2 = a - b * q2 in f10 + (p6) fnma.s1 f10=f7,f9,f6 + nop.i 0;; +} { .mfi + nop.m 0 + // Step (10) + // q3 = q2 + r2 * y2 in f8 + (p6) fma.s1 f8=f10,f8,f9 + nop.i 0;; +} { .mfb + nop.m 0 + // Step (11) + // q = trunc (q3) + fcvt.fx.trunc.s1 f8=f8 + nop.b 0;; +} { .mmi + // quotient will be in r8 (if b != 0) + getf.sig r8=f8 + nop.m 0 + nop.i 0;; +} + + // 64-BIT SIGNED INTEGER DIVIDE ENDS HERE + +{ .mmb + nop.m 0 + nop.m 0 + br.ret.sptk b0;; +} + +.endp __divdi3 diff -r d7f7021902a2 -r 3e3e92fb854a extras/mini-os/arch/ia64/__udivdi3.S --- /dev/null Thu Jan 1 00:00:00 1970 +0000 +++ b/extras/mini-os/arch/ia64/__udivdi3.S Tue Feb 6 07:41:50 2007 +0100 @@ -0,0 +1,142 @@ +.file "__udivdi3.s" + +// $FreeBSD: src/sys/libkern/ia64/__udivdi3.S,v 1.1 2000/10/04 17:53:03 dfr Exp $ +// +// Copyright (c) 2000, Intel Corporation +// All rights reserved. +// +// Contributed 2/15/2000 by Marius Cornea, John Harrison, Cristina Iordache, +// Ted Kubaska, Bob Norin, and Shane Story of the Computational Software Lab, +// Intel Corporation. +// +// WARRANTY DISCLAIMER +// +// THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS +// "AS IS" AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT +// LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR +// A PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL INTEL OR ITS +// CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, +// EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED TO, +// PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, DATA, OR +// PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY +// OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY OR TORT (INCLUDING +// NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF THIS +// SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE. +// +// Intel Corporation is the author of this code, and requests that all +// problem reports or change requests be submitted to it directly at +// http://developer.intel.com/opensource. +// + +.section .text +.proc __udivdi3# +.align 32 +.global __udivdi3# +.align 32 + +// 64-bit unsigned integer divide + +__udivdi3: + +{ .mii + alloc r31=ar.pfs,2,0,0,0 + nop.i 0 + nop.i 0;; +} + +{ .mmi + + // 64-BIT UNSIGNED INTEGER DIVIDE BEGINS HERE + + setf.sig f8=r32 + setf.sig f9=r33 + nop.i 0;; +} { .mfb + nop.m 0 + fma.s1 f6=f8,f1,f0 + nop.b 0 +} { .mfb + nop.m 0 + fma.s1 f7=f9,f1,f0 + nop.b 0;; +} { .mfi + nop.m 0 + // Step (1) + // y0 = 1 / b in f8 + frcpa.s1 f8,p6=f6,f7 + nop.i 0;; +} { .mfi + nop.m 0 + // Step (2) + // e0 = 1 - b * y0 in f9 + (p6) fnma.s1 f9=f7,f8,f1 + nop.i 0 +} { .mfi + nop.m 0 + // Step (3) + // q0 = a * y0 in f10 + (p6) fma.s1 f10=f6,f8,f0 + nop.i 0;; +} { .mfi + nop.m 0 + // Step (4) + // e1 = e0 * e0 in f11 + (p6) fma.s1 f11=f9,f9,f0 + nop.i 0 +} { .mfi + nop.m 0 + // Step (5) + // q1 = q0 + e0 * q0 in f10 + (p6) fma.s1 f10=f9,f10,f10 + nop.i 0;; +} { .mfi + nop.m 0 + // Step (6) + // y1 = y0 + e0 * y0 in f8 + (p6) fma.s1 f8=f9,f8,f8 + nop.i 0;; +} { .mfi + nop.m 0 + // Step (7) + // q2 = q1 + e1 * q1 in f9 + (p6) fma.s1 f9=f11,f10,f10 + nop.i 0;; +} { .mfi + nop.m 0 + // Step (8) + // y2 = y1 + e1 * y1 in f8 + (p6) fma.s1 f8=f11,f8,f8 + nop.i 0;; +} { .mfi + nop.m 0 + // Step (9) + // r2 = a - b * q2 in f10 + (p6) fnma.s1 f10=f7,f9,f6 + nop.i 0;; +} { .mfi + nop.m 0 + // Step (10) + // q3 = q2 + r2 * y2 in f8 + (p6) fma.s1 f8=f10,f8,f9 + nop.i 0;; +} { .mfb + nop.m 0 + // (11) q = trunc(q3) + fcvt.fxu.trunc.s1 f8=f8 + nop.b 0;; +} { .mmi + // quotient will be in r8 (if b != 0) + getf.sig r8=f8 + nop.m 0 + nop.i 0;; +} + + // 64-BIT UNSIGNED INTEGER DIVIDE ENDS HERE + +{ .mmb + nop.m 0 + nop.m 0 + br.ret.sptk b0;; +} + +.endp __udivdi3 diff -r d7f7021902a2 -r 3e3e92fb854a extras/mini-os/arch/ia64/__umoddi3.S --- /dev/null Thu Jan 1 00:00:00 1970 +0000 +++ b/extras/mini-os/arch/ia64/__umoddi3.S Tue Feb 6 07:41:50 2007 +0100 @@ -0,0 +1,154 @@ +.file "__umoddi3.s" + +// $FreeBSD: src/sys/libkern/ia64/__umoddi3.S,v 1.3 2003/02/11 20:15:11 schweikh Exp $ +// +// Copyright (c) 2000, Intel Corporation +// All rights reserved. +// +// Contributed 2/15/2000 by Marius Cornea, John Harrison, Cristina Iordache, +// Ted Kubaska, Bob Norin, and Shane Story of the Computational Software Lab, +// Intel Corporation. +// +// WARRANTY DISCLAIMER +// +// THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS +// "AS IS" AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT +// LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR +// A PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL INTEL OR ITS +// CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, +// EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED TO, +// PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, DATA, OR +// PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY +// OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY OR TORT (INCLUDING +// NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF THIS +// SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE. +// +// Intel Corporation is the author of this code, and requests that all +// problem reports or change requests be submitted to it directly at +// http://developer.intel.com/opensource. +// + +.section .text + + // 64-bit unsigned integer remainder + +.proc __umoddi3# +.align 32 +.global __umoddi3# +.align 32 + +__umoddi3: + +{ .mii + alloc r31=ar.pfs,3,0,0,0 + nop.i 0 + nop.i 0 +} { .mmb + + // 64-BIT UNSIGNED INTEGER REMAINDER BEGINS HERE + + // general register used: + // r32 - 64-bit unsigned integer dividend, called a below + // r33 - 64-bit unsigned integer divisor, called b below + // r8 - 64-bit unsigned integer result + // floating-point registers used: f6, f7, f8, f9, f10, f11, f12 + // predicate registers used: p6 + + setf.sig f12=r32 // holds a in integer form + setf.sig f7=r33 + nop.b 0;; +} { .mfi + // get 2s complement of b + sub r33=r0,r33 + fcvt.xuf.s1 f6=f12 + nop.i 0 +} { .mfi + nop.m 0 + fcvt.xuf.s1 f7=f7 + nop.i 0;; +} { .mfi + nop.m 0 + // Step (1) + // y0 = 1 / b in f8 + frcpa.s1 f8,p6=f6,f7 + nop.i 0;; +} { .mfi + nop.m 0 + // Step (2) + // q0 = a * y0 in f10 + (p6) fma.s1 f10=f6,f8,f0 + nop.i 0 +} { .mfi + nop.m 0 + // Step (3) + // e0 = 1 - b * y0 in f9 + (p6) fnma.s1 f9=f7,f8,f1 + nop.i 0;; +} { .mfi + nop.m 0 + // Step (4) + // q1 = q0 + e0 * q0 in f10 + (p6) fma.s1 f10=f9,f10,f10 + nop.i 0 +} { .mfi + nop.m 0 + // Step (5) + // e1 = e0 * e0 in f11 + (p6) fma.s1 f11=f9,f9,f0 + nop.i 0;; +} { .mfi + nop.m 0 + // Step (6) + // y1 = y0 + e0 * y0 in f8 + (p6) fma.s1 f8=f9,f8,f8 + nop.i 0;; +} { .mfi + nop.m 0 + // Step (7) + // q2 = q1 + e1 * q1 in f9 + (p6) fma.s1 f9=f11,f10,f10 + nop.i 0;; +} { .mfi + nop.m 0 + // Step (8) + // y2 = y1 + e1 * y1 in f8 + (p6) fma.s1 f8=f11,f8,f8 + nop.i 0;; +} { .mfi + nop.m 0 + // Step (9) + // r2 = a - b * q2 in f10 + (p6) fnma.s1 f10=f7,f9,f6 + nop.i 0;; +} { .mfi + // f7=-b + setf.sig f7=r33 + // Step (10) + // q3 = q2 + r2 * y2 in f8 + (p6) fma.s1 f8=f10,f8,f9 + nop.i 0;; +} { .mfi + nop.m 0 + // (11) q = trunc(q3) + fcvt.fxu.trunc.s1 f8=f8 + nop.i 0;; +} { .mfi + nop.m 0 + // (12) r = a + (-b) * q + xma.l f8=f8,f7,f12 + nop.i 0;; +} { .mib + getf.sig r8=f8 + nop.i 0 + nop.b 0 +} + + // 64-BIT UNSIGNED INTEGER REMAINDER ENDS HERE + +{ .mib + nop.m 0 + nop.i 0 + br.ret.sptk b0;; +} + +.endp __umoddi3 diff -r d7f7021902a2 -r 3e3e92fb854a extras/mini-os/arch/ia64/acpi.c --- /dev/null Thu Jan 1 00:00:00 1970 +0000 +++ b/extras/mini-os/arch/ia64/acpi.c Tue Feb 6 07:41:50 2007 +0100 @@ -0,0 +1,218 @@ +/* + * The code is mostly from FreeBSD acpica/madt.c. + * Changes: Dietmar Hahn + */ + +/*- + * Copyright (c) 2001 Doug Rabson + * All rights reserved. + * + * Redistribution and use in source and binary forms, with or without + * modification, are permitted provided that the following conditions + * are met: + * 1. Redistributions of source code must retain the above copyright + * notice, this list of conditions and the following disclaimer. + * 2. Redistributions in binary form must reproduce the above copyright + * notice, this list of conditions and the following disclaimer in the + * documentation and/or other materials provided with the distribution. + * + * THIS SOFTWARE IS PROVIDED BY THE AUTHOR AND CONTRIBUTORS ``AS IS'' AND + * ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE + * IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE + * ARE DISCLAIMED. IN NO EVENT SHALL THE AUTHOR OR CONTRIBUTORS BE LIABLE + * FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL + * DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS + * OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) + * HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT + * LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY + * OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF + * SUCH DAMAGE. + * + */ + + +#include "os.h" +#include "acpi.h" + + +uint64_t ia64_lapic_address; + +static void +print_entry(APIC_HEADER *entry) +{ + + switch (entry->Type) { + case APIC_XRUPT_OVERRIDE: { + MADT_INTERRUPT_OVERRIDE *iso = + (MADT_INTERRUPT_OVERRIDE *)entry; + printk("\tInterrupt source override entry\n"); + printk("\t\tBus=%d, Source=%d, Irq=0x%x\n", iso->Bus, + iso->Source, iso->Interrupt); + break; + } + + case APIC_IO: + printk("\tI/O APIC entry\n"); + break; + + case APIC_IO_SAPIC: { + MADT_IO_SAPIC *sapic = (MADT_IO_SAPIC *)entry; + printk("\tI/O SAPIC entry\n"); + printk("\t\tId=0x%x, InterruptBase=0x%x, Address=0x%lx\n", + sapic->IoSapicId, sapic->InterruptBase, + sapic->Address); + break; + } + + case APIC_LOCAL_NMI: + printk("\tLocal APIC NMI entry\n"); + break; + + case APIC_ADDRESS_OVERRIDE: { + MADT_ADDRESS_OVERRIDE *lapic = (MADT_ADDRESS_OVERRIDE *)entry; + printk("\tLocal APIC override entry\n"); + printk("\t\tLocal APIC address=0x%jx\n", lapic->Address); + break; + } + + case APIC_LOCAL_SAPIC: { + MADT_LOCAL_SAPIC *sapic = (MADT_LOCAL_SAPIC *)entry; + printk("\tLocal SAPIC entry\n"); + printk("\t\tProcessorId=0x%x, Id=0x%x, Eid=0x%x", + sapic->ProcessorId, sapic->LocalSapicId, + sapic->LocalSapicEid); + if (!sapic->ProcessorEnabled) + printk(" (disabled)"); + printk("\n"); + break; + } + + case APIC_NMI: + printk("\tNMI entry\n"); + break; + + case APIC_XRUPT_SOURCE: { + MADT_INTERRUPT_SOURCE *pis = (MADT_INTERRUPT_SOURCE *)entry; + printk("\tPlatform interrupt entry\n"); + printk("\t\tPolarity=%d, TriggerMode=%d, Id=0x%x, " + "Eid=0x%x, Vector=0x%x, Irq=%d\n", + pis->Polarity, pis->TriggerMode, + pis->ProcessorId, pis->ProcessorEid, + pis->IoSapicVector, pis->Interrupt); + break; + } + + case APIC_PROCESSOR: + printk("\tLocal APIC entry\n"); + break; + + default: + printk("\tUnknown type %d entry\n", entry->Type); + break; + } +} + +void +ia64_probe_sapics(void) +{ + ACPI_POINTER rsdp_ptr; + APIC_HEADER *entry; + MULTIPLE_APIC_TABLE *table; + RSDP_DESCRIPTOR *rsdp; + XSDT_DESCRIPTOR_REV2 *xsdt; + char *end, *p; + int t, tables; + + if (bootverbose) + printk("Parsing ACPI tables:\n"); + rsdp_ptr.PointerType = ACPI_PHYSICAL_POINTER; + rsdp_ptr.Pointer.Physical = machineFwG.ia64_efi_acpi20_table; + + rsdp = (RSDP_DESCRIPTOR *)IA64_PHYS_TO_RR7(rsdp_ptr.Pointer.Physical); + xsdt = (XSDT_DESCRIPTOR_REV2 *)IA64_PHYS_TO_RR7(rsdp->XsdtPhysicalAddress); + + tables = (UINT64 *)((char *)xsdt + xsdt->Length) - + xsdt->TableOffsetEntry; + + for (t = 0; t < tables; t++) + { + table = (MULTIPLE_APIC_TABLE *) + IA64_PHYS_TO_RR7(xsdt->TableOffsetEntry[t]); + + if (bootverbose) + printk(" Table '%c%c%c%c' at %p\n", + table->Signature[0], table->Signature[1], + table->Signature[2], table->Signature[3], table); + + if (strncmp(table->Signature, APIC_SIG, 4) != 0) + { + printk(" Table not supported: %c%c%c%c\n", + table->Signature[0], table->Signature[1], + table->Signature[2], table->Signature[3]); + continue; + } + /* + * TODO + if(ACPI_FAILURE(AcpiTbVerifyTableChecksum((void *)table))) + { + printk(" Table checksum failed\n"); + continue; + } + */ + + /* Save the address of the processor interrupt block. */ + if (bootverbose) + printk("\tLocal APIC address=0x%x\n", + table->LocalApicAddress); + ia64_lapic_address = table->LocalApicAddress; + + end = (char *)table + table->Length; + p = (char *)(table + 1); + while (p < end) { + entry = (APIC_HEADER *)p; + + if (bootverbose) + print_entry(entry); + + switch (entry->Type) { + case APIC_IO_SAPIC: { + /* + * TODO + MADT_IO_SAPIC *sapic = (MADT_IO_SAPIC *)entry; + sapic_create(sapic->IoSapicId, + sapic->InterruptBase, sapic->Address); + */ + break; + } + + case APIC_ADDRESS_OVERRIDE: { + MADT_ADDRESS_OVERRIDE *lapic = + (MADT_ADDRESS_OVERRIDE*)entry; + ia64_lapic_address = lapic->Address; + break; + } + + case APIC_LOCAL_SAPIC: { +#ifdef SMP + /* TODO */ + MADT_LOCAL_SAPIC *sapic = + (MADT_LOCAL_SAPIC *)entry; + if (sapic->ProcessorEnabled) + cpu_mp_add(sapic->ProcessorId, + sapic->LocalSapicId, + sapic->LocalSapicEid); +#endif + break; + } + + default: + printk("unknown entry type: %d\n", entry->Type); + break; + } + + p += entry->Length; + } + } +} + + diff -r d7f7021902a2 -r 3e3e92fb854a extras/mini-os/arch/ia64/arch.mk --- /dev/null Thu Jan 1 00:00:00 1970 +0000 +++ b/extras/mini-os/arch/ia64/arch.mk Tue Feb 6 07:41:50 2007 +0100 @@ -0,0 +1,12 @@ + +ARCH_CFLAGS := -mfixed-range=f2-f5,f12-f15,f32-f127 -mconstant-gp +ARCH_CFLAGS += -O2 +ARCH_ASFLAGS := -x assembler-with-cpp +ARCH_ASFLAGS += -mfixed-range=f2-f5,f12-f15,f32-f127 -fomit-frame-pointer +ARCH_ASFLAGS += -fno-builtin -fno-common -fno-strict-aliasing -mconstant-gp + +#ARCH_LINKS = ia64_links +#define arch_links +#[ -e include/ia64/asm-xsi-offsets.h ] || ln -sf ../../../../xen/include/asm-ia64/asm-xsi-offsets.h include/ia64/asm-xsi-offsets.h +#endef + diff -r d7f7021902a2 -r 3e3e92fb854a extras/mini-os/arch/ia64/common.c --- /dev/null Thu Jan 1 00:00:00 1970 +0000 +++ b/extras/mini-os/arch/ia64/common.c Tue Feb 6 07:41:50 2007 +0100 @@ -0,0 +1,251 @@ +/* + * Done by Dietmar Hahn + * + **************************************************************************** + * + * Redistribution and use in source and binary forms, with or without + * modification, are permitted provided that the following conditions + * are met: + * 1. Redistributions of source code must retain the above copyright + * notice, this list of conditions and the following disclaimer. + * 2. Redistributions in binary form must reproduce the above copyright + * notice, this list of conditions and the following disclaimer in the + * documentation and/or other materials provided with the distribution. + * + * THIS SOFTWARE IS PROVIDED BY THE AUTHOR AND CONTRIBUTORS ``AS IS'' AND + * ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE + * IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE + * ARE DISCLAIMED. IN NO EVENT SHALL THE AUTHOR OR CONTRIBUTORS BE LIABLE + * FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL + * DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS + * OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) + * HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT + * LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY + * OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF + * SUCH DAMAGE. + * + **************************************************************************** + * + * Parts are taken from FreeBSD. + * + */ + + +/* + * "Physically" memory layout for mini-os given from xen: + * Xen provides the configured physically memory for the mini-os. But some + * parts are reserved for special areas: + * 12KB: the bootinfo, efi and pal stuff. + * - (configMem - 3 pages): The memory usable for mini-os. + * This includes the kernel code and data. + * 3 pages at the end: 1 for xenbus, 1 for console and 1 for start_info. + */ + + +#include "os.h" +#include "types.h" +#include "lib.h" +#include "page.h" +#include "xen/xen.h" +#include "privop.h" +#include "xen/callback.h" +#include "ia64_cpu.h" +#include "hypervisor.h" +#include "events.h" +#include "console.h" +#include "time.h" +#include "xmalloc.h" + + + /* For more console messages. */ +int bootverbose = 0; + +/* + * This structure contains start-of-day info, such as pagetable base pointer, + * address of the shared_info structure, and things like that. + */ +union start_info_union start_info_union; + + +shared_info_t *HYPERVISOR_shared_info = (shared_info_t *)XSI_BASE; + +struct machine_fw machineFwG; + + +struct xen_ia64_boot_param ia64BootParamG; +char boot_cmd_line[COMMAND_LINE_SIZE+1]; + + +void +ia64_write_itr_i(ia64_pte_t* pteP, u32 reg, uint64_t vAddr, + uint64_t ps, uint64_t pk) +{ + /* The virtual address. */ + __asm __volatile("mov cr.ifa=%0" :: "r"(vAddr)); + /* The page size */ + __asm __volatile("mov cr.itir=%0;;" :: "r"((ps << IA64_ITIR_PS)|(pk << IA64_ITIR_KEY))); + /* Put pte into instruction translation register. */ + __asm __volatile("itr.i itr[%0]=%1" :: "r"(reg), "r"(*(uint64_t*)pteP)); + /* Serialization */ + __asm __volatile("srlz.i"); +} + +void +map_pal_code(void) +{ + ia64_pte_t pte; + xen_set_virtual_psr_ic(0); + memset(&pte, 0, sizeof(pte)); /* Prepare the pte */ + pte.pte_p = 1; /* present bit */ + pte.pte_ma = PTE_MA_WB; /* memory attribute */ + pte.pte_a = 1; /* accessed bit */ + pte.pte_d = 1; /* dirty bit */ + pte.pte_pl = PTE_PL_KERN; /* privilege level */ + pte.pte_ar = PTE_AR_RWX; /* access rights */ + pte.pte_ppn = ((uint64_t) __pa(machineFwG.ia64_pal_base)) >> 14; + pte.pte_ed = 0; /* exception deferral */ + /* Must purge here because a itc/dtc with the same address + * may be in the tlb! */ + ia64_ptc_l(machineFwG.ia64_pal_base, PTE_PS_16K); + ia64_write_itr_i(&pte, IA64_TR_PAL, + (uint64_t) machineFwG.ia64_pal_base, + PTE_PS_16K, 0); + /*PAL_TR_PAGE_SIZE, 0);*/ + xen_set_virtual_psr_ic(1); +} + + +extern char hypervisor_callback; + +static void +registerCallback(void) +{ + struct callback_register event = + { + .type = CALLBACKTYPE_event, + .address = (unsigned long)&hypervisor_callback, + }; + HYPERVISOR_callback_op(CALLBACKOP_register, &event); +} + +static void +init_shared_info(start_info_t* xen_start_info) +{ + shared_info_t *s = HYPERVISOR_shared_info; + + xprintk("xen_init() called: shared_info : %p\n", s); + + /* Make a copy of the start_info structure. This stuff comes + * from the hypervisor - see xen.h. + */ + memcpy((void*)&start_info, (void*)xen_start_info, sizeof(start_info)); + + //xprintk("store_mfn: 0x%lx store_evtchn: %d\n", start_info.store_mfn, start_info.store_evtchn); + //xprintk("Running on Xen! start_info_pfn=0x%lx nr_pages=%ld flags=0x%x\n", + // s->arch.start_info_pfn, start_info.nr_pages, + // start_info.flags); +} + +static void +init_boot_params(void) +{ + /* The boot parameter block in the 1. page + * of the physical memory. + * ia64_boot_paramP is initialised in ia64.S! + */ + memcpy((void*)&ia64BootParamG, (void*)ia64_boot_paramP, + sizeof(struct xen_ia64_boot_param)); + /* Parse the boot command line. + * Currently only a check of bootverbose is done. + */ + /* Copy the boot command line. */ + memset(boot_cmd_line, 0, sizeof(boot_cmd_line)); + strncpy(boot_cmd_line, (char*)__va(ia64BootParamG.command_line), COMMAND_LINE_SIZE); + boot_cmd_line[COMMAND_LINE_SIZE-1]='\n'; + /* Look for bootverbose. */ + bootverbose = 0; + if(strstr(boot_cmd_line, "bootverbose") != NULL) + { + bootverbose=1; + } +} + +void +arch_init(start_info_t *si) +{ + efi_time_t tm; + static int initialized; + + if (initialized) + { + return; + } + + init_shared_info(si); + + init_boot_params(); + + init_efi(); + + map_pal_code(); + + ia64_sal_init(machineFwG.ia64_sal_tableP); + + ia64_probe_sapics(); + + if(! efi_get_time(&tm)) + { + printk("efi_get_time() failed\n"); + } + else + { + printk("EFI-SystemTime: %d.%d.%d %d:%d:%d", + tm.Day, tm.Month, tm.Year, + tm.Hour, tm.Minute, tm.Second); + if(tm.TimeZone == EFI_UNSPECIFIED_TIMEZONE) + { + printk(" Timezone not specified!\n"); + } + else + { + printk(" TimeZone: %d Daylight: 0x%x\n", tm.TimeZone, tm.Daylight); + } + } + + registerCallback(); + initialized = 1; +} + +void +arch_print_info(void) +{ + int major, minor; + //printk("VIRTUAL address of page directory : 0x%lx\n", start_info.pt_base); + //printk("Number of bootstrap p.t. frames : 0x%lx\n", start_info.nr_pt_frames); + //printk("VIRTUAL address of page-frame list: 0x%lx\n", start_info.mfn_list); + //printk("\n"); + + minor = HYPERVISOR_xen_version(XENVER_version, 0); + major = minor >> 16; + minor &= ~0xffffffff; + printk("Running on Xen version: %d.%d\n", major, minor); + + printk("machine addr of shared_info_t : 0x%lx\n", start_info.shared_info); + printk("machine page number of shared page: 0x%lx\n", start_info.store_mfn); + printk("evtchn for store communication : %d\n", start_info.store_evtchn); + printk("MACHINE address of console page: 0x%lx\n", start_info.console.domU.mfn); + printk("evtchn for console messages : %d\n", start_info.console.domU.evtchn); + printk("xen_guest_cmdline : %s\n", boot_cmd_line); + +} + +/* Helperfunction used in gnttab.c. */ +void* +map_frames(unsigned long* frames, unsigned long n) +{ + n = n; + return (void*) __va(frames[0] << PAGE_SHIFT); +} + + + diff -r d7f7021902a2 -r 3e3e92fb854a extras/mini-os/arch/ia64/debug.c --- /dev/null Thu Jan 1 00:00:00 1970 +0000 +++ b/extras/mini-os/arch/ia64/debug.c Tue Feb 6 07:41:50 2007 +0100 @@ -0,0 +1,181 @@ +/* + **************************************************************************** + * Done by Dietmar Hahn trap_num, + ia64_vector_names[tf->trap_num]); + printk(" iip : 0x%.16lx ifa: 0x%.16lx\n", tf->iip, tf->ifa); + printk(" ipsr: 0x%.16lx ifs: 0x%.16lx\n", tf->ipsr, tf->ifs); + printk(" isr : 0x%.16lx\n", tf->isr); + printk(" gp : 0x%.16lx sp : 0x%.16lx\n", tf->gp, tf->sp); + printk(" rp : 0x%.16lx tp : 0x%.16lx\n", tf->b0, tf->tp); + printk(" b6 : 0x%.16lx b7 : 0x%.16lx\n", tf->b6, tf->b7); + printk(" r8 : 0x%.16lx\n", tf->r8); + printk(" bsp : 0x%.16lx\n", tf->bsp); + printk(" r14 : 0x%.16lx r15: 0x%.16lx\n", tf->r14, tf->r15); + printk(" r16 : 0x%.16lx r17: 0x%.16lx\n", tf->r16, tf->r17); + printk(" r18 : 0x%.16lx r19: 0x%.16lx\n", tf->r18, tf->r19); + printk(" r20 : 0x%.16lx r21: 0x%.16lx\n", tf->r20, tf->r21); + printk(" r22 : 0x%.16lx r23: 0x%.16lx\n", tf->r22, tf->r23); + printk(" r24 : 0x%.16lx r25: 0x%.16lx\n", tf->r24, tf->r25); + printk(" r26 : 0x%.16lx r27: 0x%.16lx\n", tf->r26, tf->r27); + printk(" r28 : 0x%.16lx r29: 0x%.16lx\n", tf->r28, tf->r29); + printk(" r30 : 0x%.16lx r31: 0x%.16lx\n", tf->r30, tf->r31); + + __asm __volatile("flushrs;;"); + curIfs = *((ifs_t*)((void*)(&tf->ifs))); + if(! curIfs.v) + { + printk(" ifs.v = 0"); + } + else + { + uint64_t* regP; + uint32_t i; + printk(" cfm.sof: %d cfm.sol: %d\n", curIfs.sof, curIfs.sol); + regP = (uint64_t *)(tf->bsp + tf->ndirty); + for (i = curIfs.sof; i != 0; ) + { + if (i <= (((uint64_t)regP & 0x000001f8) >> 3)) + { + regP -= i; + i = 0; + break; + } + i -= ((uint64_t)regP & 0x000001f8) >> 3; + regP = (uint64_t *)((uint64_t)regP & ~0x000001ff) - 1; + } + for(i=0; i + * The code is partly taken from FreeBSD. + * + *************************************************************************** + * + * Redistribution and use in source and binary forms, with or without + * modification, are permitted provided that the following conditions + * are met: + * 1. Redistributions of source code must retain the above copyright + * notice, this list of conditions and the following disclaimer. + * 2. Redistributions in binary form must reproduce the above copyright + * notice, this list of conditions and the following disclaimer in the + * documentation and/or other materials provided with the distribution. + * + * THIS SOFTWARE IS PROVIDED BY THE AUTHOR AND CONTRIBUTORS ``AS IS'' AND + * ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE + * IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE + * ARE DISCLAIMED. IN NO EVENT SHALL THE AUTHOR OR CONTRIBUTORS BE LIABLE + * FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL + * DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS + * OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) + * HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT + * LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY + * OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF + * SUCH DAMAGE. + * + */ + + +#include "os.h" +#include "efi.h" +#include "page.h" +#include "lib.h" +#include "console.h" + + + /* The implementation is in fw.S. */ +extern uint64_t +ia64_call_efi_func(uint64_t funcP,uint64_t a,uint64_t b,uint64_t c,uint64_t d); + +int +efi_get_time(efi_time_t* tmP) +{ + memset(tmP, 0, sizeof(efi_time_t)); + if((*machineFwG.efi.getTimeF)(tmP, NULL) != EFI_SUCCESS) + { + printk("ef.getTime() failed\n"); + return 1==0; + } + return 0==0; +} + +/* The function compares two efi_guid_t and returns 0 on equality, otherwise 1. + * The first guid, a_le, is always in little endian format!. + */ +static int +efi_guid_cmp(efi_guid_t* a_le, efi_guid_t* b) +{ + return memcmp(a_le, b, sizeof(efi_guid_t)); +} + + +void +init_efi(void) +{ + efi_system_table_t* efiSysTableP; + int mdcnt, i, numConvMem; + efi_memory_descriptor_t *memdP, *mdP; + efi_status_t status; + char fwVendor[100] = "unknown"; + efi_char16_t* fwP; + efi_runtime_services_t* rsP; + + efi_configuration_table_t* confP = (efi_configuration_table_t*)0; + efi_guid_t sal = SAL_SYSTEM_TABLE_GUID; + efi_guid_t acpi = ACPI_TABLE_GUID; + efi_guid_t acpi20 = ACPI_20_TABLE_GUID; + + memset(&machineFwG, 0, sizeof(machineFwG)); + /* Read the efi_system_table. */ + efiSysTableP = (efi_system_table_t*)__va(ia64BootParamG.efi_systab); + machineFwG.efi.efiSysTableP = efiSysTableP; + if(bootverbose) + printk("EfiSystemTable at: %p\n", efiSysTableP); + fwP = (uint16_t*) __va(efiSysTableP->FirmwareVendor); + if (fwP) + { + for (i = 0;i < (int) sizeof(fwVendor) - 1 && *fwP; ++i) + { + fwVendor[i] = *fwP++; + } + fwVendor[i] = '\0'; + } + if(bootverbose) + { + printk(" EFI-FirmwareVendor : %s\n", fwVendor); + printk(" EFI-FirmwareRevision : %d\n", efiSysTableP->FirmwareRevision); + printk(" EFI-SystemTable-Revision : %d.%d\n", + efiSysTableP->Hdr.Revision>>16, + efiSysTableP->Hdr.Revision&0xffff); + } + + rsP = (efi_runtime_services_t*) __va(efiSysTableP->RuntimeServices); + mdcnt = ia64BootParamG.efi_memmap_size / ia64BootParamG.efi_memdesc_size; + memdP = (efi_memory_descriptor_t*) __va(ia64BootParamG.efi_memmap); + + if(bootverbose) + printk("EFI-Memorydescriptors: %d\n", mdcnt); + + for(i=numConvMem=0, mdP = memdP; i < mdcnt; i++, + mdP = NextMemoryDescriptor(mdP, ia64BootParamG.efi_memdesc_size)) + { + /* + * Relocate runtime memory segments for firmware. + */ + if(bootverbose) + { + printk(" %d. Type: %x Attributes: 0x%lx\n", + i, mdP->Type, mdP->Attribute); + printk(" PhysicalStart: 0x%lx NumberOfPages: 0x%lx\n", + mdP->PhysicalStart, mdP->NumberOfPages); + } + switch(mdP->Type) + { + case EfiRuntimeServicesData: + { + if(bootverbose) + printk(" -> EfiRuntimeServicesData\n"); + break; + } + case EfiACPIReclaimMemory: + { + if(bootverbose) + printk(" -> EfiACPIReclaimMemory\n"); + break; + } + case EfiACPIMemoryNVS: + { + if(bootverbose) + printk(" -> EfiACPIMemoryNVS\n"); + break; + } + case EfiConventionalMemory: + { + if(bootverbose) + { + printk(" -> EfiConventionalMemory\n"); + printk(" start: 0x%lx end: 0x%lx\n", + mdP->PhysicalStart, + mdP->PhysicalStart+ + mdP->NumberOfPages*EFI_PAGE_SIZE); + } + if(numConvMem) + { + printk(" !! Currently only one efi memory chunk supported !!!\n"); + break; + } + machineFwG.mach_mem_start = mdP->PhysicalStart; + machineFwG.mach_mem_size = mdP->NumberOfPages*EFI_PAGE_SIZE; + numConvMem++; + break; + } + case EfiMemoryMappedIOPortSpace: + { + if(bootverbose) + printk(" -> EfiMemoryMappedIOPortSpace\n"); + break; + } + case EfiPalCode: + { + machineFwG.ia64_pal_base = __va(mdP->PhysicalStart); + if(bootverbose) + { + printk(" -> EfiPalCode\n"); + printk(" start : %p\n", machineFwG.ia64_pal_base); + } + break; + } + } + /* Look for the runtime efi memory for the firmware. */ + /* I have to setup the VirtualStart address of every + * RUNTIME-area in preparing the later call of + * SetVirtualAddressMap() therewidth the efi stuff uses + * virtual addressing and the efi runtime functions + * may be called directly. + */ + if(mdP->Attribute & EFI_MEMORY_RUNTIME) + { + if(mdP->Attribute & EFI_MEMORY_WB) + { + mdP->VirtualStart = __va(mdP->PhysicalStart); + } + else + { + if (mdP->Attribute & EFI_MEMORY_UC) + printk("efi_init: RuntimeMemory with UC attribute !!!!!!\n"); + /* + mdP->VirtualStart = + IA64_PHYS_TO_RR6(mdP->PhysicalStart); + */ + } + } + } + /* Now switch efi runtime stuff to virtual addressing. */ + status = ia64_call_efi_physical((void*)__va((uint64_t)rsP->SetVirtualAddressMap), + ia64BootParamG.efi_memmap_size, + ia64BootParamG.efi_memdesc_size, + ia64BootParamG.efi_memdesc_version, + ia64BootParamG.efi_memmap); + if(status != EFI_SUCCESS) + { + printk("warning: unable to switch EFI into virtual (status=%lu)\n", status); + return; + } + /* Getting efi function pointer for getEfiTime. */ + machineFwG.efi.getTimeF = (efi_get_time_t)__va((uint64_t)rsP->GetTime); + /* Getting efi function pointer for resetSystem. */ + machineFwG.efi.resetSystemF = (efi_reset_system_t)__va((uint64_t)rsP->ResetSystem); + + /* Scanning the Configuration table of the EfiSystemTable. */ + if(bootverbose) + printk("NumberOfConfigTableEntries: %ld\n", efiSysTableP->NumberOfTableEntries); + + confP = (efi_configuration_table_t*) __va(efiSysTableP->ConfigurationTable); + for(i = 0; i < efiSysTableP->NumberOfTableEntries; i++) + { + if(!efi_guid_cmp(&confP[i].VendorGuid, &sal)) + { + machineFwG.ia64_sal_tableP = (sal_system_table_t*) __va((uint64_t) confP[i].VendorTable); + if(bootverbose) + printk(" Found SalSystemTable at: 0x%lx\n", (uint64_t) machineFwG.ia64_sal_tableP); + continue; + } + if(!efi_guid_cmp(&confP[i].VendorGuid, &acpi)) + { + machineFwG.ia64_efi_acpi_table = __va((uint64_t) confP[i].VendorTable); + if(bootverbose) + printk(" Found AcpiTable at: 0x%lx\n", (uint64_t) machineFwG.ia64_efi_acpi_table); + continue; + } + if(!efi_guid_cmp(&confP[i].VendorGuid, &acpi20)) + { + machineFwG.ia64_efi_acpi20_table = __va((uint64_t) confP[i].VendorTable); + if(bootverbose) + printk(" Found Acpi20Table at: 0x%lx\n", (uint64_t) machineFwG.ia64_efi_acpi20_table); + continue; + } + //printk(" Not used table found\n"); + } +} + diff -r d7f7021902a2 -r 3e3e92fb854a extras/mini-os/arch/ia64/fw.S --- /dev/null Thu Jan 1 00:00:00 1970 +0000 +++ b/extras/mini-os/arch/ia64/fw.S Tue Feb 6 07:41:50 2007 +0100 @@ -0,0 +1,481 @@ +/* + * Done by Dietmar Hahn + * Most stuff taken from FreeBSD ia64/ia64/support.S + */ + +/* + * Redistribution and use in source and binary forms, with or without + * modification, are permitted provided that the following conditions + * are met: + * 1. Redistributions of source code must retain the above copyright + * notice, this list of conditions and the following disclaimer. + * 2. Redistributions in binary form must reproduce the above copyright + * notice, this list of conditions and the following disclaimer in the + * documentation and/or other materials provided with the distribution. + * + * THIS SOFTWARE IS PROVIDED BY THE AUTHOR AND CONTRIBUTORS ``AS IS'' AND + * ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE + * IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE + * ARE DISCLAIMED. IN NO EVENT SHALL THE AUTHOR OR CONTRIBUTORS BE LIABLE + * FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL + * DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS + * OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) + * HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT + * LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY + * OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF + * SUCH DAMAGE. + * + */ + + + +#include "asm.h" +#include "page.h" +#include "ia64_cpu.h" +#include "ia64_fpu.h" +#include "offsets.h" + + +/* + * ia64_change_mode: change mode to/from physical mode + * + * Arguments: + * r14 psr for desired mode + * + * Modifies: + * r15-r20 scratch + * ar.bsp translated to new mode + * sp translated to new mode + * iip translated to new mode + */ +ENTRY(ia64_change_mode) + rsm psr.i | psr.ic + mov r19=ar.rsc // save rsc while we change mode + tbit.nz p8,p9=r14,17 // Uses psr.dt-physical or virtual ? + // p8 == true: switch to virtual + // p9 == true: switch to physical + ;; + mov ar.rsc=0 // turn off RSE + mov r16=rp + ;; + flushrs // clean the rse + srlz.i + ;; +1: mov r15=ip + mov r17=ar.bsp + mov r18=ar.rnat + ;; + add r15=2f-1b,r15 // address to rfi to + /* !!! must be the same like in minios-ia64.lds */ +(p8) movl r20=(KERNEL_START - (1< + * + ****************************************************************************** + * + * Redistribution and use in source and binary forms, with or without + * modification, are permitted provided that the following conditions + * are met: + * 1. Redistributions of source code must retain the above copyright + * notice, this list of conditions and the following disclaimer. + * 2. Redistributions in binary form must reproduce the above copyright + * notice, this list of conditions and the following disclaimer in the + * documentation and/or other materials provided with the distribution. + * + * THIS SOFTWARE IS PROVIDED BY THE AUTHOR AND CONTRIBUTORS ``AS IS'' AND + * ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE + * IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE + * ARE DISCLAIMED. IN NO EVENT SHALL THE AUTHOR OR CONTRIBUTORS BE LIABLE + * FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL + * DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS + * OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) + * HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT + * LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY + * OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF + * SUCH DAMAGE. + * + */ + +#include +#include +#include +#include "types.h" +#include "sched.h" +#include "xen/xen.h" +#include "xen/arch-ia64.h" + +#define SZ(st,e) sizeof(((st *)0)->e) +#define OFF(st,e,d,o) print_define(fp, #d, offsetof(st, e) + o, SZ(st, e)) +#define TFOFF(e,d) OFF(trap_frame_t, e, d, 0) +#define SIZE(st,d) fprintf(fp, "#define %-30s\t0x%016lx\n", #d, sizeof(st)) + +#define SWOFF(e,d) OFF(struct thread, e, d, 0) + + /* shared_info_t from xen/xen.h */ +#define SI_OFF(e, d) OFF(shared_info_t, e, d,0) + /* mapped_regs_t from xen/arch-ia64.h */ +#define MR_OFF(e, d) OFF(mapped_regs_t, e, d, XMAPPEDREGS_OFS) + +void +print_define(FILE *fp, char *name, uint64_t val, int size) +{ + char ld_name[64]; + char st_name[64]; + char sz_name[64]; + + strcpy(ld_name, name); + strcat(ld_name, "_ld"); + strcpy(st_name, name); + strcat(st_name, "_st"); + strcpy(sz_name, name); + strcat(sz_name, "_sz"); + fprintf(fp, "#define %-30s\t0x%016lx\n", name, val); + fprintf(fp, "#define %-30s\t%u\n", sz_name, size); + switch (size) + { + case 1: + fprintf(fp, "#define %-30s\tld1\n", ld_name); + fprintf(fp, "#define %-30s\tst1\n", st_name); + break; + case 2: + fprintf(fp, "#define %-30s\tld2\n", ld_name); + fprintf(fp, "#define %-30s\tst2\n", st_name); + break; + case 4: + fprintf(fp, "#define %-30s\tld4\n", ld_name); + fprintf(fp, "#define %-30s\tst4\n", st_name); + break; + case 8: + fprintf(fp, "#define %-30s\tld8\n", ld_name); + fprintf(fp, "#define %-30s\tst8\n", st_name); + break; + default: + ; + } + return; +} + + +int +main(int argc, char ** argv) +{ + FILE *fp; + + fp = stdout; + + TFOFF(cfm, TF_CFM); + TFOFF(pfs, TF_PFS); + TFOFF(bsp, TF_BSP); + TFOFF(rnat, TF_RNAT); + TFOFF(csd, TF_CSD); + TFOFF(ccv, TF_CCV); + TFOFF(unat, TF_UNAT); + TFOFF(fpsr, TF_FPSR); + TFOFF(pr, TF_PR); + + TFOFF(sp, TF_SP); + TFOFF(gp, TF_GP); + TFOFF(tp, TF_TP); + + TFOFF(r2, TF_GREG2); + TFOFF(r3, TF_GREG3); + TFOFF(r16, TF_GREG16); + TFOFF(r17, TF_GREG17); + + TFOFF(b0, TF_BREG0); + TFOFF(b6, TF_BREG6); + TFOFF(b7, TF_BREG7); + + TFOFF(f6, TF_FREG6); + TFOFF(f7, TF_FREG7); + + TFOFF(rsc, TF_RSC); + TFOFF(ndirty, TF_NDIRTY); + TFOFF(ssd, TF_SSD); + TFOFF(iip, TF_IIP); + TFOFF(ipsr, TF_IPSR); + TFOFF(ifs, TF_IFS); + TFOFF(trap_num, TF_TRAP_NUM); + + TFOFF(ifa, TF_IFA); + TFOFF(isr, TF_ISR); + TFOFF(iim, TF_IIM); + + SIZE(trap_frame_t, TF_SIZE); + + SIZE(struct thread, SW_SIZE); + SWOFF(regs.unat_b, SW_UNATB); + SWOFF(regs.sp, SW_SP); + SWOFF(regs.rp, SW_RP); + SWOFF(regs.pr, SW_PR); + SWOFF(regs.pfs, SW_PFS); + SWOFF(regs.bsp, SW_BSP); + SWOFF(regs.rnat, SW_RNAT); + SWOFF(regs.lc, SW_LC); + //SWOFF(regs.fpsr, SW_FPSR); + //SWOFF(regs.psr, SW_PSR); + //SWOFF(regs.gp, SW_GP); + SWOFF(regs.unat_a, SW_UNATA); + SWOFF(regs.r4, SW_R4); + SWOFF(regs.r5, SW_R5); + SWOFF(regs.r6, SW_R6); + SWOFF(regs.r7, SW_R7); + SWOFF(regs.b1, SW_B1); + SWOFF(regs.b2, SW_B2); + SWOFF(regs.b3, SW_B3); + SWOFF(regs.b4, SW_B4); + SWOFF(regs.b5, SW_B5); + SWOFF(regs.f2, SW_F2); + SWOFF(regs.f3, SW_F3); + SWOFF(regs.f4, SW_F4); + SWOFF(regs.f5, SW_F5); + + SI_OFF(arch.start_info_pfn, START_INFO_PFN); + MR_OFF(interrupt_mask_addr, XSI_PSR_I_ADDR_OFS); + MR_OFF(interrupt_collection_enabled, XSI_PSR_IC_OFS); + MR_OFF(ipsr, XSI_IPSR_OFS); + MR_OFF(iip, XSI_IIP_OFS); + MR_OFF(ifs, XSI_IFS_OFS); + MR_OFF(ifa, XSI_IFA_OFS); + MR_OFF(iim, XSI_IIM_OFS); + MR_OFF(iim, XSI_IIM_OFS); + MR_OFF(iipa, XSI_IIPA_OFS); + MR_OFF(isr, XSI_ISR_OFS); + MR_OFF(banknum, XSI_BANKNUM_OFS); + MR_OFF(bank1_regs[0], XSI_BANK1_R16_OFS); + MR_OFF(precover_ifs, XSI_PRECOVER_IFS_OFS); + + return(0); +} diff -r d7f7021902a2 -r 3e3e92fb854a extras/mini-os/arch/ia64/ia64.S --- /dev/null Thu Jan 1 00:00:00 1970 +0000 +++ b/extras/mini-os/arch/ia64/ia64.S Tue Feb 6 07:41:50 2007 +0100 @@ -0,0 +1,223 @@ +/* + * Copyright (c) 2007 Dietmar Hahn + * + ***************************************************************************** + * Permission is hereby granted, free of charge, to any person obtaining a copy + * of this software and associated documentation files (the "Software"), to + * deal in the Software without restriction, including without limitation the + * rights to use, copy, modify, merge, publish, distribute, sublicense, and/or + * sell copies of the Software, and to permit persons to whom the Software is + * furnished to do so, subject to the following conditions: + * + * The above copyright notice and this permission notice shall be included in + * all copies or substantial portions of the Software. + * + * THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR + * IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY, + * FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE + * AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER + * LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING + * FROM, OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER + * DEALINGS IN THE SOFTWARE. + */ + + + +#include "asm.h" +#include "page.h" +#include "ia64_cpu.h" +#include "ia64_fpu.h" +#include "privop.h" +#include "offsets.h" + + + + /* Allocate kernel stack area. + * This is used for stack pointer (goes down from kstack+PAGE_SIZE) and + * RSE (goes up from kstack). + */ + .section .data.start,"aw" + .global kstack + .align PAGE_SIZE +kstack: .space KSTACK_PAGES * PAGE_SIZE + + .text + + /* + * Start the kernel. + * r28 points to the address of the boot parameter area, given + * from the bootloader. + * Execution reaches here in physical mode. + */ +ENTRY(_start) + .prologue + .save rp, r0 // terminate unwind chain with a NULL rp + .body + + alloc loc0=ar.pfs,0,1,1,0 + + rsm psr.i | psr.ic + ;; + srlz.i + ;; + + + + /* + * Initialize mini-os region registers: + * Currently only region registers 5 and 7 are used for addressing. + * rr[5] : virtual kernel address space + * rr[7] : directly mapped physically addresses. + */ + movl r2=0< + * Description: ia64 specific trap handling. + * + **************************************************************************** + * Permission is hereby granted, free of charge, to any person obtaining a copy + * of this software and associated documentation files (the "Software"), to + * deal in the Software without restriction, including without limitation the + * rights to use, copy, modify, merge, publish, distribute, sublicense, and/or + * sell copies of the Software, and to permit persons to whom the Software is + * furnished to do so, subject to the following conditions: + * + * The above copyright notice and this permission notice shall be included in + * all copies or substantial portions of the Software. + * + * THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR + * IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY, + * FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE + * AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER + * LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING + * FROM, OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER + * DEALINGS IN THE SOFTWARE. + * + */ + + +#include "asm.h" +#include "page.h" +#include "ia64_cpu.h" +#include "privop.h" +#include "offsets.h" + + +/* General register usage in interrupt handling: + * r16, r17, ... are used for input parameters of sub-routines + * r29: used to access memory which may raise nested TLB fault + * r30: b0 save register + * r31: predicates save register + * p30,p31: used for TLB stuff: (0,1)=data, (1,0)=instruction + */ + + +#define FILL_FP_PAIR(f1, f2, b1, b2) \ + ldf.fill f1=[b1],32 ;\ + ldf.fill f2=[b2],32 ;\ + ;; + +#define SPILL_FP_PAIR(f1, f2, b1, b2) \ + stf.spill [b1]=f1,32 ;\ + stf.spill [b2]=f2,32 ;\ + ;; + +#define FILL_REG_PAIR(r1, r2, b1, b2) \ + ld8.fill r1=[b1],16 ;\ + ld8.fill r2=[b2],16 ;\ + ;; + +#define SPILL_REG_PAIR(r1, r2, b1, b2) \ + .mem.offset 0,0 ;\ + st8.spill [b1]=r1,16 ;\ + .mem.offset 8,0 ;\ + st8.spill [b2]=r2,16 ;\ + ;; + + +/** + * The function does a store of the current processor context + * to the given exception frame address. + * These are some special and the scratch registers for calling + * C-functions later. + * The bspstore will be the same. A clean RSE is made with the + * cover instruction. + * + * The return is done through a jump to the next bundle after ip (r16). + * + * Used register: r16, r18, r19, r20, r21, r22 of bank 0 + * + * @param: r16 ip of the bundle with the jump. + * @param: r18 pointer to the trap frame. + * @param: r23 trap number/err val + * + */ + +ENTRY(save_tf_rse_switch) + + movl r21=XSI_IPSR // XEN !! + movl r22=XSI_IIP // XEN !! + ;; + ld8 r21=[r21] // XEN.ipsr + ld8 r22=[r22];; // XEN.iip + add r19=TF_IPSR,r18 + add r20=TF_IIP,r18 + ;; + st8 [r19]=r21 // store cr.ipsr + st8 [r20]=r22 // store cr.iip + ;; + + //// r16 return jump pointer, r18 - trap frame base, + + add r19=TF_UNAT,r18 + mov r20=ar.unat + ;; + st8 [r19]=r20 // store scratch unat + ;; + + add r19=TF_GP,r18 + add r20=TF_SP,r18 + ;; + st8 [r19]=gp,TF_TP-TF_GP // store gp + st8 [r20]=sp,TF_PR-TF_SP // store sp + mov r21=pr + ;; + st8 [r19]=r13 // store tp + st8 [r20]=r21 // store pr + ;; + add r19=TF_GREG2,r18 // Now first general regs. + add r20=TF_GREG3,r18 + ;; + SPILL_REG_PAIR( r2, r3,r19,r20) + SPILL_REG_PAIR( r8, r9,r19,r20) + SPILL_REG_PAIR(r10,r11,r19,r20) + SPILL_REG_PAIR(r14,r15,r19,r20) + ;; + mov r14=r18 // move trap frame base for bsw + mov r15=r16 // save return address + ;; + //bsw.1 // switch to bank 1 for saving these registers. + movl r30=XSI_BANKNUM // Switch to bank 1. + mov r31=1;; + st4 [r30]=r31 + ;; + /* On XEN the hypervisor has stored the bank 1 registers + * r16-r31. I must reload these registers here to get + * access. + */ + movl r30=XSI_BANK1_R16; + movl r31=XSI_BANK1_R16+8;; + ld8 r16=[r30],16; ld8 r17=[r31],16;; + ld8 r18=[r30],16; ld8 r19=[r31],16;; + ld8 r20=[r30],16; ld8 r21=[r31],16;; + ld8 r22=[r30],16; ld8 r23=[r31],16;; + ld8 r24=[r30],16; ld8 r25=[r31],16;; + ld8 r26=[r30],16; ld8 r27=[r31],16;; + ld8 r28=[r30],16; ld8 r29=[r31],16;; + ld8 r30=[r30]; ld8 r31=[r31];; + + add r2=TF_GREG16,r14 + add r3=TF_GREG17,r14 + ;; + SPILL_REG_PAIR(r16,r17,r2,r3) + SPILL_REG_PAIR(r18,r19,r2,r3) + SPILL_REG_PAIR(r20,r21,r2,r3) + SPILL_REG_PAIR(r22,r23,r2,r3) + SPILL_REG_PAIR(r24,r25,r2,r3) + SPILL_REG_PAIR(r26,r27,r2,r3) + SPILL_REG_PAIR(r28,r29,r2,r3) + SPILL_REG_PAIR(r30,r31,r2,r3) + ;; + //bsw.0 // back to interrupt bank 0 + movl r2=XSI_BANKNUM;; + st4 [r2]=r0 + ;; + mov r18=r14 // restore context pointer + mov r16=r15 // restore return address + ;; + //// r16 return jump pointer, r18 - trap frame base, + add r19=TF_CCV,r18 + add r20=TF_CSD,r18 + mov r21=ar.ccv + mov r22=ar.csd + ;; + st8 [r19]=r21 // ar.ccv + st8 [r20]=r22 // ar.csd + ;; + add r19=TF_SSD,r18 + mov r21=ar.ssd + ;; + st8 [r19]=r21 // ar.ssd + ;; + add r19=TF_FREG6,r18 + add r20=TF_FREG7,r18 + ;; + SPILL_FP_PAIR(f6, f7, r19, r20) + SPILL_FP_PAIR(f8, f9, r19, r20) + SPILL_FP_PAIR(f10, f11, r19, r20) + + add r19=TF_BREG0,r18 // b0, b6, b7 + add r20=TF_BREG6,r18 + mov r21=b0 + mov r22=b6 + ;; + st8 [r19]=r21,TF_BREG7-TF_BREG0 // store b0 + st8 [r20]=r22,16 // store b6 + ;; + mov r21=b7 + ;; + st8 [r19]=r21 // store b7 + + //// r16 return jump pointer, r18 - trap frame base, + + // Read and save RSC, PFS + add r19=TF_PFS,r18 + add r20=TF_RSC,r18 + mov r21=ar.pfs + mov r22=ar.rsc + ;; +{ .mmb + st8 [r19]=r21 // store ar.pfs + st8 [r20]=r22 // store ar.rsc + // Issue cover instruction + cover // must be the last instruction in bundle + //XEN_HYPER_COVER + ;; +} + // Read and save IFS + add r19=TF_IFS,r18 + add r20=TF_CFM,r18 + /* xen special handling for possibly lazy cover */ + movl r8=XSI_PRECOVER_IFS; + ;; + ld8 r21=[r8]; + ;; + st8 [r19]=r21 // store cr.ifs + dep.z r22=r21,0,38 // copy ifm part from ifs.ifm + ;; + st8 [r20]=r22 // store cfm + // RSE in enforced lazy mode + mov ar.rsc=IA64_RSE_LAZY + ;; + // Read and save BSPSTORE and RNAT + add r19=TF_BSP,r18 + add r20=TF_RNAT,r18 + mov r21=ar.bspstore + mov r22=ar.rnat + ;; + st8 [r19]=r21 // store ar.bspstore + st8 [r20]=r22 // store ar.rnat + ;; + // Write new BSPSTORE + //mov r21=ar.bsp + //;; + mov r22=r21 // new bspstore equal to old + ;; + mov ar.bspstore=r22 // the new bspstore + ;; + // Read and save the new BSP for calculating number of dirty regs. + mov r21=ar.bsp + ;; + sub r21=r21,r22 // r21 -> ndirty + add r19=TF_NDIRTY-TF_BSP,r19 // TF_NDIRTY pos in r19 + ;; + st8 [r19]=r21 // store ndirty + ;; + mov ar.rsc=IA64_RSE_EAGER // RSE on again + ;; + add r19=TF_FPSR,r18 + ;; + mov r21=ar.fpsr + ;; + st8 [r19]=r21 // ar.fpsr + ;; + //// r16 return jump pointer, r18 - trap frame base, + // Load the gp with our module __gp + movl gp=__gp + ;; + add r16=16,r16 // for jump to next bundle + ;; + mov b7=r16 + ;; + +{ .mfb + srlz.d + nop 0 + br.sptk b7 + ;; +} + +END(save_tf_rse_switch) + + +/** + * The function reloads the processor context stored in + * save_tf_rse_switch(). + * + * On calling the function the bank 0 must be activ. + * The return is done through a rfi. + * Used register: b7, r16, r18, r19, r20, r21, r22 of bank 0 + * + * @param: r18 pointer to the exception frame + * + */ +ENTRY(restore_tf_rse_switch) + + add r19=TF_IPSR,r18 + add r20=TF_IIP,r18 + ;; + ld8 r21=[r19] // load cr.ipsr + ld8 r22=[r20] // load cr.iip + movl r16=XSI_IPSR // XEN !! + ;; + st8 [r16]=r21,XSI_IIP_OFS-XSI_IPSR_OFS // XEN.ipsr + mov r2=r21 // save for fp stuff below + ;; + st8 [r16]=r22 // XEN.iip + ;; + //// r18 - trap frame base + // Allocate a zero sized frame + alloc r30=ar.pfs,0,0,0,0 // discard current frame + ;; + // calc number of dirty regs and put this into rsc.loardrs + add r19=TF_NDIRTY,r18 + ;; + ld8 r22=[r19] // ndirty + ;; + shl r21=r22,16 // value for ar.rsc + ;; + mov ar.rsc=r21 // setup for loadrs + ;; + // Issue a loadrs instruction +{ .mmi + loadrs // must be the first instruction + ;; + nop 0x0 + nop 0x0 +} + // Restore BSPSTORE from interrupted context + add r19=TF_BSP,r18 + add r20=TF_RNAT,r18 + ;; + ld8 r21=[r19] // load ar.bspstore + ld8 r22=[r20] // load ar.rnat + ;; + mov ar.bspstore=r21 // set ar.bspstore + ;; + // Restore RNAT + mov ar.rnat=r22 // set ar.rnat + ;; + // Restore PFS and IFS + add r19=TF_PFS,r18 + add r20=TF_IFS,r18 + movl r16=XSI_IFS // XEN !! + ;; + ld8 r21=[r19] // load ar.pfs + ld8 r22=[r20] // load cr.ifs + ;; + add r19=TF_RSC,r18 + mov ar.pfs=r21 + st8 [r16]=r22 // XEN.ifs + ;; + // Restore RSC + ld8 r21=[r19] // load ar.rsc + ;; + mov ar.rsc=r21 // set ar.rsc + //// r18 - trap frame base + add r19=TF_GP,r18 + add r20=TF_SP,r18 + ;; + ld8 gp=[r19],TF_TP-TF_GP // load gp + ld8 sp=[r20],TF_PR-TF_SP // load sp + ;; + ld8 r13=[r19] // load tp + ld8 r21=[r20] // load pr + ;; + mov pr=r21,-1 // set pr + ;; + add r19=TF_BREG0,r18 + add r20=TF_BREG6,r18 + ;; + ld8 r21=[r19],TF_BREG7-TF_BREG0 // load b0 + ld8 r22=[r20],16 // load b6 + ;; + mov b0=r21 + mov b6=r22 + ;; + ld8 r21=[r19] // load b7 + ld8 r22=[r20],16 // load b3 + ;; + mov b7=r21 + //// r18 - trap frame base + mov r14=r18 // Save the context pointer + ;; + // bsw.1 + movl r30=XSI_BANKNUM // Switch to bank 1. + mov r31=1;; + st4 [r30]=r31 + ;; + add r2=TF_GREG16,r14 + add r3=TF_GREG17,r14 + ;; + FILL_REG_PAIR(r16,r17,r2,r3) + FILL_REG_PAIR(r18,r19,r2,r3) + FILL_REG_PAIR(r20,r21,r2,r3) + FILL_REG_PAIR(r22,r23,r2,r3) + FILL_REG_PAIR(r24,r25,r2,r3) + FILL_REG_PAIR(r26,r27,r2,r3) + FILL_REG_PAIR(r28,r29,r2,r3) + FILL_REG_PAIR(r30,r31,r2,r3) + + /* On XEN I have to store the bank 1 register into the + * global XSI_... area. + */ + // r16-r31 all now hold bank1 values + movl r2=XSI_BANK1_R16 + movl r3=XSI_BANK1_R16+8 + ;; + .mem.offset 0,0; st8.spill [r2]=r16,16 + .mem.offset 8,0; st8.spill [r3]=r17,16 + ;; + .mem.offset 0,0; st8.spill [r2]=r18,16 + .mem.offset 8,0; st8.spill [r3]=r19,16 + ;; + .mem.offset 0,0; st8.spill [r2]=r20,16 + .mem.offset 8,0; st8.spill [r3]=r21,16 + ;; + .mem.offset 0,0; st8.spill [r2]=r22,16 + .mem.offset 8,0; st8.spill [r3]=r23,16 + ;; + .mem.offset 0,0; st8.spill [r2]=r24,16 + .mem.offset 8,0; st8.spill [r3]=r25,16 + ;; + .mem.offset 0,0; st8.spill [r2]=r26,16 + .mem.offset 8,0; st8.spill [r3]=r27,16 + ;; + .mem.offset 0,0; st8.spill [r2]=r28,16 + .mem.offset 8,0; st8.spill [r3]=r29,16 + ;; + .mem.offset 0,0; st8.spill [r2]=r30,16 + .mem.offset 8,0; st8.spill [r3]=r31,16 + ;; + // bsw.0 + movl r2=XSI_BANKNUM;; + st4 [r2]=r0; + + mov r18=r14 // Move back the context pointer + ;; + add r19=TF_GREG2,r18 + add r20=TF_GREG3,r18 + ;; + FILL_REG_PAIR( r2, r3,r19,r20) + FILL_REG_PAIR( r8, r9,r19,r20) + FILL_REG_PAIR(r10,r11,r19,r20) + FILL_REG_PAIR(r14,r15,r19,r20) + + //// r18 - trap frame base, + + add r19=TF_CCV,r18 + add r20=TF_CSD,r18 + ;; + ld8 r21=[r19] // ar.ccv + ld8 r22=[r20] // ar.csd + ;; + mov ar.ccv=r21 + mov ar.csd=r22 + add r19=TF_SSD,r18 + ;; + ld8 r21=[r19] // ar.ssd + ;; + mov ar.ssd=r21 + add r19=TF_FREG6,r18 + add r20=TF_FREG7,r18 + ;; + FILL_FP_PAIR(f6, f7, r19, r20) + FILL_FP_PAIR(f8, f9, r19, r20) + FILL_FP_PAIR(f10, f11, r19, r20) + add r19=TF_FPSR,r18 + ;; + ld8 r21=[r19] // ar.fpsr + ;; + mov ar.fpsr=r21 + add r19=TF_UNAT,r18 + ;; + ld8 r21=[r19] + ;; + mov ar.unat=r21 + ;; + srlz.i + ;; + //rfi + XEN_HYPER_RFI; + ;; +END(restore_tf_rse_switch) + + +ENTRY(save_special_regs) + alloc loc0=ar.pfs,1,7,0,0 + movl loc1=XSI_IFA // XEN !! + movl loc2=XSI_ISR // XEN !! + ;; + ld8 loc3=[loc1],XSI_IIM_OFS-XSI_IFA_OFS // load XEN.ifa + ld8 loc4=[loc2],XSI_IIPA_OFS-XSI_ISR_OFS // load XEN.isr + add loc5=TF_IFA,in0 + add loc6=TF_ISR,in0 + ;; + st8 [loc5]=loc3,TF_IIM-TF_IFA // store cr.ifa + st8 [loc6]=loc4 // store cr.isr + ;; + ld8 loc3=[loc1] // load XEN.iim + ;; + st8 [loc5]=loc3 // store cr.iim + ;; + mov ar.pfs=loc0 + ;; + br.ret.sptk.few rp + +END(save_special_regs) + + + +ENTRY(hypervisor_callback) + // Calculate the stack address for storing. + // Use the kernel stack here because it's mapped wired! + // -> no nested tlb faults! + movl r18=kstack+KSTACK_PAGES * PAGE_SIZE - 16 - TF_SIZE + + //add r18=-TF_SIZE,sp + add r30=0xabab,r0 + ;; +{ .mib + nop 0x02 + mov r16=ip // for jump back from save_tf_rse_switch + br.sptk save_tf_rse_switch + ;; +} + add sp=-16,r18 // the new stack + alloc r15=ar.pfs,0,0,1,0 // 1 out for do_trap_error + ;; + mov out0=r18 // the trap frame + movl r22=XSI_PSR_IC + mov r23=1;; + st8 [r22]=r23 // ssm psr.ic + ;; + br.call.sptk.few rp = do_hypervisor_callback + + movl r22=XSI_PSR_IC + ;; + st4 [r22]=r0 // rsm psr.ic + + add r16=16,sp // load EF-pointer again + ;; + //mov r18=sp + movl r18=kstack+KSTACK_PAGES * PAGE_SIZE - 16 - TF_SIZE + ;; + + // must have r18-efp, calls rfi at the end. + br.sptk restore_tf_rse_switch + ;; +END(hypervisor_callback) + + /* + * In: r30 - trap number + */ +ENTRY(trap_error) + + // Calculate the stack address for storing. + add r18=-TF_SIZE,sp + ;; + add r20=TF_TRAP_NUM,r18 + ;; + st2 [r20]=r30 // save trap number + ;; + +{ .mib + nop 0x02 + mov r16=ip // for jumping back from save_tf_rse_switch + // Used register: r16, r18, r19, r20, r21, r22 of bank 0 + br.sptk save_tf_rse_switch + ;; +} + + alloc r15=ar.pfs,0,0,1,0 // 1 out for do_trap_error + ;; + mov out0=r18 // the trap frame + add sp=-16,r18 // C-call abi + ;; + + //bsw.1 + movl r30=XSI_BANKNUM + mov r31=1;; + st4 [r30]=r31;; + + /* Save extra interrupt registers to the trap frame. */ + br.call.sptk.few rp = save_special_regs + ;; + + movl r22=XSI_PSR_IC + movl r23=XSI_PSR_I_ADDR + ;; + ld8 r23=[r23] + mov r25=1 + ;; + st4 [r22]=r25 // ssm psr.ic + st1 [r23]=r0 // ssm psr.i + ;; + + br.call.sptk.few rp = do_trap_error + ;; + // --> currently not reached!!! + movl r23=XSI_PSR_I_ADDR + movl r22=XSI_PSR_IC + ;; + ld8 r23=[r23] + mov r25=1 + ;; + st1 [r23]=r25 + st4 [r22]=r0 // note: clears both vpsr.i and vpsr.ic! + ;; + bsw.0 + ;; + add r18=16,sp // load EF-pointer again + ;; + mov sp=r18 + // must have r18-efp, calls rfi at the end. + br.sptk restore_tf_rse_switch + ;; + +END(trap_error) + + + +/* + * The trap handler stuff. + */ + +#define TRAP_ERR(num) \ + mov r30 = num; \ + ;; ; \ + br.sptk trap_error \ + ;; + +#define IVT_ENTRY(name, offset) \ + .org ia64_trap_table + offset; \ + .global hivt_##name; \ + .proc hivt_##name; \ + .prologue; \ + .body; \ +hivt_##name: + +#define IVT_END(name) \ + .endp hivt_##name; \ + .align 0x100 + +#define IVT_ERR(name, num, offset) \ + IVT_ENTRY(name, offset); \ + TRAP_ERR(num); \ + IVT_END(name) +/* + * The IA64 Interrupt Vector Table (IVT) contains 20 slots with 64 + * bundles per vector and 48 slots with 16 bundles per vector. + */ + + .section .text.hivt,"ax" + .align 32768 + .global ia64_trap_table + .size ia64_trap_table, 32768 +ia64_trap_table: + +IVT_ERR(VHPT_Translation, 0, 0x0) +IVT_ERR(Instruction_TLB, 1, 0x0400) +IVT_ERR(Data_TLB, 2, 0x0800) +IVT_ERR(Alternate_Instruction_TLB, 3, 0x0c00) + + +IVT_ENTRY(Alternate_Data_TLB, 0x1000) + mov r30=4 // trap number + mov r16=cr.ifa // where did it happen + mov r31=pr // save predicates + ;; + extr.u r17=r16,IA64_RR_IDX_POS,3 // get region number + ;; + cmp.eq p14,p15=7,r17 + ;; +//(p14) br.sptk adt_regf_addr // Check for region 7 - phys addresses +// ;; +// br.sptk trap_error +// // No return +// +//adt_regf_addr: +// extr.u r17=r16,60,4 // get region number +// ;; +// cmp.eq p14,p15=0xf,r17 +// ;; +(p14) br.sptk adt_reg7_addr // Check for region 7 - phys addresses + ;; + br.sptk trap_error + +adt_reg7_addr: + /* region 7 addresses are only directly mapped physically + * addresses. Currently I don't do a check. + */ + movl r20=~((7 << IA64_RR_IDX_POS) | 0xfff) + movl r18=((PTE_PS_16K< + * + * Description: Special ia64 memory management. + * Parts are taken from FreeBSD. + * + **************************************************************************** + * + * Permission is hereby granted, free of charge, to any person obtaining a copy + * of this software and associated documentation files (the "Software"), to + * deal in the Software without restriction, including without limitation the + * rights to use, copy, modify, merge, publish, distribute, sublicense, and/or + * sell copies of the Software, and to permit persons to whom the Software is + * furnished to do so, subject to the following conditions: + * + * The above copyright notice and this permission notice shall be included in + * all copies or substantial portions of the Software. + * + * THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR + * IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY, + * FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE + * AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER + * LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING + * FROM, OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER + * DEALINGS IN THE SOFTWARE. + */ + + +#include "os.h" +#include "mm.h" + + + +#define MAX_MEM_AREA 5 +paddr_t phys_avail[MAX_MEM_AREA * 2]; +int phys_avail_cnt; +uint64_t physmem; + +caddr_t pft_start; /* Start of page frame table. */ + + /* These variables are defined in the linker script minios_ia64.lds + * to get the size of the kernel. + */ +extern uint64_t _text[], _etext[], _end[], kstack[], phys_start[]; + +uint64_t kernstart, kernend, kernsize, kernpstart, kernpend; + + +static caddr_t +steal_memory(uint64_t size) +{ + uint64_t bank_size; + paddr_t pa, va; + + size = roundup_page(size); + + bank_size = phys_avail[1] - phys_avail[0]; + while (size > bank_size) + { + int i; + for (i = 0; phys_avail[i+2]; i+= 2) + { + phys_avail[i] = phys_avail[i+2]; + phys_avail[i+1] = phys_avail[i+3]; + } + phys_avail[i] = 0; + phys_avail[i+1] = 0; + if (!phys_avail[0]) + { + printk("steal_memory: out of memory"); + do_exit(); + } + bank_size = phys_avail[1] - phys_avail[0]; + } + + pa = phys_avail[0]; + phys_avail[0] += size; + + va = IA64_PHYS_TO_RR7(pa); + memset((void*) va, 0, size); + return va; +} + +static void +print_phys_avail(void) +{ + int indx; + printk("Physical memory chunk(s):\n"); + for (indx = 0; phys_avail[indx + 1] != 0; indx += 2) + { + int size1 = phys_avail[indx + 1] - phys_avail[indx]; + printk("0x%08lx - 0x%08lx, %d bytes (%d pages)\n", phys_avail[indx], + phys_avail[indx + 1] - 1, size1, size1 / PAGE_SIZE); + } +} + +void +arch_init_mm(unsigned long* start_pfn_p, unsigned long* max_pfn_p) +{ + uint64_t ms, me; + int i, j; + uint64_t m, n; + kernstart = trunc_page(_text); + kernend = roundup_page(_end); + + kernpstart = trunc_page(ia64_tpa(kernstart)); + kernpend = roundup_page(kernpstart + (kernend - kernstart)); + kernsize = kernpend - kernpstart; + + ms = roundup_page(machineFwG.mach_mem_start); + me = trunc_page(machineFwG.mach_mem_start+machineFwG.mach_mem_size); + memset((void*)phys_avail, 0, sizeof(phys_avail)); + /* 1. Check where the kernel lies in physical memory. */ + physmem = me - ms; + if((ms <= kernpend) && (kernpstart <= me)) + { + if(ms < kernpstart) + { /* There is a part before the kernel. */ + if(bootverbose) + { + printk(" Found chunk before kernel: 0x%lx - 0x%lx\n", + ms, kernpstart); + } + phys_avail[phys_avail_cnt] = ms; + phys_avail[phys_avail_cnt+1] = kernpstart; + phys_avail_cnt += 2; + } + if(kernpend < me) + { /* There is a part behind the kernel. */ + if(bootverbose) + { + printk(" Found chunk behind kernel: 0x%lx - 0x%lx\n", + kernpend, me); + } + phys_avail[phys_avail_cnt] = kernpend; + phys_avail[phys_avail_cnt+1] = me; + phys_avail_cnt += 2; + } + } + else + { /* One big chunk */ + if(bootverbose) + printk(" Found big chunk: 0x%lx - 0x%lx\n", ms, me); + phys_avail[phys_avail_cnt] = ms; + phys_avail[phys_avail_cnt+1] = me; + phys_avail_cnt += 2; + } + phys_avail[phys_avail_cnt] = 0; + +/* + printk("kernsize : 0x%lx\n", kernsize); + printk("physmem : 0x%lx\n", physmem); + printk("physPages : 0x%lx\n", physmem / PAGE_SIZE); + printk("kernpstart: 0x%lx\n", kernpstart); + printk("kernpend : 0x%lx\n", kernpend); +*/ + + print_phys_avail(); + /* + * Now I have the usable kernel memory chunks in phys_avail. + * I steal some memory for the page frame table. + */ + /* Reserve memory for page frame table. */ + /* !! Currently not used !! */ + pft_start = (caddr_t) steal_memory(physmem/PAGE_SIZE * + sizeof(struct page)); + /* + * In this first version I only look for the biggest mem area. + */ + for(i=j=m=n=0; i m) + { + m = n; + j = i; + } + } + *start_pfn_p = page_to_pfn(phys_avail[j]); + *max_pfn_p = page_to_pfn(phys_avail[j+1]); +} + +/* Currently only a dummy function on. */ +void +arch_init_demand_mapping_area(unsigned long max_pfn) +{ + max_pfn = max_pfn; +} + + + + + diff -r d7f7021902a2 -r 3e3e92fb854a extras/mini-os/arch/ia64/sal.c --- /dev/null Thu Jan 1 00:00:00 1970 +0000 +++ b/extras/mini-os/arch/ia64/sal.c Tue Feb 6 07:41:50 2007 +0100 @@ -0,0 +1,213 @@ +/* + * Done by Dietmar Hahn + * Mostly taken from FreeBSD. + * + **************************************************************************** + * + * Redistribution and use in source and binary forms, with or without + * modification, are permitted provided that the following conditions + * are met: + * 1. Redistributions of source code must retain the above copyright + * notice, this list of conditions and the following disclaimer. + * 2. Redistributions in binary form must reproduce the above copyright + * notice, this list of conditions and the following disclaimer in the + * documentation and/or other materials provided with the distribution. + * + * THIS SOFTWARE IS PROVIDED BY THE AUTHOR AND CONTRIBUTORS ``AS IS'' AND + * ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE + * IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE + * ARE DISCLAIMED. IN NO EVENT SHALL THE AUTHOR OR CONTRIBUTORS BE LIABLE + * FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL + * DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS + * OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) + * HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT + * LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY + * OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF + * SUCH DAMAGE. + * + */ + +#include "os.h" +#include "lib.h" +#include "console.h" +#include "page.h" + + + +/* This stuff is from smp.h. But we need no smp.h for only 1 cpu. + * Interprocessor interrupts for SMP. The following values are indices + * into the IPI vector table. The SAL gives us the vector used for AP + * wake-up. We base the other vectors on that. Keep IPI_AP_WAKEUP at + * index 0 and IPI_MCA_RENDEZ at index 1. See sal.c for details. + */ +/* Architecture specific IPIs. */ +#define IPI_AP_WAKEUP 0 +#define IPI_HIGH_FP 1 +#define IPI_MCA_CMCV 2 +#define IPI_MCA_RENDEZ 3 +#define IPI_TEST 4 +/* Machine independent IPIs. */ +#define IPI_AST 5 +#define IPI_RENDEZVOUS 6 +#define IPI_STOP 7 + +#define IPI_COUNT 8 + + +/* + * IPIs are used more genericly than only + * for inter-processor interrupts. Don't + * make it a SMP specific thing... + */ +int ipi_vector[IPI_COUNT]; + +static struct ia64_fdesc sal_fdesc; +static sal_entry_t fake_sal; + +uint64_t ia64_pal_entry; /* PAL_PROC entrypoint */ + + +//static sal_entry_t* ia64_sal_entry;/* SAL_PROC entrypoint */ +//sal_entry_t* ia64_sal_entry;/* SAL_PROC entrypoint */ + +struct ia64_sal_result +ia64_sal_call(uint64_t a1, uint64_t a2, uint64_t a3, uint64_t a4, + uint64_t a5, uint64_t a6, uint64_t a7, uint64_t a8) +{ + return ia64_sal_entry(a1, a2, a3, a4, a5, a6, a7, a8); +} + +static struct ia64_sal_result +fake_sal(u_int64_t a1, u_int64_t a2, u_int64_t a3, u_int64_t a4, + u_int64_t a5, u_int64_t a6, u_int64_t a7, u_int64_t a8) +{ + struct ia64_sal_result res; + res.sal_status = -3; + res.sal_result[0] = 0; + res.sal_result[1] = 0; + res.sal_result[2] = 0; + return res; +} + +static void +setup_ipi_vectors(int ceil) +{ + int ipi; + + ipi_vector[IPI_MCA_RENDEZ] = ceil - 0x10; + ipi_vector[IPI_MCA_CMCV] = ceil - 0x30; + ipi_vector[IPI_TEST] = ceil - 0x30 + 1; + + ipi = IPI_AST; /* First generic IPI. */ + ceil -= 0x20; /* First vector in group. */ + while (ipi < IPI_COUNT) + ipi_vector[ipi++] = ceil++; +} + +void +ia64_sal_init(struct sal_system_table *saltab) +{ + static int sizes[6] = { + 48, 32, 16, 32, 16, 16 + }; + u_int8_t *p; + int i; + + if(bootverbose) + printk("Reading SALtable:\n"); + ia64_sal_entry = fake_sal; + + if (memcmp((void*)(uint64_t)(saltab->sal_signature), SAL_SIGNATURE, 4)) { + printk("Bad signature for SAL System Table\n"); + return; + } + p = (u_int8_t *) (saltab + 1); + for (i = 0; i < saltab->sal_entry_count; i++) { + switch (*p) + { + case SAL_DESC_ENTRYPOINT: // 0 + { + struct sal_entrypoint_descriptor *dp; + + dp = (struct sal_entrypoint_descriptor*)p; + ia64_pal_entry = IA64_PHYS_TO_RR7(dp->sale_pal_proc); + if (bootverbose) + printk(" PAL Proc at 0x%lx\n", ia64_pal_entry); + sal_fdesc.func = IA64_PHYS_TO_RR7(dp->sale_sal_proc); + sal_fdesc.gp = IA64_PHYS_TO_RR7(dp->sale_sal_gp); + if (bootverbose) + printk(" SAL Proc at 0x%lx, GP at 0x%lx\n", + sal_fdesc.func, sal_fdesc.gp); + ia64_sal_entry = (sal_entry_t *) &sal_fdesc; + break; + } + case SAL_DESC_AP_WAKEUP: // 5 + { + struct sal_ap_wakeup_descriptor *dp; +#ifdef SMP + struct ia64_sal_result result; +#endif + + dp = (struct sal_ap_wakeup_descriptor*)p; + if (dp->sale_mechanism != 0) { + printk(" SAL: unsupported AP wake-up mechanism " + "(%d)\n", dp->sale_mechanism); + break; + } + + if (dp->sale_vector < 0x10 || dp->sale_vector > 0xff) { + printk(" SAL: invalid AP wake-up vector " + "(0x%lx)\n", dp->sale_vector); + break; + } + + /* + * SAL documents that the wake-up vector should be + * high (close to 255). The MCA rendezvous vector + * should be less than the wake-up vector, but still + * "high". We use the following priority assignment: + * Wake-up: priority of the sale_vector + * Rendezvous: priority-1 + * Generic IPIs: priority-2 + * Special IPIs: priority-3 + * Consequently, the wake-up priority should be at + * least 4 (ie vector >= 0x40). + */ + if (dp->sale_vector < 0x40) { + printk(" SAL: AP wake-up vector too low " + "(0x%lx)\n", dp->sale_vector); + break; + } + + if (bootverbose) + printk(" SAL: AP wake-up vector: 0x%lx\n", + dp->sale_vector); + + ipi_vector[IPI_AP_WAKEUP] = dp->sale_vector; + setup_ipi_vectors(dp->sale_vector & 0xf0); + +#ifdef SMP +#error SMP Currently not supported + /* os_boot_rendez is a assembler routine + * booting the new processor. + * The call is done via IPI_AP_WAKEUP. + */ + result = ia64_sal_entry(SAL_SET_VECTORS, + SAL_OS_BOOT_RENDEZ, + ia64_tpa(FDESC_FUNC(os_boot_rendez)), + ia64_tpa(FDESC_GP(os_boot_rendez)), + 0, 0, 0, 0); +#endif + + break; + } + default: + break; + } + p += sizes[*p]; + } + + if (ipi_vector[IPI_AP_WAKEUP] == 0) + setup_ipi_vectors(0xf0); +} + diff -r d7f7021902a2 -r 3e3e92fb854a extras/mini-os/arch/ia64/sched.c --- /dev/null Thu Jan 1 00:00:00 1970 +0000 +++ b/extras/mini-os/arch/ia64/sched.c Tue Feb 6 07:41:50 2007 +0100 @@ -0,0 +1,74 @@ +/* + * Done by Dietmar Hahn stack = (char *)alloc_pages(1); + _thread->name = name; + memset((void*)&(_thread->regs), 0, sizeof(_thread->regs)); + _thread->regs.sp = ((uint64_t)_thread->stack) + 2*PAGE_SIZE-16; + _thread->regs.bsp = ((uint64_t)_thread->stack) + 0x10; + _thread->regs.rp = FDESC_FUNC(thread_starter); + _thread->regs.pfs = 0x82; + _thread->regs.r4 = FDESC_FUNC(function); + _thread->regs.r6 = (uint64_t)data; + return _thread; +} + +extern void restore_context(struct thread*); +extern int switch_context(struct thread*, struct thread*); +void +arch_switch_threads(struct thread* prev, struct thread* next) +{ + ia64_set_r13((uint64_t)next); + switch_context(prev, next); +} + + /* Everything initialised, start idle thread */ +void +run_idle_thread(void) +{ + ia64_set_r13((uint64_t)idle_thread); + restore_context(idle_thread); + printk("%s: behind restore_context()-should not be reached!\n", __func__); +} + + diff -r d7f7021902a2 -r 3e3e92fb854a extras/mini-os/arch/ia64/time.c --- /dev/null Thu Jan 1 00:00:00 1970 +0000 +++ b/extras/mini-os/arch/ia64/time.c Tue Feb 6 07:41:50 2007 +0100 @@ -0,0 +1,286 @@ +/* + * Done by Dietmar Hahn + * Description: simple ia64 specific time handling + * mktime() is taken from Linux (see copyright below) + * Parts are taken from FreeBSD. + * + **************************************************************************** + * For the copy of the mktime() from linux. + * 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; either version 2 of the License, or + * (at your option) any later version. + * + * 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. + * + * You should have received a copy of the GNU General Public License + * along with this program; if not, write to the Free Software + * Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA + * + **************************************************************************** + * + * Redistribution and use in source and binary forms, with or without + * modification, are permitted provided that the following conditions + * are met: + * 1. Redistributions of source code must retain the above copyright + * notice, this list of conditions and the following disclaimer. + * 2. Redistributions in binary form must reproduce the above copyright + * notice, this list of conditions and the following disclaimer in the + * documentation and/or other materials provided with the distribution. + * + * THIS SOFTWARE IS PROVIDED BY THE AUTHOR AND CONTRIBUTORS ``AS IS'' AND + * ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE + * IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE + * ARE DISCLAIMED. IN NO EVENT SHALL THE AUTHOR OR CONTRIBUTORS BE LIABLE + * FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL + * DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS + * OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) + * HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT + * LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY + * OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF + * SUCH DAMAGE. + */ + +#include "os.h" +#include "console.h" +#include "time.h" +#include "efi.h" +#include "events.h" + +struct timespec os_time; +static uint64_t itc_alt; /* itc on last update. */ +static uint64_t itc_at_boot; /* itc on boot */ +static uint64_t itc_frequency; +static uint64_t processor_frequency; + + +/* mktime() is take from Linux. See copyright above. + * Converts Gregorian date to seconds since 1970-01-01 00:00:00. + * Assumes input in normal date format, i.e. 1980-12-31 23:59:59 + * => year=1980, mon=12, day=31, hour=23, min=59, sec=59. + * + * [For the Julian calendar (which was used in Russia before 1917, + * Britain & colonies before 1752, anywhere else before 1582, + * and is still in use by some communities) leave out the + * -year/100+year/400 terms, and add 10.] + * + * This algorithm was first published by Gauss (I think). + * + * WARNING: this function will overflow on 2106-02-07 06:28:16 on + * machines were long is 32-bit! (However, as time_t is signed, we + * will already get problems at other places on 2038-01-19 03:14:08) + */ +static unsigned long +mktime(const unsigned int year0, const unsigned int mon0, + const unsigned int day, const unsigned int hour, + const unsigned int min, const unsigned int sec) +{ + unsigned int mon = mon0, year = year0; + + /* 1..12 -> 11,12,1..10 */ + if (0 >= (int) (mon -= 2)) { + mon += 12; /* Puts Feb last since it has leap day */ + year -= 1; + } + + return ((((unsigned long) + (year/4 - year/100 + year/400 + 367*mon/12 + day) + + year*365 - 719499 + )*24 + hour /* now have hours */ + )*60 + min /* now have minutes */ + )*60 + sec; /* finally seconds */ +} + +static inline uint64_t +ns_from_cycles(uint64_t cycles) +{ + uint64_t x = 1000000000 / itc_frequency; + return (cycles * x); +} + +static inline uint64_t +ns_to_cycles(uint64_t ns) +{ + uint64_t x = itc_frequency / 1000000000; + return (ns * x); +} + +static uint64_t itm_val; +/* Block the domain until until(nanoseconds) is over. */ +void +block_domain(s_time_t until) +{ + struct ia64_pal_result pal_res; + uint64_t c, new; + + c = ns_to_cycles(until); + new = ia64_get_itc() + c - NOW(); + ia64_set_itm(new); /* Reload cr.itm */ + /* PAL_HALT_LIGHT returns on every external interrupt, + * including timer interrupts. */ + pal_res = ia64_call_pal_static(PAL_HALT_LIGHT, 0, 0, 0); + if(pal_res.pal_status != 0) + { + printk("%s: PAL_HALT_LIGHT returns an error\n"); + } + /* Reload the normal timer interrupt match. */ + new = ia64_get_itc() + itm_val; + ia64_set_itm(new); /* Reload cr.itm */ +} + +static void +calculate_time(void) +{ + uint64_t itc_new, new; + itc_new = ia64_get_itc(); + if(itc_new < itc_alt) + new = ~0 - itc_alt + itc_new; + else new = itc_new - itc_alt; + itc_alt = itc_new; + new = ns_from_cycles(new); + os_time.ts_nsec += new; + if(os_time.ts_nsec > 1000000000) + { /* On overflow. */ + os_time.ts_sec++; + os_time.ts_nsec -= 1000000000; + } +} + +volatile uint64_t numTimerInterrupts = 0; + +void +timer_interrupt(evtchn_port_t port, struct pt_regs* regsP, void *data) +{ + uint64_t new; + data = data; + calculate_time(); + new = ia64_get_itc() + itm_val; + //xprintk("!!!!!!! In timerinterrupt\n"); + ia64_set_itm(new); /* Reload cr.itm */ + numTimerInterrupts++; +} + +/* + * monotonic_clock(): returns # of nanoseconds passed since time_init() + */ +u64 +monotonic_clock(void) +{ + uint64_t delta; + delta = ia64_get_itc() - itc_at_boot; + delta = ns_from_cycles(delta); + return delta; +} + +void +gettimeofday(struct timeval *tv) +{ + calculate_time(); + tv->tv_sec = os_time.ts_sec; /* seconds */ + tv->tv_usec = NSEC_TO_USEC(os_time.ts_nsec); /* microseconds */ +}; + +/* + * Read the clock frequencies from pal and sal for calculating + * the clock interrupt. + */ +//extern sal_entry_t* ia64_sal_entry; +static void +calculate_frequencies(void) +{ + struct ia64_sal_result sal_res; + struct ia64_pal_result pal_res; + + pal_res = ia64_call_pal_static(PAL_FREQ_RATIOS, 0, 0, 0); + sal_res = ia64_sal_entry(SAL_FREQ_BASE, 0, 0, 0, 0, 0, 0, 0); + + if (sal_res.sal_status == 0 && pal_res.pal_status == 0) + { + processor_frequency = + sal_res.sal_result[0] * (pal_res.pal_result[0] >> 32) + / (pal_res.pal_result[0] & ((1L << 32) - 1)); + itc_frequency = + sal_res.sal_result[0] * (pal_res.pal_result[2] >> 32) + / (pal_res.pal_result[2] & ((1L << 32) - 1)); + if (bootverbose) + { + printk("Reading clock frequencies:\n"); + printk(" Platform clock frequency %ld Hz\n", + sal_res.sal_result[0]); + printk(" Processor ratio %ld/%ld, Bus ratio %ld/%ld, " + " ITC ratio %ld/%ld\n", + pal_res.pal_result[0] >> 32, + pal_res.pal_result[0] & ((1L << 32) - 1), + pal_res.pal_result[1] >> 32, + pal_res.pal_result[1] & ((1L << 32) - 1), + pal_res.pal_result[2] >> 32, + pal_res.pal_result[2] & ((1L << 32) - 1)); + } + printk(" ITC frequency %ld\n", itc_frequency); + } + else + { + printk("Reading clock frequencies failed!!! Using default\n"); + processor_frequency = 0; + itc_frequency = 1000000000; + } +} + + +int my_hz = 1000; // 1000 per sec +//int my_hz = 1; +#define HZ my_hz +#define IA64_TIMER_VECTOR 0xef + +void +init_time(void) +{ + uint64_t new; + efi_time_t tm; + int err = 0; + + printk("Initialising time\n"); + calculate_frequencies(); + + itm_val = (itc_frequency + HZ/2) / HZ; + printk(" itm_val: %ld\n", itm_val); + + os_time.ts_sec = 0; + os_time.ts_nsec = 0; + + if(! efi_get_time(&tm)) + { + printk("efi_get_time() failed\n"); + } + else + { + printk(" EFI-Time: %d.%d.%d %d:%d:%d\n", + tm.Day, tm.Month, tm.Year, + tm.Hour, tm.Minute, tm.Second); + os_time.ts_sec = mktime(tm.Year, tm.Month, + tm.Day, tm.Hour, + tm.Minute, tm.Second); + os_time.ts_nsec = tm.Nanosecond; + } + + err = bind_virq(VIRQ_ITC, timer_interrupt, NULL); + if(err != 0) + { + printk("XEN timer request chn bind failed %i\n", err); + return; + } + + itc_alt = ia64_get_itc(); + itc_at_boot = itc_alt; + new = ia64_get_itc() + itm_val; + ia64_set_itv(IA64_TIMER_VECTOR); + ia64_set_itm(new); + + ia64_srlz_d(); + +} + + diff -r d7f7021902a2 -r 3e3e92fb854a extras/mini-os/arch/ia64/xencomm.c --- /dev/null Thu Jan 1 00:00:00 1970 +0000 +++ b/extras/mini-os/arch/ia64/xencomm.c Tue Feb 6 07:41:50 2007 +0100 @@ -0,0 +1,260 @@ +/* + * Copyright (C) 2006 Hollis Blanchard , IBM Corporation + * Tristan Gingold + * + * 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; either version 2 of the License, or + * (at your option) any later version. + * + * 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. + * + * You should have received a copy of the GNU General Public License + * along with this program; if not, write to the Free Software + * Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA + */ + +/* + * This code is mostly taken from ia64-xen files xcom_mini.c and xencomm.c. + * Changes: Dietmar Hahn +#include +#include +#include + + +#define XENCOMM_MINI_ADDRS 3 +struct xencomm_mini +{ + struct xencomm_desc _desc; + uint64_t address[XENCOMM_MINI_ADDRS]; +}; + +#define xen_guest_handle(hnd) ((hnd).p) + + +/* Translate virtual address to physical address. */ +uint64_t +xencomm_vaddr_to_paddr(uint64_t vaddr) +{ + if(IA64_RR_EXTR(vaddr) == 5) + { + return KERN_VIRT_2_PHYS(vaddr); + } + if(IA64_RR_EXTR(vaddr) == 7) + { + return __pa(vaddr); + } + return 0; +} + +#define min(a,b) (((a) < (b)) ? (a) : (b)) +static int +xencomm_init_desc(struct xencomm_desc *desc, void *buffer, unsigned long bytes) +{ + unsigned long recorded = 0; + int i = 0; + + if((buffer == NULL) && (bytes > 0)) + BUG(); + + /* record the physical pages used */ + if (buffer == NULL) + desc->nr_addrs = 0; + + while ((recorded < bytes) && (i < desc->nr_addrs)) { + unsigned long vaddr = (unsigned long)buffer + recorded; + unsigned long paddr; + int offset; + int chunksz; + + offset = vaddr % PAGE_SIZE; /* handle partial pages */ + chunksz = min(PAGE_SIZE - offset, bytes - recorded); + + paddr = xencomm_vaddr_to_paddr(vaddr); + if (paddr == ~0UL) { + printk("%s: couldn't translate vaddr %lx\n", + __func__, vaddr); + return -EINVAL; + } + + desc->address[i++] = paddr; + recorded += chunksz; + } + if (recorded < bytes) { + printk("%s: could only translate %ld of %ld bytes\n", + __func__, recorded, bytes); + return -ENOSPC; + } + + /* mark remaining addresses invalid (just for safety) */ + while (i < desc->nr_addrs) + desc->address[i++] = XENCOMM_INVALID; + desc->magic = XENCOMM_MAGIC; + return 0; +} + +static void * +xencomm_alloc_mini(struct xencomm_mini *area, int *nbr_area) +{ + unsigned long base; + unsigned int pageoffset; + + while (*nbr_area >= 0) { + /* Allocate an area. */ + (*nbr_area)--; + + base = (unsigned long)(area + *nbr_area); + pageoffset = base % PAGE_SIZE; + + /* If the area does not cross a page, use it. */ + if ((PAGE_SIZE - pageoffset) >= sizeof(struct xencomm_mini)) + return &area[*nbr_area]; + } + /* No more area. */ + return NULL; +} + +int +xencomm_create_mini(struct xencomm_mini *area, int *nbr_area, + void *buffer, unsigned long bytes, + struct xencomm_handle **ret) +{ + struct xencomm_desc *desc; + int rc; + unsigned long res; + + desc = xencomm_alloc_mini(area, nbr_area); + if (!desc) + return -ENOMEM; + desc->nr_addrs = XENCOMM_MINI_ADDRS; + + rc = xencomm_init_desc(desc, buffer, bytes); + if (rc) + return rc; + + res = xencomm_vaddr_to_paddr((unsigned long)desc); + if (res == ~0UL) + return -EINVAL; + + *ret = (struct xencomm_handle*)res; + return 0; +} + +static int +xencommize_mini_grant_table_op(struct xencomm_mini *xc_area, int *nbr_area, + unsigned int cmd, void *op, unsigned int count, + struct xencomm_handle **desc) +{ + struct xencomm_handle *desc1; + unsigned int argsize=0; + int rc; + + switch (cmd) { + case GNTTABOP_map_grant_ref: + argsize = sizeof(struct gnttab_map_grant_ref); + break; + case GNTTABOP_unmap_grant_ref: + argsize = sizeof(struct gnttab_unmap_grant_ref); + break; + case GNTTABOP_setup_table: + { + struct gnttab_setup_table *setup = op; + + argsize = sizeof(*setup); + + if (count != 1) + return -EINVAL; + rc = xencomm_create_mini + (xc_area, nbr_area, + xen_guest_handle(setup->frame_list), + setup->nr_frames + * sizeof(*xen_guest_handle(setup->frame_list)), + &desc1); + if (rc) + return rc; + set_xen_guest_handle(setup->frame_list, (void *)desc1); + break; + } + case GNTTABOP_dump_table: + argsize = sizeof(struct gnttab_dump_table); + break; + case GNTTABOP_transfer: + argsize = sizeof(struct gnttab_transfer); + break; + case GNTTABOP_copy: + argsize = sizeof(struct gnttab_copy); + break; + default: + printk("%s: unknown mini grant table op %d\n", __func__, cmd); + BUG(); + } + + rc = xencomm_create_mini(xc_area, nbr_area, op, count * argsize, desc); + if (rc) + return rc; + + return 0; +} + +int +xencomm_mini_hypercall_grant_table_op(unsigned int cmd, void *op, + unsigned int count) +{ + int rc; + struct xencomm_handle *desc; + int nbr_area = 2; + struct xencomm_mini xc_area[2]; + + rc = xencommize_mini_grant_table_op(xc_area, &nbr_area, + cmd, op, count, &desc); + if (rc) + return rc; + return xencomm_arch_hypercall_grant_table_op(cmd, desc, count); +} + +static void +gnttab_map_grant_ref_pre(struct gnttab_map_grant_ref *uop) +{ + uint32_t flags; + + flags = uop->flags; + + if (flags & GNTMAP_host_map) { + if (flags & GNTMAP_application_map) { + printk("GNTMAP_application_map is not supported yet: flags 0x%x\n", flags); + BUG(); + } + if (flags & GNTMAP_contains_pte) { + printk("GNTMAP_contains_pte is not supported yet flags 0x%x\n", flags); + BUG(); + } + } else if (flags & GNTMAP_device_map) { + printk("GNTMAP_device_map is not supported yet 0x%x\n", flags); + BUG();//XXX not yet. actually this flag is not used. + } else { + BUG(); + } +} + +int +HYPERVISOR_grant_table_op(unsigned int cmd, void *uop, unsigned int count) +{ + if (cmd == GNTTABOP_map_grant_ref) { + unsigned int i; + for (i = 0; i < count; i++) { + gnttab_map_grant_ref_pre( + (struct gnttab_map_grant_ref*)uop + i); + } + } + return xencomm_mini_hypercall_grant_table_op(cmd, uop, count); +} + + + diff -r d7f7021902a2 -r 3e3e92fb854a extras/mini-os/include/ia64/acpi.h --- /dev/null Thu Jan 1 00:00:00 1970 +0000 +++ b/extras/mini-os/include/ia64/acpi.h Tue Feb 6 07:41:50 2007 +0100 @@ -0,0 +1,403 @@ +/* + * This is a short summary of declarations and definitions from different + * acpi header files of Intels' acpica-unix-20060707.tar.gz + * used for the minimal implementation in mini-os. + * + * Changes: Dietmar Hahn + * + ***************************************************************************** + * + * 1. Copyright Notice + * + * Some or all of this work - Copyright (c) 1999 - 2004, Intel Corp. + * All rights reserved. + * + * 2. License + * + * 2.1. This is your license from Intel Corp. under its intellectual property + * rights. You may have additional license terms from the party that provided + * you this software, covering your right to use that party's intellectual + * property rights. + * + * 2.2. Intel grants, free of charge, to any person ("Licensee") obtaining a + * copy of the source code appearing in this file ("Covered Code") an + * irrevocable, perpetual, worldwide license under Intel's copyrights in the + * base code distributed originally by Intel ("Original Intel Code") to copy, + * make derivatives, distribute, use and display any portion of the Covered + * Code in any form, with the right to sublicense such rights; and + * + * 2.3. Intel grants Licensee a non-exclusive and non-transferable patent + * license (with the right to sublicense), under only those claims of Intel + * patents that are infringed by the Original Intel Code, to make, use, sell, + * offer to sell, and import the Covered Code and derivative works thereof + * solely to the minimum extent necessary to exercise the above copyright + * license, and in no event shall the patent license extend to any additions + * to or modifications of the Original Intel Code. No other license or right + * is granted directly or by implication, estoppel or otherwise; + * + * The above copyright and patent license is granted only if the following + * conditions are met: + * + * 3. Conditions + * + * 3.1. Redistribution of Source with Rights to Further Distribute Source. + * Redistribution of source code of any substantial portion of the Covered + * Code or modification with rights to further distribute source must include + * the above Copyright Notice, the above License, this list of Conditions, + * and the following Disclaimer and Export Compliance provision. In addition, + * Licensee must cause all Covered Code to which Licensee contributes to + * contain a file documenting the changes Licensee made to create that Covered + * Code and the date of any change. Licensee must include in that file the + * documentation of any changes made by any predecessor Licensee. Licensee + * must include a prominent statement that the modification is derived, + * directly or indirectly, from Original Intel Code. + * + * 3.2. Redistribution of Source with no Rights to Further Distribute Source. + * Redistribution of source code of any substantial portion of the Covered + * Code or modification without rights to further distribute source must + * include the following Disclaimer and Export Compliance provision in the + * documentation and/or other materials provided with distribution. In + * addition, Licensee may not authorize further sublicense of source of any + * portion of the Covered Code, and must include terms to the effect that the + * license from Licensee to its licensee is limited to the intellectual + * property embodied in the software Licensee provides to its licensee, and + * not to intellectual property embodied in modifications its licensee may + * make. + * + * 3.3. Redistribution of Executable. Redistribution in executable form of any + * substantial portion of the Covered Code or modification must reproduce the + * above Copyright Notice, and the following Disclaimer and Export Compliance + * provision in the documentation and/or other materials provided with the + * distribution. + * + * 3.4. Intel retains all right, title, and interest in and to the Original + * Intel Code. + * + * 3.5. Neither the name Intel nor any other trademark owned or controlled by + * Intel shall be used in advertising or otherwise to promote the sale, use or + * other dealings in products derived from or relating to the Covered Code + * without prior written authorization from Intel. + * + * 4. Disclaimer and Export Compliance + * + * 4.1. INTEL MAKES NO WARRANTY OF ANY KIND REGARDING ANY SOFTWARE PROVIDED + * HERE. ANY SOFTWARE ORIGINATING FROM INTEL OR DERIVED FROM INTEL SOFTWARE + * IS PROVIDED "AS IS," AND INTEL WILL NOT PROVIDE ANY SUPPORT, ASSISTANCE, + * INSTALLATION, TRAINING OR OTHER SERVICES. INTEL WILL NOT PROVIDE ANY + * UPDATES, ENHANCEMENTS OR EXTENSIONS. INTEL SPECIFICALLY DISCLAIMS ANY + * IMPLIED WARRANTIES OF MERCHANTABILITY, NONINFRINGEMENT AND FITNESS FOR A + * PARTICULAR PURPOSE. + * + * 4.2. IN NO EVENT SHALL INTEL HAVE ANY LIABILITY TO LICENSEE, ITS LICENSEES + * OR ANY OTHER THIRD PARTY, FOR ANY LOST PROFITS, LOST DATA, LOSS OF USE OR + * COSTS OF PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES, OR FOR ANY INDIRECT, + * SPECIAL OR CONSEQUENTIAL DAMAGES ARISING OUT OF THIS AGREEMENT, UNDER ANY + * CAUSE OF ACTION OR THEORY OF LIABILITY, AND IRRESPECTIVE OF WHETHER INTEL + * HAS ADVANCE NOTICE OF THE POSSIBILITY OF SUCH DAMAGES. THESE LIMITATIONS + * SHALL APPLY NOTWITHSTANDING THE FAILURE OF THE ESSENTIAL PURPOSE OF ANY + * LIMITED REMEDY. + * + * 4.3. Licensee shall not export, either directly or indirectly, any of this + * software or system incorporating such software without first obtaining any + * required license or other approval from the U. S. Department of Commerce or + * any other agency or department of the United States Government. In the + * event Licensee exports any such software from the United States or + * re-exports any such software from a foreign destination, Licensee shall + * ensure that the distribution and export/re-export of the software is in + * compliance with all laws, regulations, orders, or other restrictions of the + * U.S. Export Administration Regulations. Licensee agrees that neither it nor + * any of its subsidiaries will export/re-export any technical data, process, + * software, or service, directly or indirectly, to any country for which the + * United States government or any agency thereof requires an export license, + * other governmental approval, or letter of assurance, without first obtaining + * such license, approval or letter. + * + *****************************************************************************/ + + + +#if !defined(_ACPI_H_) +#define _ACPI_H_ + + +#define ACPI_MACHINE_WIDTH 64 +#define COMPILER_DEPENDENT_INT64 long +#define COMPILER_DEPENDENT_UINT64 unsigned long + +/* + * 64-bit type definitions + */ +typedef unsigned char UINT8; +typedef unsigned char BOOLEAN; +typedef unsigned short UINT16; +typedef int INT32; +typedef unsigned int UINT32; +typedef COMPILER_DEPENDENT_INT64 INT64; +typedef COMPILER_DEPENDENT_UINT64 UINT64; + +/*! [End] no source code translation !*/ + +typedef INT64 ACPI_NATIVE_INT; +typedef UINT64 ACPI_NATIVE_UINT; + +typedef UINT64 ACPI_TABLE_PTR; +typedef UINT64 ACPI_IO_ADDRESS; +typedef UINT64 ACPI_PHYSICAL_ADDRESS; +typedef UINT64 ACPI_SIZE; + +/* + * Miscellaneous common types + */ +typedef UINT16 UINT16_BIT; +typedef UINT32 UINT32_BIT; +typedef ACPI_NATIVE_UINT ACPI_PTRDIFF; + + +/* + * Local datatypes + */ +typedef UINT32 ACPI_STATUS; /* All ACPI Exceptions */ +typedef UINT32 ACPI_NAME; /* 4-byte ACPI name */ +typedef char * ACPI_STRING; /* Null terminated ASCII string */ +typedef void * ACPI_HANDLE; /* Actually a ptr to an Node */ + + +#define ACPI_SUCCESS(a) (!(a)) +#define ACPI_FAILURE(a) (a) + +#define AE_OK (ACPI_STATUS) 0x0000 + + +/* + * Values for description table header signatures + */ +#define RSDP_NAME "RSDP" +#define RSDP_SIG "RSD PTR " /* RSDT Pointer signature */ +#define APIC_SIG "APIC" /* Multiple APIC Description Table */ +#define DSDT_SIG "DSDT" /* Differentiated System Description Table */ +#define FADT_SIG "FACP" /* Fixed ACPI Description Table */ +#define FACS_SIG "FACS" /* Firmware ACPI Control Structure */ +#define PSDT_SIG "PSDT" /* Persistent System Description Table */ +#define RSDT_SIG "RSDT" /* Root System Description Table */ +#define XSDT_SIG "XSDT" /* Extended System Description Table */ +#define SSDT_SIG "SSDT" /* Secondary System Description Table */ +#define SBST_SIG "SBST" /* Smart Battery Specification Table */ +#define SPIC_SIG "SPIC" /* IOSAPIC table */ +#define BOOT_SIG "BOOT" /* Boot table */ + + +#pragma pack(1) + +/* + * Pointer overlays to avoid lots of typecasting for + * code that accepts both physical and logical pointers. + */ +typedef union acpi_pointers +{ + ACPI_PHYSICAL_ADDRESS Physical; + void *Logical; + ACPI_TABLE_PTR Value; + +} ACPI_POINTERS; + +typedef struct acpi_pointer +{ + UINT32 PointerType; + union acpi_pointers Pointer; + +} ACPI_POINTER; + +/* PointerTypes for above */ + +#define ACPI_PHYSICAL_POINTER 0x01 +#define ACPI_LOGICAL_POINTER 0x02 + +/* Processor mode */ + +#define ACPI_PHYSICAL_ADDRESSING 0x04 +#define ACPI_LOGICAL_ADDRESSING 0x08 +#define ACPI_MEMORY_MODE 0x0C + +#define ACPI_PHYSMODE_PHYSPTR ACPI_PHYSICAL_ADDRESSING | ACPI_PHYSICAL_POINTER +#define ACPI_LOGMODE_PHYSPTR ACPI_LOGICAL_ADDRESSING | ACPI_PHYSICAL_POINTER +#define ACPI_LOGMODE_LOGPTR ACPI_LOGICAL_ADDRESSING | ACPI_LOGICAL_POINTER + + + + + +/* + * MADT sub-structures (Follow MULTIPLE_APIC_DESCRIPTION_TABLE) + */ +#define APIC_HEADER_DEF /* Common APIC sub-structure header */ \ + UINT8 Type; \ + UINT8 Length; + +/* Values for Type in APIC_HEADER_DEF */ + +#define APIC_PROCESSOR 0 +#define APIC_IO 1 +#define APIC_XRUPT_OVERRIDE 2 +#define APIC_NMI 3 +#define APIC_LOCAL_NMI 4 +#define APIC_ADDRESS_OVERRIDE 5 +#define APIC_IO_SAPIC 6 +#define APIC_LOCAL_SAPIC 7 +#define APIC_XRUPT_SOURCE 8 +#define APIC_RESERVED 9 /* 9 and greater are reserved */ + + + +typedef struct apic_header +{ + APIC_HEADER_DEF + +} APIC_HEADER; + +#define ACPI_TABLE_HEADER_DEF /* ACPI common table header */ \ + char Signature [4]; /* ACPI signature (4 ASCII characters) */\ + UINT32 Length; /* Length of table, in bytes, including header */\ + UINT8 Revision; /* ACPI Specification minor version # */\ + UINT8 Checksum; /* To make sum of entire table == 0 */\ + char OemId [6]; /* OEM identification */\ + char OemTableId [8]; /* OEM table identification */\ + UINT32 OemRevision; /* OEM revision number */\ + char AslCompilerId [4]; /* ASL compiler vendor ID */\ + UINT32 AslCompilerRevision; /* ASL compiler revision number */ + + +/* Master MADT */ + +typedef struct multiple_apic_table +{ + ACPI_TABLE_HEADER_DEF /* ACPI common table header */ + UINT32 LocalApicAddress; /* Physical address of local APIC */ + UINT32_BIT PCATCompat : 1; /* A one indicates system also has dual 8259s */ + UINT32_BIT Reserved1 : 31; + +} MULTIPLE_APIC_TABLE; + +typedef struct madt_address_override +{ + APIC_HEADER_DEF + UINT16 Reserved; /* Reserved - must be zero */ + UINT64 Address; /* APIC physical address */ + +} MADT_ADDRESS_OVERRIDE; + + +/* + * Common table types. The base code can remain + * constant if the underlying tables are changed + */ +#define RSDT_DESCRIPTOR RSDT_DESCRIPTOR_REV2 +#define XSDT_DESCRIPTOR XSDT_DESCRIPTOR_REV2 +#define FACS_DESCRIPTOR FACS_DESCRIPTOR_REV2 +#define FADT_DESCRIPTOR FADT_DESCRIPTOR_REV2 + + +/* + * ACPI 2.0 Root System Description Table (RSDT) + */ +typedef struct rsdt_descriptor_rev2 +{ + ACPI_TABLE_HEADER_DEF /* ACPI common table header */ + UINT32 TableOffsetEntry [1]; /* Array of pointers to */ + /* ACPI table headers */ +} RSDT_DESCRIPTOR_REV2; + + +/* + * ACPI 2.0 Extended System Description Table (XSDT) + */ +typedef struct xsdt_descriptor_rev2 +{ + ACPI_TABLE_HEADER_DEF /* ACPI common table header */ + UINT64 TableOffsetEntry [1]; /* Array of pointers to */ + /* ACPI table headers */ +} XSDT_DESCRIPTOR_REV2; + +/* + * ACPI Version-independent tables + * + * NOTE: The tables that are specific to ACPI versions (1.0, 2.0, etc.) + * are in separate files. + */ +typedef struct rsdp_descriptor /* Root System Descriptor Pointer */ +{ + char Signature [8]; /* ACPI signature, contains "RSD PTR " */ + UINT8 Checksum; /* To make sum of struct == 0 */ + char OemId [6]; /* OEM identification */ + UINT8 Revision; /* Must be 0 for 1.0, 2 for 2.0 */ + UINT32 RsdtPhysicalAddress; /* 32-bit physical address of RSDT */ + UINT32 Length; /* XSDT Length in bytes including hdr */ + UINT64 XsdtPhysicalAddress; /* 64-bit physical address of XSDT */ + UINT8 ExtendedChecksum; /* Checksum of entire table */ + char Reserved [3]; /* Reserved field must be 0 */ + +} RSDP_DESCRIPTOR; + + + + + +typedef struct madt_io_sapic +{ + APIC_HEADER_DEF + UINT8 IoSapicId; /* I/O SAPIC ID */ + UINT8 Reserved; /* Reserved - must be zero */ + UINT32 InterruptBase; /* Glocal interrupt for SAPIC start */ + UINT64 Address; /* SAPIC physical address */ + +} MADT_IO_SAPIC; + +/* Common flag definitions */ + +#define MPS_INTI_FLAGS \ + UINT16_BIT Polarity : 2; /* Polarity of APIC I/O input signals */\ + UINT16_BIT TriggerMode : 2; /* Trigger mode of APIC input signals */\ + UINT16_BIT Reserved1 : 12; /* Reserved, must be zero */ + +#define LOCAL_APIC_FLAGS \ + UINT32_BIT ProcessorEnabled: 1; /* Processor is usable if set */\ + UINT32_BIT Reserved2 : 31; /* Reserved, must be zero */ + +typedef struct madt_local_sapic +{ + APIC_HEADER_DEF + UINT8 ProcessorId; /* ACPI processor id */ + UINT8 LocalSapicId; /* SAPIC ID */ + UINT8 LocalSapicEid; /* SAPIC EID */ + UINT8 Reserved [3]; /* Reserved - must be zero */ + LOCAL_APIC_FLAGS + +} MADT_LOCAL_SAPIC; + + +typedef struct madt_interrupt_override +{ + APIC_HEADER_DEF + UINT8 Bus; /* 0 - ISA */ + UINT8 Source; /* Interrupt source (IRQ) */ + UINT32 Interrupt; /* Global system interrupt */ + MPS_INTI_FLAGS + +} MADT_INTERRUPT_OVERRIDE; + +typedef struct madt_interrupt_source +{ + APIC_HEADER_DEF + MPS_INTI_FLAGS + UINT8 InterruptType; /* 1=PMI, 2=INIT, 3=corrected */ + UINT8 ProcessorId; /* Processor ID */ + UINT8 ProcessorEid; /* Processor EID */ + UINT8 IoSapicVector; /* Vector value for PMI interrupts */ + UINT32 Interrupt; /* Global system interrupt */ + UINT32 Reserved; /* Reserved - must be zero */ + +} MADT_INTERRUPT_SOURCE; + + +#pragma pack() + +#endif /* _ACPI_H_ */ diff -r d7f7021902a2 -r 3e3e92fb854a extras/mini-os/include/ia64/arch_mm.h --- /dev/null Thu Jan 1 00:00:00 1970 +0000 +++ b/extras/mini-os/include/ia64/arch_mm.h Tue Feb 6 07:41:50 2007 +0100 @@ -0,0 +1,36 @@ +/* + * Copyright (C) 2007 - Dietmar Hahn + * + **************************************************************************** + * Permission is hereby granted, free of charge, to any person obtaining a copy + * of this software and associated documentation files (the "Software"), to + * deal in the Software without restriction, including without limitation the + * rights to use, copy, modify, merge, publish, distribute, sublicense, and/or + * sell copies of the Software, and to permit persons to whom the Software is + * furnished to do so, subject to the following conditions: + * + * The above copyright notice and this permission notice shall be included in + * all copies or substantial portions of the Software. + * + * THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR + * IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY, + * FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE + * AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER + * LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING + * FROM, OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER + * DEALINGS IN THE SOFTWARE. + */ + +#ifndef __ARCH_MM_H__ +#define __ARCH_MM_H__ + +#include "page.h" + +#define PFN_PHYS(x) (pfn_to_page(x)) +#define PHYS_PFN(x) (page_to_pfn(x)) +#define to_virt(x) __va(x) +#define to_phys(x) __pa(x) + +#define virt_to_mfn(x) virt_to_pfn(x) + +#endif /* __ARCH_MM_H__ */ diff -r d7f7021902a2 -r 3e3e92fb854a extras/mini-os/include/ia64/arch_sched.h --- /dev/null Thu Jan 1 00:00:00 1970 +0000 +++ b/extras/mini-os/include/ia64/arch_sched.h Tue Feb 6 07:41:50 2007 +0100 @@ -0,0 +1,91 @@ +/* + * Copyright (c) 2006 Dietmar Hahn + * All rights reserved. + * + * The file contains ia64 specific scheduler declarations. + * + **************************************************************************** + * Permission is hereby granted, free of charge, to any person obtaining a copy + * of this software and associated documentation files (the "Software"), to + * deal in the Software without restriction, including without limitation the + * rights to use, copy, modify, merge, publish, distribute, sublicense, and/or + * sell copies of the Software, and to permit persons to whom the Software is + * furnished to do so, subject to the following conditions: + * + * The above copyright notice and this permission notice shall be included in + * all copies or substantial portions of the Software. + * + * THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR + * IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY, + * FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE + * AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER + * LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING + * FROM, OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER + * DEALINGS IN THE SOFTWARE. + */ + +#ifndef __ARCH_SCHED_H__ +#define __ARCH_SCHED_H__ + +#include "os.h" + +struct thread; /* Only declaration */ + +struct thread_regs +{ + unsigned long unat_b; /* NaT before spilling */ + unsigned long sp; + unsigned long rp; + unsigned long pr; + unsigned long bsp; + unsigned long pfs; + unsigned long rnat; + unsigned long lc; + + unsigned long unat_a; /* NaT after spilling. */ + unsigned long r4; + unsigned long r5; + unsigned long r6; + unsigned long r7; + + unsigned long b1; + unsigned long b2; + unsigned long b3; + unsigned long b4; + unsigned long b5; + + ia64_fpreg_t f2; + ia64_fpreg_t f3; + ia64_fpreg_t f4; + ia64_fpreg_t f5; + ia64_fpreg_t f16; + ia64_fpreg_t f17; + ia64_fpreg_t f18; + ia64_fpreg_t f19; + ia64_fpreg_t f20; + ia64_fpreg_t f21; + ia64_fpreg_t f22; + ia64_fpreg_t f23; + ia64_fpreg_t f24; + ia64_fpreg_t f25; + ia64_fpreg_t f26; + ia64_fpreg_t f27; + ia64_fpreg_t f28; + ia64_fpreg_t f29; + ia64_fpreg_t f30; + ia64_fpreg_t f31; +}; + +typedef struct thread_regs thread_regs_t; + +void arch_switch_threads(struct thread* prev, struct thread* next); + +static inline struct thread* get_current(void) +{ + struct thread *current; + __asm ("mov %0=r13" : "=r" (current)); + return current; +} + + +#endif /* __ARCH_SCHED_H__ */ diff -r d7f7021902a2 -r 3e3e92fb854a extras/mini-os/include/ia64/arch_spinlock.h --- /dev/null Thu Jan 1 00:00:00 1970 +0000 +++ b/extras/mini-os/include/ia64/arch_spinlock.h Tue Feb 6 07:41:50 2007 +0100 @@ -0,0 +1,64 @@ +/* + * (C) 2006 - Dietmar Hahn slock), + SPIN_LOCK_UNUSED, SPIN_LOCK_USED); + } while(ret == SPIN_LOCK_USED); +} + +static inline void +_raw_spin_unlock(spinlock_t *lck) +{ + asm volatile ("st4.rel.nta [%0] = r0\n\t" :: "r"(&(lck->slock)) + : "memory" ); +} + +static inline uint32_t +_raw_spin_trylock(spinlock_t* lck) +{ + uint32_t ret; + ret = ia64_cmpxchg_acq_32(&(lck->slock), SPIN_LOCK_USED, SPIN_LOCK_USED); + return (ret == SPIN_LOCK_USED); +} + + +#endif /* _ARCH_SPINLOCK_H_ */ diff -r d7f7021902a2 -r 3e3e92fb854a extras/mini-os/include/ia64/asm.h --- /dev/null Thu Jan 1 00:00:00 1970 +0000 +++ b/extras/mini-os/include/ia64/asm.h Tue Feb 6 07:41:50 2007 +0100 @@ -0,0 +1,20 @@ + + +#if !defined(_ASM_H_) +#define _ASM_H_ + + + +#define ENTRY(_name_) \ + .global _name_; \ + .align 16; \ + .proc _name_; \ +_name_:; \ + + +#define END(_name_) \ + .endp _name_ + + + +#endif /* !defined(_ASM_H_) */ diff -r d7f7021902a2 -r 3e3e92fb854a extras/mini-os/include/ia64/atomic.h --- /dev/null Thu Jan 1 00:00:00 1970 +0000 +++ b/extras/mini-os/include/ia64/atomic.h Tue Feb 6 07:41:50 2007 +0100 @@ -0,0 +1,504 @@ +/* + * This code is mostly taken from FreeBSD machine/atomic.h + * Changes: Dietmar Hahn + * + **************************************************************************** + * Copyright (c) 1998 Doug Rabson + * All rights reserved. + * + * Redistribution and use in source and binary forms, with or without + * modification, are permitted provided that the following conditions + * are met: + * 1. Redistributions of source code must retain the above copyright + * notice, this list of conditions and the following disclaimer. + * 2. Redistributions in binary form must reproduce the above copyright + * notice, this list of conditions and the following disclaimer in the + * documentation and/or other materials provided with the distribution. + * + * THIS SOFTWARE IS PROVIDED BY THE AUTHOR AND CONTRIBUTORS ``AS IS'' AND + * ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE + * IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE + * ARE DISCLAIMED. IN NO EVENT SHALL THE AUTHOR OR CONTRIBUTORS BE LIABLE + * FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL + * DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS + * OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) + * HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT + * LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY + * OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF + * SUCH DAMAGE. + */ + +#ifndef _MACHINE_ATOMIC_H_ +#define _MACHINE_ATOMIC_H_ + +/* + * Various simple arithmetic on memory which is atomic in the presence + * of interrupts and SMP safe. + */ + +#if !defined(__ASSEMBLY__) + +#include + + +/* + * Everything is built out of cmpxchg. + */ +#define IA64_CMPXCHG(sz, sem, p, cmpval, newval, ret) \ + __asm __volatile ( \ + "mov ar.ccv=%2;;\n\t" \ + "cmpxchg" #sz "." #sem " %0=%4,%3,ar.ccv\n\t" \ + : "=r" (ret), "=m" (*p) \ + : "r" (cmpval), "r" (newval), "m" (*p) \ + : "memory") + + +/* + * Some common forms of cmpxch. + */ + +static __inline uint8_t +ia64_cmpxchg_acq_8(volatile uint8_t* p, uint8_t cmpval, uint8_t newval) +{ + uint8_t ret; + IA64_CMPXCHG(1, acq, p, cmpval, newval, ret); + return (ret); +} + +static __inline uint16_t +ia64_cmpxchg_acq_16(volatile uint16_t* p, uint16_t cmpval, uint16_t newval) +{ + uint16_t ret; + IA64_CMPXCHG(2, acq, p, cmpval, newval, ret); + return (ret); +} + +static __inline uint32_t +ia64_cmpxchg_acq_32(volatile uint32_t* p, uint32_t cmpval, uint32_t newval) +{ + uint32_t ret; + IA64_CMPXCHG(4, acq, p, cmpval, newval, ret); + return (ret); +} + +static __inline uint32_t +ia64_cmpxchg_rel_32(volatile uint32_t* p, uint32_t cmpval, uint32_t newval) +{ + uint32_t ret; + IA64_CMPXCHG(4, rel, p, cmpval, newval, ret); + return (ret); +} + +static __inline uint64_t +ia64_cmpxchg_acq_64(volatile uint64_t* p, uint64_t cmpval, uint64_t newval) +{ + uint64_t ret; + IA64_CMPXCHG(8, acq, p, cmpval, newval, ret); + return (ret); +} + +static __inline uint64_t +ia64_cmpxchg_rel_64(volatile uint64_t* p, uint64_t cmpval, uint64_t newval) +{ + uint64_t ret; + IA64_CMPXCHG(8, rel, p, cmpval, newval, ret); + return (ret); +} + +#define ATOMIC_STORE_LOAD(type, width, size) \ +static __inline uint##width##_t \ +ia64_ld_acq_##width(volatile uint##width##_t* p) \ +{ \ + uint##width##_t v; \ + \ + __asm __volatile ("ld" size ".acq %0=%1" \ + : "=r" (v) \ + : "m" (*p) \ + : "memory"); \ + return (v); \ +} \ + \ +static __inline uint##width##_t \ +atomic_load_acq_##width(volatile uint##width##_t* p) \ +{ \ + uint##width##_t v; \ + \ + __asm __volatile ("ld" size ".acq %0=%1" \ + : "=r" (v) \ + : "m" (*p) \ + : "memory"); \ + return (v); \ +} \ + \ +static __inline uint##width##_t \ +atomic_load_acq_##type(volatile uint##width##_t* p) \ +{ \ + uint##width##_t v; \ + \ + __asm __volatile ("ld" size ".acq %0=%1" \ + : "=r" (v) \ + : "m" (*p) \ + : "memory"); \ + return (v); \ +} \ + \ +static __inline void \ +ia64_st_rel_##width(volatile uint##width##_t* p, uint##width##_t v)\ +{ \ + __asm __volatile ("st" size ".rel %0=%1" \ + : "=m" (*p) \ + : "r" (v) \ + : "memory"); \ +} \ + \ +static __inline void \ +atomic_store_rel_##width(volatile uint##width##_t* p, uint##width##_t v)\ +{ \ + __asm __volatile ("st" size ".rel %0=%1" \ + : "=m" (*p) \ + : "r" (v) \ + : "memory"); \ +} \ + \ +static __inline void \ +atomic_store_rel_##type(volatile uint##width##_t* p, uint##width##_t v)\ +{ \ + __asm __volatile ("st" size ".rel %0=%1" \ + : "=m" (*p) \ + : "r" (v) \ + : "memory"); \ +} + +ATOMIC_STORE_LOAD(char, 8, "1") +ATOMIC_STORE_LOAD(short, 16, "2") +ATOMIC_STORE_LOAD(int, 32, "4") +ATOMIC_STORE_LOAD(long, 64, "8") + +#undef ATOMIC_STORE_LOAD + +#define IA64_ATOMIC(sz, type, name, width, op) \ + \ +static __inline type \ +atomic_##name##_acq_##width(volatile type *p, type v) \ +{ \ + type old, ret; \ + do { \ + old = *p; \ + IA64_CMPXCHG(sz, acq, p, old, old op v, ret); \ + } while (ret != old); \ + return(ret); \ +} \ + \ +static __inline type \ +atomic_##name##_rel_##width(volatile type *p, type v) \ +{ \ + type old, ret; \ + do { \ + old = *p; \ + IA64_CMPXCHG(sz, rel, p, old, old op v, ret); \ + } while (ret != old); \ + return(ret); \ +} + +IA64_ATOMIC(1, uint8_t, set, 8, |) +IA64_ATOMIC(2, uint16_t, set, 16, |) +IA64_ATOMIC(4, uint32_t, set, 32, |) +IA64_ATOMIC(8, uint64_t, set, 64, |) + +IA64_ATOMIC(1, uint8_t, clear, 8, &~) +IA64_ATOMIC(2, uint16_t, clear, 16, &~) +IA64_ATOMIC(4, uint32_t, clear, 32, &~) +IA64_ATOMIC(8, uint64_t, clear, 64, &~) + +IA64_ATOMIC(1, uint8_t, add, 8, +) +IA64_ATOMIC(2, uint16_t, add, 16, +) +IA64_ATOMIC(4, uint32_t, add, 32, +) +IA64_ATOMIC(8, uint64_t, add, 64, +) + +IA64_ATOMIC(1, uint8_t, subtract, 8, -) +IA64_ATOMIC(2, uint16_t, subtract, 16, -) +IA64_ATOMIC(4, uint32_t, subtract, 32, -) +IA64_ATOMIC(8, uint64_t, subtract, 64, -) + +#undef IA64_ATOMIC +#undef IA64_CMPXCHG + +#define atomic_set_8 atomic_set_acq_8 +#define atomic_clear_8 atomic_clear_acq_8 +#define atomic_add_8 atomic_add_acq_8 +#define atomic_subtract_8 atomic_subtract_acq_8 + +#define atomic_set_16 atomic_set_acq_16 +#define atomic_clear_16 atomic_clear_acq_16 +#define atomic_add_16 atomic_add_acq_16 +#define atomic_subtract_16 atomic_subtract_acq_16 + +#define atomic_set_32 atomic_set_acq_32 +#define atomic_clear_32 atomic_clear_acq_32 +#define atomic_add_32 atomic_add_acq_32 +#define atomic_subtract_32 atomic_subtract_acq_32 + +#define atomic_set_64 atomic_set_acq_64 +#define atomic_clear_64 atomic_clear_acq_64 +#define atomic_add_64 atomic_add_acq_64 +#define atomic_subtract_64 atomic_subtract_acq_64 + +#define atomic_set_char atomic_set_8 +#define atomic_clear_char atomic_clear_8 +#define atomic_add_char atomic_add_8 +#define atomic_subtract_char atomic_subtract_8 +#define atomic_set_acq_char atomic_set_acq_8 +#define atomic_clear_acq_char atomic_clear_acq_8 +#define atomic_add_acq_char atomic_add_acq_8 +#define atomic_subtract_acq_char atomic_subtract_acq_8 +#define atomic_set_rel_char atomic_set_rel_8 +#define atomic_clear_rel_char atomic_clear_rel_8 +#define atomic_add_rel_char atomic_add_rel_8 +#define atomic_subtract_rel_char atomic_subtract_rel_8 + +#define atomic_set_short atomic_set_16 +#define atomic_clear_short atomic_clear_16 +#define atomic_add_short atomic_add_16 +#define atomic_subtract_short atomic_subtract_16 +#define atomic_set_acq_short atomic_set_acq_16 +#define atomic_clear_acq_short atomic_clear_acq_16 +#define atomic_add_acq_short atomic_add_acq_16 +#define atomic_subtract_acq_short atomic_subtract_acq_16 +#define atomic_set_rel_short atomic_set_rel_16 +#define atomic_clear_rel_short atomic_clear_rel_16 +#define atomic_add_rel_short atomic_add_rel_16 +#define atomic_subtract_rel_short atomic_subtract_rel_16 + +#define atomic_set_int atomic_set_32 +#define atomic_clear_int atomic_clear_32 +#define atomic_add_int atomic_add_32 +#define atomic_subtract_int atomic_subtract_32 +#define atomic_set_acq_int atomic_set_acq_32 +#define atomic_clear_acq_int atomic_clear_acq_32 +#define atomic_add_acq_int atomic_add_acq_32 +#define atomic_subtract_acq_int atomic_subtract_acq_32 +#define atomic_set_rel_int atomic_set_rel_32 +#define atomic_clear_rel_int atomic_clear_rel_32 +#define atomic_add_rel_int atomic_add_rel_32 +#define atomic_subtract_rel_int atomic_subtract_rel_32 + +#define atomic_set_long atomic_set_64 +#define atomic_clear_long atomic_clear_64 +#define atomic_add_long atomic_add_64 +#define atomic_subtract_long atomic_subtract_64 +#define atomic_set_acq_long atomic_set_acq_64 +#define atomic_clear_acq_long atomic_clear_acq_64 +#define atomic_add_acq_long atomic_add_acq_64 +#define atomic_subtract_acq_long atomic_subtract_acq_64 +#define atomic_set_rel_long atomic_set_rel_64 +#define atomic_clear_rel_long atomic_clear_rel_64 +#define atomic_add_rel_long atomic_add_rel_64 +#define atomic_subtract_rel_long atomic_subtract_rel_64 + +/* + * Atomically compare the value stored at *p with cmpval and if the + * two values are equal, update the value of *p with newval. Returns + * zero if the compare failed, nonzero otherwise. + */ +static __inline int +atomic_cmpset_acq_32(volatile uint32_t* p, uint32_t cmpval, uint32_t newval) +{ + return ia64_cmpxchg_acq_32(p, cmpval, newval) == cmpval; +} + +static __inline int +atomic_cmpset_rel_32(volatile uint32_t* p, uint32_t cmpval, uint32_t newval) +{ + return ia64_cmpxchg_rel_32(p, cmpval, newval) == cmpval; +} + +/* + * Atomically compare the value stored at *p with cmpval and if the + * two values are equal, update the value of *p with newval. Returns + * zero if the compare failed, nonzero otherwise. + */ +static __inline int +atomic_cmpset_acq_64(volatile uint64_t* p, uint64_t cmpval, uint64_t newval) +{ + return ia64_cmpxchg_acq_64(p, cmpval, newval) == cmpval; +} + +static __inline int +atomic_cmpset_rel_64(volatile uint64_t* p, uint64_t cmpval, uint64_t newval) +{ + return ia64_cmpxchg_rel_64(p, cmpval, newval) == cmpval; +} + +#define atomic_cmpset_32 atomic_cmpset_acq_32 +#define atomic_cmpset_64 atomic_cmpset_acq_64 +#define atomic_cmpset_int atomic_cmpset_32 +#define atomic_cmpset_long atomic_cmpset_64 +#define atomic_cmpset_acq_int atomic_cmpset_acq_32 +#define atomic_cmpset_rel_int atomic_cmpset_rel_32 +#define atomic_cmpset_acq_long atomic_cmpset_acq_64 +#define atomic_cmpset_rel_long atomic_cmpset_rel_64 + +static __inline int +atomic_cmpset_acq_ptr(volatile void *dst, void *exp, void *src) +{ + return atomic_cmpset_acq_long((volatile u_long *)dst, + (u_long)exp, (u_long)src); +} + +static __inline int +atomic_cmpset_rel_ptr(volatile void *dst, void *exp, void *src) +{ + return atomic_cmpset_rel_long((volatile u_long *)dst, + (u_long)exp, (u_long)src); +} + +#define atomic_cmpset_ptr atomic_cmpset_acq_ptr + +static __inline void * +atomic_load_acq_ptr(volatile void *p) +{ + return (void *)atomic_load_acq_long((volatile u_long *)p); +} + +static __inline void +atomic_store_rel_ptr(volatile void *p, void *v) +{ + atomic_store_rel_long((volatile u_long *)p, (u_long)v); +} + +#define IA64_ATOMIC_PTR(NAME) \ +static __inline void \ +atomic_##NAME##_ptr(volatile void *p, uintptr_t v) \ +{ \ + atomic_##NAME##_long((volatile u_long *)p, v); \ +} \ + \ +static __inline void \ +atomic_##NAME##_acq_ptr(volatile void *p, uintptr_t v) \ +{ \ + atomic_##NAME##_acq_long((volatile u_long *)p, v);\ +} \ + \ +static __inline void \ +atomic_##NAME##_rel_ptr(volatile void *p, uintptr_t v) \ +{ \ + atomic_##NAME##_rel_long((volatile u_long *)p, v);\ +} + +IA64_ATOMIC_PTR(set) +IA64_ATOMIC_PTR(clear) +IA64_ATOMIC_PTR(add) +IA64_ATOMIC_PTR(subtract) + +#undef IA64_ATOMIC_PTR + +static __inline uint32_t +atomic_readandclear_32(volatile uint32_t* p) +{ + uint32_t val; + do { + val = *p; + } while (!atomic_cmpset_32(p, val, 0)); + return val; +} + +static __inline uint64_t +atomic_readandclear_64(volatile uint64_t* p) +{ + uint64_t val; + do { + val = *p; + } while (!atomic_cmpset_64(p, val, 0)); + return val; +} + +#define atomic_readandclear_int atomic_readandclear_32 +#define atomic_readandclear_long atomic_readandclear_64 + + +/* Some bit operations */ + +static inline void +set_bit(int num, volatile void *addr) +{ + uint32_t b, old, new; + volatile uint32_t *p; + p = (volatile uint32_t *) addr + (num >> 5); + b = 1 << (num & 31); + do + { + old = *p; + new = old | b; + } while(ia64_cmpxchg_acq_32(p, old, new) != old); +} + +static __inline__ void +clear_bit(int num, volatile void *addr) +{ + uint32_t m, old, new; + volatile uint32_t *p; + p = (volatile uint32_t *) addr + (num >> 5); + m = ~(1 << (num & 31)); + do { + old = *p; + new = old & m; + } while (ia64_cmpxchg_acq_32(p, old, new) != old); +} + +static __inline__ int +test_bit(int num, const volatile void *addr) +{ + uint32_t val = 1; + return val & (((const volatile uint32_t *) addr)[num >> 5] >> (num & 31)); +} + +/** + * test_and_set_bit - Set a bit and return its old value + * @num: Bit to set + * @addr: Address to count from + * + * This operation is atomic and cannot be reordered. + * It also implies a memory barrier. + */ +static inline int +test_and_set_bit (int num, volatile void *addr) +{ + uint32_t b, old, new; + volatile uint32_t *m; + + m = (volatile uint32_t *) addr + (num >> 5); + b = 1 << (num & 31); + do { + old = *m; + new = old | b; + } while (ia64_cmpxchg_acq_32(m, old, new) != old); + return (old & b) != 0; +} + +/** + * test_and_clear_bit - Clear a bit and return its old value + * @num: Bit to set + * @addr: Address to count from + * + * This operation is atomic and cannot be reordered. + * It also implies a memory barrier. + */ +static +inline int test_and_clear_bit(int num, volatile unsigned long * addr) +{ + uint32_t b, old, new; + volatile uint32_t* a; + + a = (volatile uint32_t *) addr + (num >> 5); + b = ~(1 << (num & 31)); + do { + old = *a; + new = old & b; + } while (ia64_cmpxchg_acq_32(a, old, new) != old); + return (old & ~b) != 0; +} + + +#endif /* !defined(__ASSEMBLY__) */ + +#endif /* ! _MACHINE_ATOMIC_H_ */ diff -r d7f7021902a2 -r 3e3e92fb854a extras/mini-os/include/ia64/efi.h --- /dev/null Thu Jan 1 00:00:00 1970 +0000 +++ b/extras/mini-os/include/ia64/efi.h Tue Feb 6 07:41:50 2007 +0100 @@ -0,0 +1,400 @@ +/* + * This is a short summary of declarations and definitions from different + * efi header files of Intels' EFI_Toolkit_1.10.14.62 + * used for the minimal implementation in mini-os. + * Changes: Dietmar Hahn + * + **************************************************************************** + * Copyright (C) 2001-2004, Intel Corporation. + * THIS SPECIFICATION IS PROVIDED "AS IS" WITH NO WARRANTIES WHATSOEVER, + * INCLUDING ANY WARRANTY OF MERCHANTABILITY, NONINFRINGEMENT, FITNESS FOR + * ANY PARTICULAR PURPOSE, OR ANY WARRANTY OTHERWISE ARISING OUT OF ANY + * PROPOSAL, SPECIFICATION OR SAMPLE. Except for a limited copyright license + * to copy this specification for internal use only, no license, express or + * implied, by estoppel or otherwise, to any intellectual property rights is + * granted herein. Intel disclaims all liability, including liability for + * infringement of any proprietary rights, relating to implementation of + * information in this specification. Intel does not warrant or represent + * that such implementation(s) will not infringe such rights. Designers must + * not rely on the absence or characteristics of any features or instructions + * marked "reserved" or "undefined." Intel reserves these for future + * definition and shall have no responsibility whatsoever for conflicts or + * incompatibilities arising from future changes to them. + * This document is an intermediate draft for comment only and is subject to + * change without notice. Readers should not design products based on this + * document. + * Intel, the Intel logo, and Itanium are trademarks or registered trademarks + * of Intel Corporation or its subsidiaries in the United States and other + * countries. + * Other names and brands may be claimed as the property of others. + */ + +#ifndef _EFI_H_ +#define _EFI_H_ + +#include "types.h" + + +#define EFIWARN(a) (a) +#define EFI_ERROR(a) (((int64_t) a) < 0) + + +#define EFI_SUCCESS 0 +#define EFI_LOAD_ERROR EFIERR(1) +#define EFI_INVALID_PARAMETER EFIERR(2) +#define EFI_UNSUPPORTED EFIERR(3) +#define EFI_BAD_BUFFER_SIZE EFIERR(4) +#define EFI_BUFFER_TOO_SMALL EFIERR(5) +#define EFI_NOT_READY EFIERR(6) +#define EFI_DEVICE_ERROR EFIERR(7) +#define EFI_WRITE_PROTECTED EFIERR(8) +#define EFI_OUT_OF_RESOURCES EFIERR(9) +#define EFI_VOLUME_CORRUPTED EFIERR(10) +#define EFI_VOLUME_FULL EFIERR(11) +#define EFI_NO_MEDIA EFIERR(12) +#define EFI_MEDIA_CHANGED EFIERR(13) +#define EFI_NOT_FOUND EFIERR(14) +#define EFI_ACCESS_DENIED EFIERR(15) +#define EFI_NO_RESPONSE EFIERR(16) +#define EFI_NO_MAPPING EFIERR(17) +#define EFI_TIMEOUT EFIERR(18) +#define EFI_NOT_STARTED EFIERR(19) +#define EFI_ALREADY_STARTED EFIERR(20) +#define EFI_ABORTED EFIERR(21) +#define EFI_ICMP_ERROR EFIERR(22) +#define EFI_TFTP_ERROR EFIERR(23) +#define EFI_PROTOCOL_ERROR EFIERR(24) + +#define EFI_WARN_UNKOWN_GLYPH EFIWARN(1) +#define EFI_WARN_DELETE_FAILURE EFIWARN(2) +#define EFI_WARN_WRITE_FAILURE EFIWARN(3) +#define EFI_WARN_BUFFER_TOO_SMALL EFIWARN(4) + + +typedef uint64_t efi_status_t; +typedef void* efi_handle_t; +typedef void* efi_event_t; +typedef uint16_t efi_char16_t; + + +/* + * Standard EFI table header + */ + +struct efi_table_header +{ + uint64_t Signature; + // Revision of EFI table specification, + // upper 16 bit - major revision number + // lower 16 bit - minor revision number + uint32_t Revision; + uint32_t HeaderSize; + uint32_t CRC32; + uint32_t Reserved; +}; +typedef struct efi_table_header efi_table_header_t; + + +/* + * EFI Time + */ +typedef struct +{ + uint16_t Year; /* 1998 - 20XX */ + uint8_t Month; /* 1 - 12 */ + uint8_t Day; /* 1 - 31 */ + uint8_t Hour; /* 0 - 23 */ + uint8_t Minute; /* 0 - 59 */ + uint8_t Second; /* 0 - 59 */ + uint8_t Pad1; + uint32_t Nanosecond; /* 0 - 999,999,999 */ + int16_t TimeZone; /* -1440 to 1440 or 2047 */ + uint8_t Daylight; + uint8_t Pad2; +} efi_time_t; + +/* Bit definitions for efi_time_t.Daylight */ +#define EFI_TIME_ADJUST_DAYLIGHT 0x01 +#define EFI_TIME_IN_DAYLIGHT 0x02 + +/* Value definition for efi_time_t.TimeZone */ +#define EFI_UNSPECIFIED_TIMEZONE 0x07FF + + + +typedef struct +{ + uint32_t Resolution; /* 1e-6 parts per million */ + uint32_t Accuracy; /* hertz */ + uint8_t SetsToZero; /* Set clears sub-second time */ +} efi_time_capabilities_t; + + +typedef efi_status_t (*efi_get_time_t) (efi_time_t*, efi_time_capabilities_t*); +typedef efi_status_t (*efi_set_time_t) (efi_time_t*); +typedef efi_status_t (*efi_get_wakeup_time_t) (uint8_t*, uint8_t*, efi_time_t*); +typedef efi_status_t (*efi_set_wakeup_time_t) (uint8_t, efi_time_t*); + + + +/* + * Memory + * Preseve the attr on any range supplied. + * ConventialMemory must have WB,SR,SW when supplied. + * When allocating from ConventialMemory always make it WB,SR,SW + * When returning to ConventialMemory always make it WB,SR,SW + * When getting the memory map, or on RT for runtime types + */ + +typedef enum { + EfiReservedMemoryType, /* 0 */ + EfiLoaderCode, + EfiLoaderData, + EfiBootServicesCode, + EfiBootServicesData, + EfiRuntimeServicesCode, + EfiRuntimeServicesData, /* 6 */ + EfiConventionalMemory, /* 7 */ + EfiUnusableMemory, + EfiACPIReclaimMemory, /* 9 */ + EfiACPIMemoryNVS, /* 10, a */ + EfiMemoryMappedIO, + EfiMemoryMappedIOPortSpace, /* 12, c */ + EfiPalCode, /* 13, d */ + EfiMaxMemoryType /* 14, e */ +} efi_memory_type_t; + +/* possible caching types for the memory range */ +#define EFI_MEMORY_UC 0x0000000000000001 +#define EFI_MEMORY_WC 0x0000000000000002 +#define EFI_MEMORY_WT 0x0000000000000004 +#define EFI_MEMORY_WB 0x0000000000000008 +#define EFI_MEMORY_UCE 0x0000000000000010 +/* physical memory protection on range */ +#define EFI_MEMORY_WP 0x0000000000001000 +#define EFI_MEMORY_RP 0x0000000000002000 +#define EFI_MEMORY_XP 0x0000000000004000 +/* range requires a runtime mapping */ +#define EFI_MEMORY_RUNTIME 0x8000000000000000 + +#define EFI_MEMORY_DESCRIPTOR_VERSION 1 + +typedef uint64_t efi_phys_addr_t; +typedef uint64_t efi_virt_addr_t; + +typedef struct +{ + uint32_t Type; /* 32 bit padding */ + efi_phys_addr_t PhysicalStart; + efi_virt_addr_t VirtualStart; + uint64_t NumberOfPages; + uint64_t Attribute; +} efi_memory_descriptor_t; + +#define NextMemoryDescriptor(Ptr,Size) ((efi_memory_descriptor_t*) (((uint8_t*) Ptr) + Size)) + + +typedef efi_status_t (*efi_set_virtual_address_map_t) + ( + uint64_t MemoryMapSize, + uint64_t DescriptorSize, + uint32_t DescriptorVersion, + efi_memory_descriptor_t* VirtualMap + ); + +typedef efi_status_t (*efi_convert_pointer_t) + ( + uint64_t DebugDisposition, + void** Address + ); + +/* + * A GUID + */ + +typedef struct +{ + uint32_t Data1; + uint16_t Data2; + uint16_t Data3; + uint8_t Data4[8]; +} efi_guid_t; + + +/* + * EFI Configuration Table and GUID definitions + */ + +#define MPS_TABLE_GUID \ + { 0xeb9d2d2f, 0x2d88, 0x11d3, \ + { 0x9a, 0x16, 0x0, 0x90, 0x27, 0x3f, 0xc1, 0x4d } } + +#define ACPI_TABLE_GUID \ + { 0xeb9d2d30, 0x2d88, 0x11d3, \ + { 0x9a, 0x16, 0x0, 0x90, 0x27, 0x3f, 0xc1, 0x4d } } + +#define ACPI_20_TABLE_GUID \ + { 0x8868e871, 0xe4f1, 0x11d3, \ + { 0xbc, 0x22, 0x0, 0x80, 0xc7, 0x3c, 0x88, 0x81 } } + +#define SMBIOS_TABLE_GUID \ + { 0xeb9d2d31, 0x2d88, 0x11d3, \ + { 0x9a, 0x16, 0x0, 0x90, 0x27, 0x3f, 0xc1, 0x4d } } + +#define SAL_SYSTEM_TABLE_GUID \ + { 0xeb9d2d32, 0x2d88, 0x11d3, \ + { 0x9a, 0x16, 0x0, 0x90, 0x27, 0x3f, 0xc1, 0x4d } } + +/* DIG64 Headless Console & Debug Port Table. */ +#define HCDP_TABLE_GUID \ + {0xf951938d, 0x620b, 0x42ef, \ + {0x82, 0x79, 0xa8, 0x4b, 0x79, 0x61, 0x78, 0x98 } } + + +typedef struct efi_configuration_table +{ + efi_guid_t VendorGuid; + void* VendorTable; +} efi_configuration_table_t; + + + +/* + * EFI platform variables + */ + +#define EFI_GLOBAL_VARIABLE \ + { 0x8BE4DF61, 0x93CA, 0x11d2, 0xAA, 0x0D, 0x00, 0xE0, 0x98, 0x03, 0x2B, 0x8C } + +/* Variable attributes */ +#define EFI_VARIABLE_NON_VOLATILE 0x00000001 +#define EFI_VARIABLE_BOOTSERVICE_ACCESS 0x00000002 +#define EFI_VARIABLE_RUNTIME_ACCESS 0x00000004 + +/* Variable size limitation */ +#define EFI_MAXIMUM_VARIABLE_SIZE 1024 + +typedef efi_status_t (*efi_get_variable_t) + ( + efi_char16_t* VariableName, + efi_guid_t *VendorGuid, + uint32_t* Attributes, + uint64_t* DataSize, + void* Data + ); + +typedef +efi_status_t (*efi_get_next_variable_name_t) + ( + uint64_t* VariableNameSize, + efi_char16_t* VariableName, + efi_guid_t* VendorGuid + ); + + +typedef efi_status_t (*efi_set_variable_t) + ( + efi_char16_t* VariableName, + efi_guid_t* VendorGuid, + uint32_t Attributes, + uint64_t DataSize, + void* Data + ); + + +/* + * Misc + */ + +typedef enum +{ + EfiResetCold, + EfiResetWarm, + EfiResetShutdown +} efi_reset_type_t; + + +typedef efi_status_t (*efi_reset_system_t) + ( + efi_reset_type_t ResetType, + efi_status_t ResetStatus, + uint64_t DataSize, + efi_char16_t* ResetData + ); + +typedef efi_status_t (*efi_get_next_high_mono_count_t) (uint32_t* HighCount); + + +/* + * EFI Runtime Serivces Table + */ + +#define EFI_RUNTIME_SERVICES_SIGNATURE 0x56524553544e5552 +#define EFI_RUNTIME_SERVICES_REVISION (EFI_SPECIFICATION_MAJOR_REVISION<<16) | (EFI_SPECIFICATION_MINOR_REVISION) + +typedef struct +{ + efi_table_header_t Hdr; + /* Time services */ + efi_get_time_t GetTime; + efi_set_time_t SetTime; + efi_get_wakeup_time_t GetWakeupTime; + efi_set_wakeup_time_t SetWakeupTime; + /* Virtual memory services */ + efi_set_virtual_address_map_t SetVirtualAddressMap; + efi_convert_pointer_t ConvertPointer; + /* Variable serviers */ + efi_get_variable_t GetVariable; + efi_get_next_variable_name_t GetNextVariableName; + efi_set_variable_t SetVariable; + /* Misc */ + efi_get_next_high_mono_count_t GetNextHighMonotonicCount; + efi_reset_system_t ResetSystem; + +} efi_runtime_services_t; + + +#define EFI_SPECIFICATION_MAJOR_REVISION 1 +#define EFI_SYSTEM_TABLE_SIGNATURE 0x5453595320494249 +#define EFI_SYSTEM_TABLE_REVISION (EFI_SPECIFICATION_MAJOR_REVISION<<16) | (EFI_SPECIFICATION_MINOR_REVISION) + +struct efi_system_table +{ + efi_table_header_t Hdr; + + uint64_t FirmwareVendor; // phys addr of CHAR16 + uint32_t FirmwareRevision; // Firmware vendor specific + + efi_handle_t ConsoleInHandle; + uint64_t ConIn; + + efi_handle_t ConsoleOutHandle; + uint64_t ConOut; + + efi_handle_t StandardErrorHandle; + uint64_t StdErr; + + uint64_t RuntimeServices; // phys addr + uint64_t BootServices; // phys addr + + uint64_t NumberOfTableEntries; // Number of entries in Config + uint64_t ConfigurationTable; // phys addr of ConfigTable +}; + +typedef struct efi_system_table efi_system_table_t; + + +#define EFI_PAGE_SIZE 4096 +#define EFI_PAGE_MASK 0xFFF +#define EFI_PAGE_SHIFT 12 + +#define EFI_SIZE_TO_PAGES(a) \ + ( ((a) >> EFI_PAGE_SHIFT) + ((a) & EFI_PAGE_MASK ? 1 : 0) ) + + +void init_efi(void); +int efi_get_time(efi_time_t* tmP); +efi_status_t ia64_call_efi_physical(void *, ...); + + +#endif /* _EFI_H_ */ diff -r d7f7021902a2 -r 3e3e92fb854a extras/mini-os/include/ia64/hypercall-ia64.h --- /dev/null Thu Jan 1 00:00:00 1970 +0000 +++ b/extras/mini-os/include/ia64/hypercall-ia64.h Tue Feb 6 07:41:50 2007 +0100 @@ -0,0 +1,232 @@ +/****************************************************************************** + * hypercall.h + * + * Mini-OS-specific hypervisor handling for ia64. + * + * Copyright (c) 2002-2004, K A Fraser + * Changes: 2007 Dietmar Hahn + * + * This program is free software; you can redistribute it and/or + * modify it under the terms of the GNU General Public License version 2 + * as published by the Free Software Foundation; or, when distributed + * separately from the Linux kernel or incorporated into other + * software packages, subject to the following license: + * + * Permission is hereby granted, free of charge, to any person obtaining a copy + * of this source file (the "Software"), to deal in the Software without + * restriction, including without limitation the rights to use, copy, modify, + * merge, publish, distribute, sublicense, and/or sell copies of the Software, + * and to permit persons to whom the Software is furnished to do so, subject to + * the following conditions: + * + * The above copyright notice and this permission notice shall be included in + * all copies or substantial portions of the Software. + * + * THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR + * IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY, + * FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE + * AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER + * LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING + * FROM, OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS + * IN THE SOFTWARE. + */ + +#ifndef __HYPERCALL_H__ +#define __HYPERCALL_H__ + +#include "lib.h" /* memcpy() */ +#include "errno.h" /* ENOSYS() */ +#include +#include +#include + +#ifndef _HYPERVISOR_H_ +# error "please don't include this file directly" +#endif + + // See linux/compiler.h +#define likely(x) __builtin_expect(!!(x), 1) +#define unlikely(x) __builtin_expect(!!(x), 0) + +extern unsigned long __hypercall(unsigned long a1, unsigned long a2, + unsigned long a3, unsigned long a4, + unsigned long a5, unsigned long cmd); +/* + * Assembler stubs for hyper-calls. + */ + +#define _hypercall0(type, name) \ +({ \ + long __res; \ + __res=__hypercall(0, 0, 0, 0, 0, __HYPERVISOR_##name); \ + (type)__res; \ +}) + +#define _hypercall1(type, name, a1) \ +({ \ + long __res; \ + __res = __hypercall((unsigned long)a1, \ + 0, 0, 0, 0, __HYPERVISOR_##name); \ + (type)__res; \ +}) + +#define _hypercall2(type, name, a1, a2) \ +({ \ + long __res; \ + __res = __hypercall((unsigned long)a1, \ + (unsigned long)a2, \ + 0, 0, 0, __HYPERVISOR_##name); \ + (type)__res; \ +}) + +#define _hypercall3(type, name, a1, a2, a3) \ +({ \ + long __res; \ + __res = __hypercall((unsigned long)a1, \ + (unsigned long)a2, \ + (unsigned long)a3, \ + 0, 0, __HYPERVISOR_##name); \ + (type)__res; \ +}) + +#define _hypercall4(type, name, a1, a2, a3, a4) \ +({ \ + long __res; \ + __res = __hypercall((unsigned long)a1, \ + (unsigned long)a2, \ + (unsigned long)a3, \ + (unsigned long)a4, \ + 0, __HYPERVISOR_##name); \ + (type)__res; \ +}) + +#define _hypercall5(type, name, a1, a2, a3, a4, a5) \ +({ \ + long __res; \ + __res = __hypercall((unsigned long)a1, \ + (unsigned long)a2, \ + (unsigned long)a3, \ + (unsigned long)a4, \ + (unsigned long)a5, \ + __HYPERVISOR_##name); \ + (type)__res; \ +}) + + +extern unsigned long xencomm_vaddr_to_paddr(unsigned long vaddr); +struct xencomm_handle; + +/* Inline version. To be used only on linear space (kernel space). */ +static inline struct xencomm_handle * +xencomm_create_inline(void *buffer) +{ + unsigned long paddr; + + paddr = xencomm_vaddr_to_paddr((unsigned long)buffer); + return (struct xencomm_handle *)(paddr | XENCOMM_INLINE_FLAG); +} + +static inline int +HYPERVISOR_sched_op_compat(int cmd, unsigned long arg) +{ + return _hypercall2(int, sched_op_compat, cmd, arg); +} + + +static inline int +xencomm_arch_sched_op(int cmd, void *arg) +{ + struct xencomm_handle *newArg; + newArg = xencomm_create_inline(arg); + return _hypercall2(int, sched_op, cmd, newArg); +} + +#define HYPERVISOR_sched_op xencomm_arch_sched_op + +//static inline int +//HYPERVISOR_multicall(void *call_list, int nr_calls) +//{ +// return _hypercall2(int, multicall, call_list, nr_calls); +//} + +static inline int +xencomm_arch_event_channel_op(int cmd, void *arg) +{ + int rc; + struct xencomm_handle *newArg; + newArg = xencomm_create_inline(arg); + rc = _hypercall2(int, event_channel_op, cmd, newArg); + if(unlikely(rc == -ENOSYS)) + { + struct evtchn_op op; + op.cmd = cmd; + memcpy(&op.u, arg, sizeof(op.u)); + rc = _hypercall1(int, event_channel_op_compat, &op); + } + return rc; +} +#define HYPERVISOR_event_channel_op xencomm_arch_event_channel_op + +static inline int +xencomm_arch_xen_version(int cmd, struct xencomm_handle *arg) +{ + return _hypercall2(int, xen_version, cmd, arg); +} + +static inline int +xencomm_arch_xen_feature(int cmd, struct xencomm_handle *arg) +{ + struct xencomm_handle *newArg; + newArg = xencomm_create_inline(arg); + return _hypercall2(int, xen_version, cmd, newArg); +} + +static inline int +HYPERVISOR_xen_version(int cmd, void *arg) +{ + switch(cmd) + { + case XENVER_version: + return xencomm_arch_xen_version(cmd, 0); + case XENVER_get_features: + return xencomm_arch_xen_feature(cmd, arg); + default: return -1; + } +} + +static inline int +xencomm_arch_console_io(int cmd, int count, char *str) +{ + struct xencomm_handle *newStr; + newStr = xencomm_create_inline(str); + + return _hypercall3(int, console_io, cmd, count, newStr); +} + + +#define HYPERVISOR_console_io xencomm_arch_console_io + + +static inline int +xencomm_arch_callback_op(int cmd, void *arg) +{ + struct xencomm_handle *newArg; + newArg = xencomm_create_inline(arg); + return _hypercall2(int, callback_op, cmd, newArg); +} +#define HYPERVISOR_callback_op xencomm_arch_callback_op + +static inline int +xencomm_arch_hypercall_grant_table_op(unsigned int cmd, + struct xencomm_handle *uop, + unsigned int count) +{ + return _hypercall3(int, grant_table_op, cmd, uop, count); +} + +int HYPERVISOR_grant_table_op(unsigned int cmd, void *uop, unsigned int count); + + + + +#endif /* __HYPERCALL_H__ */ diff -r d7f7021902a2 -r 3e3e92fb854a extras/mini-os/include/ia64/ia64_cpu.h --- /dev/null Thu Jan 1 00:00:00 1970 +0000 +++ b/extras/mini-os/include/ia64/ia64_cpu.h Tue Feb 6 07:41:50 2007 +0100 @@ -0,0 +1,763 @@ +/* + * This code is mostly taken from FreeBSD machine/ia64_cpu.h + * Changes: Dietmar Hahn + * + * + **************************************************************************** + * Copyright (c) 2000 Doug Rabson + * All rights reserved. + * + * Redistribution and use in source and binary forms, with or without + * modification, are permitted provided that the following conditions + * are met: + * 1. Redistributions of source code must retain the above copyright + * notice, this list of conditions and the following disclaimer. + * 2. Redistributions in binary form must reproduce the above copyright + * notice, this list of conditions and the following disclaimer in the + * documentation and/or other materials provided with the distribution. + * + * THIS SOFTWARE IS PROVIDED BY THE AUTHOR AND CONTRIBUTORS ``AS IS'' AND + * ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE + * IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE + * ARE DISCLAIMED. IN NO EVENT SHALL THE AUTHOR OR CONTRIBUTORS BE LIABLE + * FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL + * DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS + * OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) + * HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT + * LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY + * OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF + * SUCH DAMAGE. + * + */ + +#ifndef _MACHINE_IA64_CPU_H_ +#define _MACHINE_IA64_CPU_H_ + +#include "ia64_fpu.h" + + +/* + * Definition of Region Register bits (RR) + * + * RR bit field positions + */ +#define IA64_RR_VE 0 +#define IA64_RR_MBZ0 1 +#define IA64_RR_PS 2 +#define IA64_RR_PS_LEN 6 +#define IA64_RR_RID 8 +#define IA64_RR_RID_LEN 24 +#define IA64_RR_MBZ1 32 + +#define IA64_RR_IDX_POS 61 + +#define IA64_RR_VAL(size,rid) (((size) << IA64_RR_PS) | ((rid) << IA64_RR_RID)) + +/* + * Define Protection Key Register (PKR) + * + * PKR bit field positions + */ +#define IA64_PKR_V 0 +#define IA64_PKR_WD 1 +#define IA64_PKR_RD 2 +#define IA64_PKR_XD 3 +#define IA64_PKR_MBZ0 4 +#define IA64_PKR_KEY 8 +#define IA64_PKR_KEY_LEN 24 +#define IA64_PKR_MBZ1 32 + +#define IA64_PKR_VALID (1<func) +#define FDESC_GP(fn) (((struct ia64_fdesc *) fn)->gp) + + +/* + * Various special ia64 instructions. + */ + +/* + * Memory Fence. + */ +static __inline void +ia64_mf(void) +{ + __asm __volatile("mf" ::: "memory"); +} + +static __inline void +ia64_mf_a(void) +{ + __asm __volatile("mf.a"); +} + +/* + * Flush Cache. + */ +static __inline void +ia64_fc(uint64_t va) +{ + __asm __volatile("fc %0" :: "r"(va)); +} + +/* + * Sync instruction stream. + */ +static __inline void +ia64_sync_i(void) +{ + __asm __volatile("sync.i"); +} + +/* + * Calculate address in VHPT for va. + */ +static __inline uint64_t +ia64_thash(uint64_t va) +{ + uint64_t result; + __asm __volatile("thash %0=%1" : "=r" (result) : "r" (va)); + return result; +} + +/* + * Calculate VHPT tag for va. + */ +static __inline uint64_t +ia64_ttag(uint64_t va) +{ + uint64_t result; + __asm __volatile("ttag %0=%1" : "=r" (result) : "r" (va)); + return result; +} + +/* + * Convert virtual address to physical. + */ +static __inline uint64_t +ia64_tpa(uint64_t va) +{ + uint64_t result; + __asm __volatile("tpa %0=%1" : "=r" (result) : "r" (va)); + return result; +} + +/* + * Generate a ptc.e instruction. + */ +static __inline void +ia64_ptc_e(uint64_t v) +{ + __asm __volatile("ptc.e %0;; srlz.d;;" :: "r"(v)); +} + +/* + * Generate a ptc.g instruction. + */ +static __inline void +ia64_ptc_g(uint64_t va, uint64_t size) +{ + __asm __volatile("ptc.g %0,%1;; srlz.d;;" :: "r"(va), "r"(size<<2)); +} + +/* + * Generate a ptc.ga instruction. + */ +static __inline void +ia64_ptc_ga(uint64_t va, uint64_t size) +{ + __asm __volatile("ptc.ga %0,%1;; srlz.d;;" :: "r"(va), "r"(size<<2)); +} + +/* + * Generate a ptc.l instruction. + */ +static __inline void +ia64_ptc_l(uint64_t va, uint64_t size) +{ + __asm __volatile("ptc.l %0,%1;; srlz.d;;" :: "r"(va), "r"(size<<2)); +} + +/* + * Read the value of psr. + */ +static __inline uint64_t +ia64_get_psr(void) +{ + uint64_t result; + __asm __volatile("mov %0=psr;;" : "=r" (result)); + return result; +} + +static __inline void \ +ia64_set_psr(uint64_t v) \ +{ \ + __asm __volatile("mov psr.l=%0" :: "r" (v)); \ +} + +static __inline void +ia64_srlz_d(void) +{ + __asm __volatile("srlz.d;;"); +} + +static __inline void +disable_intr(void) +{ + __asm __volatile ("rsm psr.ic|psr.i"); +} + +static __inline void +enable_intr(void) +{ + __asm __volatile ("ssm psr.ic|psr.i"); +} + + + +/* + * Define accessors for application registers. + */ + +#define IA64_AR(name) \ + \ +static __inline uint64_t \ +ia64_get_##name(void) \ +{ \ + uint64_t result; \ + __asm __volatile(";;mov %0=ar." #name ";;" : "=r" (result)); \ + return result; \ +} \ + \ +static __inline void \ +ia64_set_##name(uint64_t v) \ +{ \ + __asm __volatile("mov ar." #name "=%0" :: "r" (v)); \ +} + +IA64_AR(k0) +IA64_AR(k1) +IA64_AR(k2) +IA64_AR(k3) +IA64_AR(k4) +IA64_AR(k5) +IA64_AR(k6) +IA64_AR(k7) + +IA64_AR(rsc) +IA64_AR(bsp) +IA64_AR(bspstore) +IA64_AR(rnat) + +IA64_AR(fcr) + +IA64_AR(eflag) +IA64_AR(csd) +IA64_AR(ssd) +IA64_AR(cflg) +IA64_AR(fsr) +IA64_AR(fir) +IA64_AR(fdr) + +IA64_AR(ccv) + +IA64_AR(unat) + +IA64_AR(fpsr) + +IA64_AR(itc) + +IA64_AR(pfs) +IA64_AR(lc) +IA64_AR(ec) + +/* + * Define accessors for control registers. + */ + +#define IA64_CR(name) \ + \ +static __inline uint64_t \ +ia64_get_##name(void) \ +{ \ + uint64_t result; \ + __asm __volatile("mov %0=cr." #name : "=r" (result)); \ + return result; \ +} \ + \ +static __inline void \ +ia64_set_##name(uint64_t v) \ +{ \ + __asm __volatile("mov cr." #name "=%0" :: "r" (v)); \ +} + +IA64_CR(dcr) +IA64_CR(itm) +IA64_CR(iva) + +IA64_CR(pta) + +IA64_CR(ipsr) +IA64_CR(isr) + +IA64_CR(iip) +IA64_CR(ifa) +IA64_CR(itir) +IA64_CR(iipa) +IA64_CR(ifs) +IA64_CR(iim) +IA64_CR(iha) + +IA64_CR(lid) +IA64_CR(ivr) +IA64_CR(tpr) +IA64_CR(eoi) +IA64_CR(irr0) +IA64_CR(irr1) +IA64_CR(irr2) +IA64_CR(irr3) +IA64_CR(itv) +IA64_CR(pmv) +IA64_CR(cmcv) + +IA64_CR(lrr0) +IA64_CR(lrr1) + +#define IA64_GR(name) \ + \ +static __inline uint64_t \ +ia64_get_##name(void) \ +{ \ + uint64_t result; \ + __asm __volatile("mov %0=" #name : "=r" (result)); \ + return result; \ +} \ + \ +static __inline void \ +ia64_set_##name(uint64_t v) \ +{ \ + __asm __volatile("mov " #name "=%0" :: "r" (v)); \ +} + +IA64_GR(sp) +IA64_GR(b0) +IA64_GR(r13) // tp +IA64_GR(r32) +IA64_GR(r33) +IA64_GR(r37) +IA64_GR(r38) +IA64_GR(r39) + + + +/* + * Write a region register. + */ +static __inline void +ia64_set_rr(uint64_t rrbase, uint64_t v) +{ + __asm __volatile("mov rr[%0]=%1;; srlz.d;;" + :: "r"(rrbase), "r"(v) : "memory"); +} + +/* + * Read a region register. + */ +static __inline uint64_t +ia64_get_rr(uint64_t rrbase) +{ + uint64_t v; + __asm __volatile("mov %1=rr[%0];;" + : "=r" (v) : "r"(rrbase) : "memory"); + return v; +} + + +/* + * Read a CPUID register. + */ +static __inline uint64_t +ia64_get_cpuid(int i) +{ + uint64_t result; + __asm __volatile("mov %0=cpuid[%1]" + : "=r" (result) : "r"(i)); + return result; +} + + +struct trap_frame +{ + uint64_t rsc; + uint64_t ndirty; /* number of dirty regs */ + uint64_t ssd; + uint64_t iip; /* interrupted ip */ + uint64_t ipsr; /* interrupted psr */ + uint64_t ifs; /* interruption func status register */ + + uint16_t trap_num; /* Trap num, index in trap_vec */ + uint64_t cfm; /* current frame marker */ + uint64_t pfs; /* previous function state ar64 */ + uint64_t bsp; /* backing store pointer ar17 */ + uint64_t rnat; /* rse nat collection ar19 */ + uint64_t csd; /* comp and store data reg ar25 */ + uint64_t ccv; /* comp and xchange val reg ar32 */ + uint64_t unat; /* */ + uint64_t fpsr; /* floating point state reg ar40 */ + uint64_t pr; /* predicate regs 0-63 */ + + uint64_t gp; /* the gp pointer */ + uint64_t sp; /* stack pointer */ + uint64_t tp; /* thread pointer */ + + uint64_t r2; /* global reg 2 */ + uint64_t r3; + uint64_t r8; + uint64_t r9; + uint64_t r10; + uint64_t r11; + uint64_t r14; + uint64_t r15; + uint64_t r16; + uint64_t r17; + uint64_t r18; + uint64_t r19; + uint64_t r20; + uint64_t r21; + uint64_t r22; + uint64_t r23; + uint64_t r24; + uint64_t r25; + uint64_t r26; + uint64_t r27; + uint64_t r28; + uint64_t r29; + uint64_t r30; + uint64_t r31; + + uint64_t b0; + uint64_t b6; + uint64_t b7; + + ia64_fpreg_t f6; /* floating point register 6 */ + ia64_fpreg_t f7; + ia64_fpreg_t f8; + ia64_fpreg_t f9; + ia64_fpreg_t f10; + ia64_fpreg_t f11; + + uint64_t ifa; /* interruption faulting address */ + uint64_t isr; /* interruption status register */ + uint64_t iim; /* interruption immediate register */ +}; + +typedef struct trap_frame trap_frame_t; + + +#endif /* __ASSEMBLY__ */ + + /* Page access parameters. */ +#define PTE_P_SHIFT 0 +#define PTE_P 1 + +#define PTE_MA_SHIFT 2 +#define PTE_MA_WB 0 + +#define PTE_A_SHIFT 5 +#define PTE_A 1 +#define PTE_D_SHIFT 6 +#define PTE_D 1 + +#define PTE_AR_SHIFT 9 +#define PTE_AR_R 0 +#define PTE_AR_RX 1 +#define PTE_AR_RW 2 +#define PTE_AR_RWX 3 +#define PTE_AR_R_RW 4 +#define PTE_AR_RX_RWX 5 +#define PTE_AR_RWX_RW 6 + /* privilege level */ +#define PTE_PL_SHIFT 7 +#define PTE_PL_KERN 0 /* used for kernel */ + /* page size */ +#define PTE_PS_4K 12 +#define PTE_PS_8K 13 +#define PTE_PS_16K 14 +#define PTE_PS_64K 16 +#define PTE_PS_256K 18 +#define PTE_PS_1M 20 +#define PTE_PS_4M 22 +#define PTE_PS_16M 24 +#define PTE_PS_64M 26 +#define PTE_PS_256M 28 + + + /* Some offsets for ia64_pte_t. */ +#define PTE_OFF_P 0 +#define PTE_OFF_MA 3 +#define PTE_OFF_A 5 +#define PTE_OFF_D 6 +#define PTE_OFF_PL 7 +#define PTE_OFF_AR 9 +#define PTE_OFF_PPN 12 +#define PTE_OFF_ED 52 + +#if !defined(_ASM) && !defined(__ASSEMBLY__) +/* + * A short-format VHPT entry. Also matches the TLB insertion format. + */ +typedef struct +{ + uint64_t pte_p :1; /* bits 0..0 */ + uint64_t pte_rv1:1; /* bits 1..1 */ + uint64_t pte_ma :3; /* bits 2..4 */ + uint64_t pte_a :1; /* bits 5..5 */ + uint64_t pte_d :1; /* bits 6..6 */ + uint64_t pte_pl :2; /* bits 7..8 */ + uint64_t pte_ar :3; /* bits 9..11 */ + uint64_t pte_ppn:38; /* bits 12..49 */ + uint64_t pte_rv2:2; /* bits 50..51 */ + uint64_t pte_ed :1; /* bits 52..52 */ + uint64_t pte_ig :11; /* bits 53..63 */ +} ia64_pte_t; + + +/* + * A long-format VHPT entry. + */ +typedef struct +{ + uint64_t pte_p :1; /* bits 0..0 */ + uint64_t pte_rv1 :1; /* bits 1..1 */ + uint64_t pte_ma :3; /* bits 2..4 */ + uint64_t pte_a :1; /* bits 5..5 */ + uint64_t pte_d :1; /* bits 6..6 */ + uint64_t pte_pl :2; /* bits 7..8 */ + uint64_t pte_ar :3; /* bits 9..11 */ + uint64_t pte_ppn :38; /* bits 12..49 */ + uint64_t pte_rv2 :2; /* bits 50..51 */ + uint64_t pte_ed :1; /* bits 52..52 */ + uint64_t pte_ig :11; /* bits 53..63 */ + uint64_t pte_rv3 :2; /* bits 0..1 */ + uint64_t pte_ps :6; /* bits 2..7 */ + uint64_t pte_key :24; /* bits 8..31 */ + uint64_t pte_rv4 :32; /* bits 32..63 */ + uint64_t pte_tag; /* includes ti */ + uint64_t pte_chain; /* pa of collision chain */ +} ia64_lpte_t; + +#endif /* __ASSEMBLY__ */ + + + + + +#endif /* _MACHINE_IA64_CPU_H_ */ + diff -r d7f7021902a2 -r 3e3e92fb854a extras/mini-os/include/ia64/ia64_fpu.h --- /dev/null Thu Jan 1 00:00:00 1970 +0000 +++ b/extras/mini-os/include/ia64/ia64_fpu.h Tue Feb 6 07:41:50 2007 +0100 @@ -0,0 +1,104 @@ +/* + * The code is taken from FreeBSD. + * Changes: Dietmar Hahn + * + **************************************************************************** + * Copyright (c) 1998 Doug Rabson + * All rights reserved. + * + * Redistribution and use in source and binary forms, with or without + * modification, are permitted provided that the following conditions + * are met: + * 1. Redistributions of source code must retain the above copyright + * notice, this list of conditions and the following disclaimer. + * 2. Redistributions in binary form must reproduce the above copyright + * notice, this list of conditions and the following disclaimer in the + * documentation and/or other materials provided with the distribution. + * + * THIS SOFTWARE IS PROVIDED BY THE AUTHOR AND CONTRIBUTORS ``AS IS'' AND + * ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE + * IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE + * ARE DISCLAIMED. IN NO EVENT SHALL THE AUTHOR OR CONTRIBUTORS BE LIABLE + * FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL + * DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS + * OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) + * HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT + * LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY + * OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF + * SUCH DAMAGE. + * + */ + +#ifndef _MACHINE_FPU_H_ +#define _MACHINE_FPU_H_ + +#include "os.h" + +/* + * Floating point status register bits. + */ +#define IA64_FPSR_TRAP_VD UL_CONST(0x0000000000000001) +#define IA64_FPSR_TRAP_DD UL_CONST(0x0000000000000002) +#define IA64_FPSR_TRAP_ZD UL_CONST(0x0000000000000004) +#define IA64_FPSR_TRAP_OD UL_CONST(0x0000000000000008) +#define IA64_FPSR_TRAP_UD UL_CONST(0x0000000000000010) +#define IA64_FPSR_TRAP_ID UL_CONST(0x0000000000000020) +#define IA64_FPSR_SF(i,v) ((v) << ((i)*13+6)) + +#define IA64_SF_FTZ UL_CONST(0x0001) +#define IA64_SF_WRE UL_CONST(0x0002) +#define IA64_SF_PC UL_CONST(0x000c) +#define IA64_SF_PC_0 UL_CONST(0x0000) +#define IA64_SF_PC_1 UL_CONST(0x0004) +#define IA64_SF_PC_2 UL_CONST(0x0008) +#define IA64_SF_PC_3 UL_CONST(0x000c) +#define IA64_SF_RC UL_CONST(0x0030) +#define IA64_SF_RC_NEAREST UL_CONST(0x0000) +#define IA64_SF_RC_NEGINF UL_CONST(0x0010) +#define IA64_SF_RC_POSINF UL_CONST(0x0020) +#define IA64_SF_RC_TRUNC UL_CONST(0x0030) +#define IA64_SF_TD UL_CONST(0x0040) +#define IA64_SF_V UL_CONST(0x0080) +#define IA64_SF_D UL_CONST(0x0100) +#define IA64_SF_Z UL_CONST(0x0200) +#define IA64_SF_O UL_CONST(0x0400) +#define IA64_SF_U UL_CONST(0x0800) +#define IA64_SF_I UL_CONST(0x1000) + +#define IA64_SF_DEFAULT (IA64_SF_PC_3 | IA64_SF_RC_NEAREST) + +#define IA64_FPSR_DEFAULT (IA64_FPSR_TRAP_VD \ + | IA64_FPSR_TRAP_DD \ + | IA64_FPSR_TRAP_ZD \ + | IA64_FPSR_TRAP_OD \ + | IA64_FPSR_TRAP_UD \ + | IA64_FPSR_TRAP_ID \ + | IA64_FPSR_SF(0, IA64_SF_DEFAULT) \ + | IA64_FPSR_SF(1, (IA64_SF_DEFAULT \ + | IA64_SF_TD \ + | IA64_SF_WRE)) \ + | IA64_FPSR_SF(2, (IA64_SF_DEFAULT \ + | IA64_SF_TD)) \ + | IA64_FPSR_SF(3, (IA64_SF_DEFAULT \ + | IA64_SF_TD))) + + + +#ifndef __ASSEMBLY__ + + /* This is from sys/cdefs.h in FreeBSD */ +#define __aligned(x) __attribute__((__aligned__(x))) + + /* A single Floating Point register. */ +struct ia64_fpreg +{ + uint8_t fpr_bits[16]; +} __aligned(16); + +typedef struct ia64_fpreg ia64_fpreg_t; + +#endif /* __ASSEMBLY__ */ + + + +#endif /* ! _MACHINE_FPU_H_ */ diff -r d7f7021902a2 -r 3e3e92fb854a extras/mini-os/include/ia64/os.h --- /dev/null Thu Jan 1 00:00:00 1970 +0000 +++ b/extras/mini-os/include/ia64/os.h Tue Feb 6 07:41:50 2007 +0100 @@ -0,0 +1,318 @@ +/* + * Copyright (C) 2007 - Dietmar Hahn + * + **************************************************************************** + * Permission is hereby granted, free of charge, to any person obtaining a copy + * of this software and associated documentation files (the "Software"), to + * deal in the Software without restriction, including without limitation the + * rights to use, copy, modify, merge, publish, distribute, sublicense, and/or + * sell copies of the Software, and to permit persons to whom the Software is + * furnished to do so, subject to the following conditions: + * + * The above copyright notice and this permission notice shall be included in + * all copies or substantial portions of the Software. + * + * THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR + * IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY, + * FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE + * AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER + * LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING + * FROM, OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER + * DEALINGS IN THE SOFTWARE. + */ + + +#if !defined(__OS_H__) +#define __OS_H__ + +#if !defined(__ASSEMBLY__) + +#include "types.h" +#include "ia64_cpu.h" +#include "atomic.h" +#include "efi.h" +#include "sal.h" +#include "pal.h" +#include "hypervisor.h" + + +typedef uint64_t paddr_t; /* Physical address. */ +typedef uint64_t caddr_t; /* rr7/kernel memory address. */ + +#include "page.h" +#include "mm.h" + + +void do_exit(void); +void arch_init(start_info_t *si); /* in common.c */ +void arch_print_info(void); /* in common.c */ + + + /* Size of xen_ia64_boot_param.command_line */ +#define COMMAND_LINE_SIZE 512 + +struct xen_ia64_boot_param* ia64_boot_paramP; +extern struct xen_ia64_boot_param ia64BootParamG; +extern char boot_cmd_line[]; +extern efi_system_table_t* efiSysTableP; +extern int bootverbose; + +extern void ia64_probe_sapics(void); + + + + /* Contains the needed stuff from efi. */ +struct efi +{ + + efi_system_table_t* efiSysTableP; + efi_set_virtual_address_map_t setVirtAddrMapF; + efi_get_time_t getTimeF; + efi_reset_system_t resetSystemF; + +}; + +struct machine_fw +{ + + struct efi efi; + + uint64_t ia64_port_base; /* physical address */ + uint64_t ia64_pal_base; /* virtual rr7 address */ + + sal_system_table_t* ia64_sal_tableP; + sal_entry_t* ia64_sal_entryP;/* SAL_PROC entrypoint */ + + uint64_t ia64_efi_acpi_table; /* physical address */ + uint64_t ia64_efi_acpi20_table; /* physical address */ + + uint64_t mach_mem_start; /* phys start adress of machine memory */ + uint64_t mach_mem_size; /* size of machine memory */ + + uint64_t kernstart; /* virt address of kern text start */ + uint64_t kernend; + uint64_t kernpstart; /* phys address of kern text start */ + uint64_t kernpend; + +}; + +extern struct machine_fw machineFwG; + +#define ia64_sal_entry machineFwG.ia64_sal_entryP + + +#define smp_processor_id() 0 + + +static inline uint64_t +xchg8(uint64_t* ptr, uint64_t x) \ +{ + uint64_t oldVal; + asm volatile ("xchg8 %0=[%1],%2" : "=r" (oldVal) + : "r" (ptr), "r" (x) : "memory"); + return oldVal; +} +#define xchg xchg8 + + + // Counts the number of 1-bits in x. +#if __GNUC__ >= 4 || (__GNUC__ == 3 && __GNUC_MINOR__ >= 4) +# define get_popcnt(x) __builtin_popcountl(x) +#else +# define get_popcnt(x) \ + ({ \ + uint64_t num; \ + asm ("popcnt %0=%1" : "=r" (num) : "r" (x)); \ + \ + num; \ + }) +#endif + +/** + * __ffs - find first bit in word. + * @x: The word to search + * + * Undefined if no bit exists, so code should check against 0 first. + */ +static inline unsigned long +__ffs (unsigned long x) +{ + unsigned long result; + + result = get_popcnt((x-1) & ~x); + return result; +} + + +static inline void +synch_clear_bit(int num, volatile void *addr) +{ + clear_bit(num, addr); +} + +static inline void +synch_set_bit(int num, volatile void *addr) +{ + set_bit(num, addr); +} + +static inline int +synch_test_bit(int nr, const volatile void *addr) +{ + return test_bit(nr, addr); +} + +static inline int +synch_test_and_set_bit(int num, volatile void * addr) +{ + return test_and_set_bit(num, addr); +} + + +#define synch_cmpxchg(ptr, old, new) \ +((__typeof__(*(ptr)))__synch_cmpxchg((ptr),\ + (unsigned long)(old), \ + (unsigned long)(new), \ + sizeof(*(ptr)))) + +static inline unsigned long +__synch_cmpxchg(volatile void *ptr, uint64_t old, uint64_t new, int size) +{ + switch (size) + { + case 1: return ia64_cmpxchg_acq_8(ptr, old, new); + case 2: return ia64_cmpxchg_acq_16(ptr, old, new); + case 4: return ia64_cmpxchg_acq_32(ptr, old, new); + case 8: return ia64_cmpxchg_acq_64(ptr, old, new); + } + return ia64_cmpxchg_acq_64(ptr, old, new); +} + +/* + * Force a proper event-channel callback from Xen after clearing the + * callback mask. We do this in a very simple manner, by making a call + * down into Xen. The pending flag will be checked by Xen on return. + */ +static inline void +force_evtchn_callback(void) +{ + (void)HYPERVISOR_xen_version(0, NULL); +} + +extern shared_info_t *HYPERVISOR_shared_info; + +static inline int +HYPERVISOR_shutdown( + unsigned int reason) +{ + struct sched_shutdown sched_shutdown = { + .reason = reason + }; + + int rc = HYPERVISOR_sched_op(SCHEDOP_shutdown, &sched_shutdown); + + if (rc == -ENOSYS) + rc = HYPERVISOR_sched_op_compat(SCHEDOP_shutdown, reason); + + return rc; +} + + +/* + * This code is from the originally os.h and should be put in a + * common header file! + */ + +/* + * The use of 'barrier' in the following reflects their use as local-lock + * operations. Reentrancy must be prevented (e.g., __cli()) /before/ following + * critical operations are executed. All critical operations must complete + * /before/ reentrancy is permitted (e.g., __sti()). Alpha architecture also + * includes these barriers, for example. + */ + +#define __cli() \ +do { \ + vcpu_info_t *_vcpu; \ + _vcpu = &HYPERVISOR_shared_info->vcpu_info[smp_processor_id()]; \ + _vcpu->evtchn_upcall_mask = 1; \ + barrier(); \ +} while (0) + +#define __sti() \ +do { \ + vcpu_info_t *_vcpu; \ + barrier(); \ + _vcpu = &HYPERVISOR_shared_info->vcpu_info[smp_processor_id()]; \ + _vcpu->evtchn_upcall_mask = 0; \ + barrier(); /* unmask then check (avoid races) */ \ + if ( unlikely(_vcpu->evtchn_upcall_pending) ) \ + force_evtchn_callback(); \ +} while (0) + +#define __save_flags(x) \ +do { \ + vcpu_info_t *_vcpu; \ + _vcpu = &HYPERVISOR_shared_info->vcpu_info[smp_processor_id()]; \ + (x) = _vcpu->evtchn_upcall_mask; \ +} while (0) + +#define __restore_flags(x) \ +do { \ + vcpu_info_t *_vcpu; \ + barrier(); \ + _vcpu = &HYPERVISOR_shared_info->vcpu_info[smp_processor_id()]; \ + if ((_vcpu->evtchn_upcall_mask = (x)) == 0) { \ + barrier(); /* unmask then check (avoid races) */ \ + if ( unlikely(_vcpu->evtchn_upcall_pending) ) \ + force_evtchn_callback(); \ + }\ +} while (0) + +#define safe_halt() ((void)0) + +#define __save_and_cli(x) \ +do { \ + vcpu_info_t *_vcpu; \ + _vcpu = &HYPERVISOR_shared_info->vcpu_info[smp_processor_id()]; \ + (x) = _vcpu->evtchn_upcall_mask; \ + _vcpu->evtchn_upcall_mask = 1; \ + barrier(); \ +} while (0) + +#define local_irq_save(x) __save_and_cli(x) +#define local_irq_restore(x) __restore_flags(x) +#define local_save_flags(x) __save_flags(x) +#define local_irq_disable() __cli() +#define local_irq_enable() __sti() + +#define irqs_disabled() \ + HYPERVISOR_shared_info->vcpu_info[smp_processor_id()].evtchn_upcall_mask + +/* This is a barrier for the compiler only, NOT the processor! */ +#define barrier() __asm__ __volatile__("": : :"memory") + +#define mb() ia64_mf() +#define rmb() mb() +#define wmb() mb() + + +#define BUG() \ + { printk("mini-os BUG at %s:%d!\n", __FILE__, __LINE__); do_exit(); } + + +#endif /* !defined(__ASSEMBLY__) */ + +#if defined(__ASSEMBLY__) + +#define UL_CONST(x) x +#define UL_TYPE(x) x + +#else /* defined(__ASSEMBLY__) */ + +#define UL_CONST(x) x##UL +#define UL_TYPE(x) ((uint64_t)x) + +#endif /* defined(__ASSEMBLY__) */ + +#endif /* !defined(__OS_H__) */ diff -r d7f7021902a2 -r 3e3e92fb854a extras/mini-os/include/ia64/page.h --- /dev/null Thu Jan 1 00:00:00 1970 +0000 +++ b/extras/mini-os/include/ia64/page.h Tue Feb 6 07:41:50 2007 +0100 @@ -0,0 +1,116 @@ +/* + * Copyright (C) 2007 - Dietmar Hahn + * Common stuff for memory and page handling. + * Parts are taken from FreeBSD. + * + **************************************************************************** + * Permission is hereby granted, free of charge, to any person obtaining a copy + * of this software and associated documentation files (the "Software"), to + * deal in the Software without restriction, including without limitation the + * rights to use, copy, modify, merge, publish, distribute, sublicense, and/or + * sell copies of the Software, and to permit persons to whom the Software is + * furnished to do so, subject to the following conditions: + * + * The above copyright notice and this permission notice shall be included in + * all copies or substantial portions of the Software. + * + * THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR + * IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY, + * FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE + * AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER + * LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING + * FROM, OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER + * DEALINGS IN THE SOFTWARE. + */ + + +#if !defined(__PAGE_H__) +#define __PAGE_H__ + +#include "os.h" +#include "ia64_cpu.h" + +#define PTE_KERNEL_ATTR ((PTE_P<> 61) + +#define IA64_PHYS_TO_RR5(x) ((x) | IA64_RR_BASE(5)) +#define IA64_PHYS_TO_RR7(x) ((x) | IA64_RR_BASE(7)) + +#define __pa(x) IA64_RR_MASK(x) +#define __va(x) IA64_PHYS_TO_RR7(x) + +#define roundup_page(x) ((((unsigned long)(x)) + PAGE_SIZE -1) & PAGE_MASK) +#define trunc_page(x) ((unsigned long)(x) & PAGE_MASK) + + +#if !defined(__ASSEMBLY__) + + + /* Start address of the page frame table. */ +extern uint64_t pft_start; + +extern paddr_t phys_avail[]; + +struct page +{ + uint64_t flags; +}; + +#define page_to_pfn(page) ((uint64_t)(page) >> PAGE_SHIFT) +#define pfn_to_page(pfn) ((uint64_t)pfn << PAGE_SHIFT) + /* Get phyiscal address of page of virtual address. */ +#define virt_to_page(addr) ((uint64_t)__pa(addr) & PAGE_MASK) +#define virt_to_pfn(addr) (page_to_pfn(virt_to_page(addr))) + + +#endif /* __ASSEMBLY__ */ + + + + /* For both see minios-ia64.lds. */ + /* This is where the kernel virtually starts. */ +#define KERNEL_START IA64_PHYS_TO_RR5(0x100000000) + /* !!!!! + * For physical start of kernel + * Currently used in arch/ia64/fw.S. + * !!!!! + */ +#define KERNEL_PHYS_START_SHIFT 20 + + /* A region 5 address to physical address */ +#define KERN_VIRT_2_PHYS(x) (((x) - KERNEL_START) + (1 << KERNEL_PHYS_START_SHIFT)) + + // This is xen specific ! +#define PAGE_SHIFT_XEN_16K 14 // For 16KB page size +#define mfn_to_virt(mfn) ((void*)__va((mfn) << PAGE_SHIFT_XEN_16K)) + + + +#endif /* !defined(__PAGE_H__) */ diff -r d7f7021902a2 -r 3e3e92fb854a extras/mini-os/include/ia64/pal.h --- /dev/null Thu Jan 1 00:00:00 1970 +0000 +++ b/extras/mini-os/include/ia64/pal.h Tue Feb 6 07:41:50 2007 +0100 @@ -0,0 +1,114 @@ +/* + * The code is taken from FreeBSD. + * Changes: Dietmar Hahn + * + **************************************************************************** + * Copyright (c) 2000 Doug Rabson + * All rights reserved. + * + * Redistribution and use in source and binary forms, with or without + * modification, are permitted provided that the following conditions + * are met: + * 1. Redistributions of source code must retain the above copyright + * notice, this list of conditions and the following disclaimer. + * 2. Redistributions in binary form must reproduce the above copyright + * notice, this list of conditions and the following disclaimer in the + * documentation and/or other materials provided with the distribution. + * + * THIS SOFTWARE IS PROVIDED BY THE AUTHOR AND CONTRIBUTORS ``AS IS'' AND + * ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE + * IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE + * ARE DISCLAIMED. IN NO EVENT SHALL THE AUTHOR OR CONTRIBUTORS BE LIABLE + * FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL + * DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS + * OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) + * HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT + * LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY + * OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF + * SUCH DAMAGE. + * + */ + +#ifndef _MACHINE_PAL_H_ +#define _MACHINE_PAL_H_ + +/* + * Architected static calling convention procedures. + */ +#define PAL_CACHE_FLUSH 1 +#define PAL_CACHE_INFO 2 +#define PAL_CACHE_INIT 3 +#define PAL_CACHE_SUMMARY 4 +#define PAL_MEM_ATTRIB 5 +#define PAL_PTCE_INFO 6 +#define PAL_VM_INFO 7 +#define PAL_VM_SUMMARY 8 +#define PAL_BUS_GET_FEATURES 9 +#define PAL_BUS_SET_FEATURES 10 +#define PAL_DEBUG_INFO 11 +#define PAL_FIXED_ADDR 12 +#define PAL_FREQ_BASE 13 +#define PAL_FREQ_RATIOS 14 +#define PAL_PERF_MON_INFO 15 +#define PAL_PLATFORM_ADDR 16 +#define PAL_PROC_GET_FEATURE 17 +#define PAL_PROC_SET_FEATURE 18 +#define PAL_RSE_INFO 19 +#define PAL_VERSION 20 +#define PAL_MC_CLEAR_LOG 21 +#define PAL_MC_DRAIN 22 +#define PAL_MC_DYNAMIC_STATE 24 +#define PAL_MC_ERROR_INFO 25 +#define PAL_MC_EXPECTED 23 +#define PAL_MC_REGISTER_MEM 27 +#define PAL_MC_RESUME 26 +#define PAL_HALT 28 +#define PAL_HALT_LIGHT 29 +#define PAL_COPY_INFO 30 +#define PAL_CACHE_LINE_INIT 31 +#define PAL_PMI_ENTRYPOINT 32 +#define PAL_ENTER_IA_32_ENV 33 +#define PAL_VM_PAGE_SIZE 34 +#define PAL_MEM_FOR_TEST 37 +#define PAL_CACHE_PROT_INFO 38 +#define PAL_REGISTER_INFO 39 +#define PAL_SHUTDOWN 40 +#define PAL_PREFETCH_VISIBILITY 41 + +/* + * Architected stacked calling convention procedures. + */ +#define PAL_COPY_PAL 256 +#define PAL_HALT_INFO 257 +#define PAL_TEST_PROC 258 +#define PAL_CACHE_READ 259 +#define PAL_CACHE_WRITE 260 +#define PAL_VM_TR_READ 261 + +/* + * Default physical address of the Processor Interrupt Block (PIB). + * See also: IA-64 SDM, rev 1.1, volume 2, page 5-31. + */ +#define PAL_PIB_DEFAULT_ADDR 0x00000000FEE00000L + +struct ia64_pal_result { + int64_t pal_status; + uint64_t pal_result[3]; +}; + +extern struct ia64_pal_result + ia64_call_pal_static(uint64_t proc, uint64_t arg1, + uint64_t arg2, uint64_t arg3); +/* +extern struct ia64_pal_result + ia64_call_pal_static_physical(uint64_t proc, uint64_t arg1, + uint64_t arg2, uint64_t arg3); +extern struct ia64_pal_result + ia64_call_pal_stacked(uint64_t proc, uint64_t arg1, + uint64_t arg2, uint64_t arg3); +extern struct ia64_pal_result + ia64_call_pal_stacked_physical(uint64_t proc, uint64_t arg1, + uint64_t arg2, uint64_t arg3); +*/ + +#endif /* _MACHINE_PAL_H_ */ diff -r d7f7021902a2 -r 3e3e92fb854a extras/mini-os/include/ia64/privop.h --- /dev/null Thu Jan 1 00:00:00 1970 +0000 +++ b/extras/mini-os/include/ia64/privop.h Tue Feb 6 07:41:50 2007 +0100 @@ -0,0 +1,97 @@ +#ifndef _ASM_IA64_MINIOS_PRIVOP_H +#define _ASM_IA64_MINIOS_PRIVOP_H + +/* + * Copyright (C) 2005 Hewlett-Packard Co + * Dan Magenheimer + * + * Paravirtualizations of privileged operations for Xen/ia64 + * + */ + + +#include + +#define IA64_PARAVIRTUALIZED + +/* At 1 MB, before per-cpu space but still addressable using addl instead + of movl. */ +#define XSI_BASE 0xfffffffffff00000 + +/* Address of mapped regs. */ +#define XMAPPEDREGS_BASE (XSI_BASE + XSI_SIZE) + +#ifdef __ASSEMBLY__ +#define XEN_HYPER_RFI break HYPERPRIVOP_RFI +#define XEN_HYPER_RSM_PSR_DT break HYPERPRIVOP_RSM_DT +#define XEN_HYPER_SSM_PSR_DT break HYPERPRIVOP_SSM_DT +#define XEN_HYPER_COVER break HYPERPRIVOP_COVER +#define XEN_HYPER_ITC_D break HYPERPRIVOP_ITC_D +#define XEN_HYPER_ITC_I break HYPERPRIVOP_ITC_I +#define XEN_HYPER_SSM_I break HYPERPRIVOP_SSM_I +#define XEN_HYPER_GET_IVR break HYPERPRIVOP_GET_IVR +#define XEN_HYPER_GET_TPR break HYPERPRIVOP_GET_TPR +#define XEN_HYPER_SET_TPR break HYPERPRIVOP_SET_TPR +#define XEN_HYPER_EOI break HYPERPRIVOP_EOI +#define XEN_HYPER_SET_ITM break HYPERPRIVOP_SET_ITM +#define XEN_HYPER_THASH break HYPERPRIVOP_THASH +#define XEN_HYPER_PTC_GA break HYPERPRIVOP_PTC_GA +#define XEN_HYPER_ITR_D break HYPERPRIVOP_ITR_D +#define XEN_HYPER_GET_RR break HYPERPRIVOP_GET_RR +#define XEN_HYPER_SET_RR break HYPERPRIVOP_SET_RR +#define XEN_HYPER_SET_KR break HYPERPRIVOP_SET_KR +#define XEN_HYPER_FC break HYPERPRIVOP_FC +#define XEN_HYPER_GET_CPUID break HYPERPRIVOP_GET_CPUID +#define XEN_HYPER_GET_PMD break HYPERPRIVOP_GET_PMD +#define XEN_HYPER_GET_EFLAG break HYPERPRIVOP_GET_EFLAG +#define XEN_HYPER_SET_EFLAG break HYPERPRIVOP_SET_EFLAG +#define XEN_HYPER_RSM_BE break HYPERPRIVOP_RSM_BE +#define XEN_HYPER_GET_PSR break HYPERPRIVOP_GET_PSR + +#define XSI_IFS (XSI_BASE + XSI_IFS_OFS) +#define XSI_PRECOVER_IFS (XSI_BASE + XSI_PRECOVER_IFS_OFS) +#define XSI_INCOMPL_REGFR (XSI_BASE + XSI_INCOMPL_REGFR_OFS) +#define XSI_IFA (XSI_BASE + XSI_IFA_OFS) +#define XSI_ISR (XSI_BASE + XSI_ISR_OFS) +#define XSI_IIM (XSI_BASE + XSI_IIM_OFS) +#define XSI_ITIR (XSI_BASE + XSI_ITIR_OFS) +#define XSI_PSR_I_ADDR (XSI_BASE + XSI_PSR_I_ADDR_OFS) +#define XSI_PSR_IC (XSI_BASE + XSI_PSR_IC_OFS) +#define XSI_IPSR (XSI_BASE + XSI_IPSR_OFS) +#define XSI_IIP (XSI_BASE + XSI_IIP_OFS) +#define XSI_BANK1_R16 (XSI_BASE + XSI_BANK1_R16_OFS) +#define XSI_BANKNUM (XSI_BASE + XSI_BANKNUM_OFS) +#define XSI_IHA (XSI_BASE + XSI_IHA_OFS) +#endif + +#ifndef __ASSEMBLY__ +#define XEN_HYPER_SSM_I asm("break %0" : : "i" (HYPERPRIVOP_SSM_I)) +#define XEN_HYPER_GET_IVR asm("break %0" : : "i" (HYPERPRIVOP_GET_IVR)) + +/************************************************/ +/* Instructions paravirtualized for performance */ +/************************************************/ + +/* Xen uses memory-mapped virtual privileged registers for access to many + * performance-sensitive privileged registers. Some, like the processor + * status register (psr), are broken up into multiple memory locations. + * Others, like "pend", are abstractions based on privileged registers. + * "Pend" is guaranteed to be set if reading cr.ivr would return a + * (non-spurious) interrupt. */ +#define XEN_MAPPEDREGS ((struct mapped_regs *)XMAPPEDREGS_BASE) +#define XSI_PSR_I \ + (*XEN_MAPPEDREGS->interrupt_mask_addr) +#define xen_get_virtual_psr_i() \ + (!XSI_PSR_I) +#define xen_set_virtual_psr_i(_val) \ + ({ XSI_PSR_I = (uint8_t)(_val) ? 0 : 1; }) +#define xen_get_virtual_psr_ic() \ + ( XEN_MAPPEDREGS->interrupt_collection_enabled ) +#define xen_set_virtual_psr_ic(_val) \ + ({ XEN_MAPPEDREGS->interrupt_collection_enabled = _val ? 1 : 0; }) +#define xen_get_virtual_pend() (XEN_MAPPEDREGS->pending_interruption) + +#endif /* __ASSEMBLY__ */ + +#endif /* _ASM_IA64_MINIOS_PRIVOP_H */ + diff -r d7f7021902a2 -r 3e3e92fb854a extras/mini-os/include/ia64/sal.h --- /dev/null Thu Jan 1 00:00:00 1970 +0000 +++ b/extras/mini-os/include/ia64/sal.h Tue Feb 6 07:41:50 2007 +0100 @@ -0,0 +1,182 @@ +/* + * The code is taken from FreeBSD. + * Changes: Dietmar Hahn + * + **************************************************************************** + * Copyright (c) 2001 Doug Rabson + * All rights reserved. + * + * Redistribution and use in source and binary forms, with or without + * modification, are permitted provided that the following conditions + * are met: + * 1. Redistributions of source code must retain the above copyright + * notice, this list of conditions and the following disclaimer. + * 2. Redistributions in binary form must reproduce the above copyright + * notice, this list of conditions and the following disclaimer in the + * documentation and/or other materials provided with the distribution. + * + * THIS SOFTWARE IS PROVIDED BY THE AUTHOR AND CONTRIBUTORS ``AS IS'' AND + * ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE + * IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE + * ARE DISCLAIMED. IN NO EVENT SHALL THE AUTHOR OR CONTRIBUTORS BE LIABLE + * FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL + * DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS + * OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) + * HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT + * LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY + * OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF + * SUCH DAMAGE. + * + */ + + +/* + * The SAL System Table starts with a header which is described in + * sal_system_table_t. + * Table header will be followed by a variable number of variable length + * entries. The first byte of each entry will identify the entry type and + * the entries shall be in ascending order by the entry type. Each entry + * type will have a known fixed length. The total length of this table + * depends upon the configuration of the system. Operating system software + * must step through each entry until it reaches the ENTRY_COUNT. The entries + * are sorted on entry type in ascending order. + * Unless otherwise stated, there is one entry per entry type. + */ + +#ifndef _MACHINE_SAL_H_ +#define _MACHINE_SAL_H_ + +typedef uint64_t u_int64_t; +typedef uint32_t u_int32_t; +typedef uint16_t u_int16_t; +typedef uint8_t u_int8_t; + +struct sal_system_table { + char sal_signature[4]; +#define SAL_SIGNATURE "SST_" + u_int32_t sal_length; + u_int8_t sal_rev[2]; /* Byte 8 - Minor, Byte 0 - Major */ + u_int16_t sal_entry_count; // num entries in var part + u_int8_t sal_checksum; + u_int8_t sal_reserved1[7]; + u_int8_t sal_a_version[2]; // like sal_rev + u_int8_t sal_b_version[2]; // like sal_rev + char sal_oem_id[32]; // Ascii - manufacturer of HW + char sal_product_id[32]; // ascii - identification + u_int8_t sal_reserved2[8]; +}; + +typedef struct sal_system_table sal_system_table_t; + +#define SAL_DESC_ENTRYPOINT 0 +#define SAL_DESC_ENTRYPOINT_LENGTH 48 +#define SAL_DESC_MEMORY 1 +#define SAL_DESC_MEMORY_LENGTH 32 +#define SAL_DESC_PLATFORM 2 +#define SAL_DESC_PLATFORM_LENGT 16 +#define SAL_DESC_TR_REG 3 +#define SAL_DESC_TR_REG_LENGTH 32 +#define SAL_DESC_PURGE_TR_CACHE 4 +#define SAL_DESC_PURGE_TR_CACHE_LENGTH 16 +#define SAL_DESC_AP_WAKEUP 5 +#define SAL_DESC_AP_WAKEUP_LENGTH 16 + + +struct sal_entrypoint_descriptor { + u_int8_t sale_type; /* == 0 */ + u_int8_t sale_reserved1[7]; + u_int64_t sale_pal_proc; /* PAL_PROC entry point */ + u_int64_t sale_sal_proc; /* SAL_PROC entry point */ + u_int64_t sale_sal_gp; /* gp for SAL_PROC, PAL_PROC */ + u_int8_t sale_reserved2[16]; +}; + +struct sal_memory_descriptor { + u_int8_t sale_type; /* == 1 */ + u_int8_t sale_need_virtual; + u_int8_t sale_current_attribute; + u_int8_t sale_access_rights; + u_int8_t sale_supported_attributes; + u_int8_t sale_reserved1; + u_int8_t sale_memory_type[2]; + u_int64_t sale_physical_address; + u_int32_t sale_length; + u_int8_t sale_reserved2[12]; +}; + +struct sal_platform_descriptor { + u_int8_t sale_type; /* == 2 */ + u_int8_t sale_features; + u_int8_t sale_reserved[14]; +}; + +struct sal_tr_descriptor { + u_int8_t sale_type; /* == 3 */ + u_int8_t sale_register_type; + u_int8_t sale_register_number; + u_int8_t sale_reserved1[5]; + u_int64_t sale_virtual_address; + u_int64_t sale_page_size; + u_int8_t sale_reserved2[8]; +}; + +struct sal_ptc_cache_descriptor { + u_int8_t sale_type; /* == 4 */ + u_int8_t sale_reserved[3]; + u_int32_t sale_domains; + u_int64_t sale_address; +}; + +struct sal_ap_wakeup_descriptor { + u_int8_t sale_type; /* == 5 */ + u_int8_t sale_mechanism; + u_int8_t sale_reserved[6]; + u_int64_t sale_vector; +}; + +/* + * SAL Procedure numbers. + */ + +#define SAL_SET_VECTORS 0x01000000 +#define SAL_GET_STATE_INFO 0x01000001 +#define SAL_GET_STATE_INFO_SIZE 0x01000002 +#define SAL_CLEAR_STATE_INFO 0x01000003 +#define SAL_MC_RENDEZ 0x01000004 +#define SAL_MC_SET_PARAMS 0x01000005 +#define SAL_REGISTER_PHYSICAL_ADDR 0x01000006 +#define SAL_CACHE_FLUSH 0x01000008 +#define SAL_CACHE_INIT 0x01000009 +#define SAL_PCI_CONFIG_READ 0x01000010 +#define SAL_PCI_CONFIG_WRITE 0x01000011 +#define SAL_FREQ_BASE 0x01000012 +#define SAL_UPDATE_PAL 0x01000020 + +/* SAL_SET_VECTORS event handler types */ +#define SAL_OS_MCA 0 +#define SAL_OS_INIT 1 +#define SAL_OS_BOOT_RENDEZ 2 + +/* SAL_GET_STATE_INFO, SAL_GET_STATE_INFO_SIZE types */ +#define SAL_INFO_MCA 0 +#define SAL_INFO_INIT 1 +#define SAL_INFO_CMC 2 +#define SAL_INFO_CPE 3 +#define SAL_INFO_TYPES 4 /* number of types we know about */ + +struct ia64_sal_result { + int64_t sal_status; + u_int64_t sal_result[3]; +}; +typedef struct ia64_sal_result ia64_sal_result_t; + +typedef ia64_sal_result_t sal_entry_t + (u_int64_t, u_int64_t, u_int64_t, u_int64_t, + u_int64_t, u_int64_t, u_int64_t, u_int64_t); + +extern ia64_sal_result_t ia64_sal_call(uint64_t, uint64_t, uint64_t, uint64_t, + uint64_t, uint64_t, uint64_t, uint64_t); + +extern void ia64_sal_init(sal_system_table_t *saltab); + +#endif /* _MACHINE_SAL_H_ */ diff -r d7f7021902a2 -r 3e3e92fb854a extras/mini-os/include/ia64/traps.h --- /dev/null Thu Jan 1 00:00:00 1970 +0000 +++ b/extras/mini-os/include/ia64/traps.h Tue Feb 6 07:41:50 2007 +0100 @@ -0,0 +1,46 @@ +/* + * Copyright (C) 2007 - Dietmar Hahn + * + **************************************************************************** + * Permission is hereby granted, free of charge, to any person obtaining a copy + * of this software and associated documentation files (the "Software"), to + * deal in the Software without restriction, including without limitation the + * rights to use, copy, modify, merge, publish, distribute, sublicense, and/or + * sell copies of the Software, and to permit persons to whom the Software is + * furnished to do so, subject to the following conditions: + * + * The above copyright notice and this permission notice shall be included in + * all copies or substantial portions of the Software. + * + * THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR + * IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY, + * FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE + * AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER + * LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING + * FROM, OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER + * DEALINGS IN THE SOFTWARE. + */ + +#if !defined(__TRAPS_H__) +#define __TRAPS_H__ + +#if !defined(__ASSEMBLY__) + +struct trap_frame; + +#define pt_regs trap_frame + +/* + * A dummy function, which is currently not supported. + */ +inline static void trap_init(void) +{ + //printk("trap_init() until now not needed!\n"); +} + + +#endif /* !defined(__ASSEMBLY__) */ + +#include "ia64_cpu.h" + +#endif // !defined(__TRAPS_H__)