Subversion Repositories HelenOS

Compare Revisions

Ignore whitespace Rev 3424 → Rev 3425

/branches/tracing/kernel/arch/sparc64/include/atomic.h
37,6 → 37,7
 
#include <arch/barrier.h>
#include <arch/types.h>
#include <preemption.h>
 
/** Atomic add operation.
*
56,7 → 57,8
 
a = *((uint64_t *) x);
b = a + i;
asm volatile ("casx %0, %2, %1\n" : "+m" (*((uint64_t *)x)), "+r" (b) : "r" (a));
asm volatile ("casx %0, %2, %1\n" : "+m" (*((uint64_t *)x)),
"+r" (b) : "r" (a));
} while (a != b);
 
return a;
97,7 → 99,8
uint64_t v = 1;
volatile uintptr_t x = (uint64_t) &val->count;
 
asm volatile ("casx %0, %2, %1\n" : "+m" (*((uint64_t *) x)), "+r" (v) : "r" (0));
asm volatile ("casx %0, %2, %1\n" : "+m" (*((uint64_t *) x)),
"+r" (v) : "r" (0));
 
return v;
}
109,6 → 112,8
 
volatile uintptr_t x = (uint64_t) &val->count;
 
preemption_disable();
 
asm volatile (
"0:\n"
"casx %0, %3, %1\n"
/branches/tracing/kernel/arch/sparc64/include/mm/page.h
53,11 → 53,6
 
#define MMU_PAGES_PER_PAGE (1 << (PAGE_WIDTH - MMU_PAGE_WIDTH))
 
/*
* With 16K pages, there is only one page color.
*/
#define PAGE_COLOR_BITS 0 /**< 14 - 14; 2^14 == 16K == alias boundary. */
 
#ifdef KERNEL
 
#ifndef __ASM__
/branches/tracing/kernel/arch/sparc64/Makefile.inc
29,11 → 29,15
## Toolchain configuration
#
 
ifndef CROSS_PREFIX
CROSS_PREFIX = /usr/local
endif
 
BFD_NAME = elf64-sparc
BFD_ARCH = sparc
BFD = binary
TARGET = sparc64-linux-gnu
TOOLCHAIN_DIR = /usr/local/sparc64
TOOLCHAIN_DIR = $(CROSS_PREFIX)/sparc64
 
GCC_CFLAGS += -m64 -mcpu=ultrasparc
SUNCC_CFLAGS += -m64 -xarch=sparc -xregs=appl,no%float
/branches/tracing/kernel/arch/sparc64/src/asm.S
41,6 → 41,7
*/
.global memcpy
memcpy:
mov %o0, %o3 ! save dst
add %o1, 7, %g1
and %g1, -8, %g1
cmp %o1, %g1
59,7 → 60,7
mov %g2, %g3
2:
jmp %o7 + 8 ! exit point
mov %o1, %o0
mov %o3, %o0
3:
and %g1, -8, %g1
cmp %o0, %g1
93,7 → 94,7
mov %g2, %g3
 
jmp %o7 + 8 ! exit point
mov %o1, %o0
mov %o3, %o0
 
/*
* Almost the same as memcpy() except the loads are from userspace.
100,6 → 101,7
*/
.global memcpy_from_uspace
memcpy_from_uspace:
mov %o0, %o3 ! save dst
add %o1, 7, %g1
and %g1, -8, %g1
cmp %o1, %g1
118,7 → 120,7
mov %g2, %g3
2:
jmp %o7 + 8 ! exit point
mov %o1, %o0
mov %o3, %o0
3:
and %g1, -8, %g1
cmp %o0, %g1
152,7 → 154,7
mov %g2, %g3
 
jmp %o7 + 8 ! exit point
mov %o1, %o0
mov %o3, %o0
 
/*
* Almost the same as memcpy() except the stores are to userspace.
159,6 → 161,7
*/
.global memcpy_to_uspace
memcpy_to_uspace:
mov %o0, %o3 ! save dst
add %o1, 7, %g1
and %g1, -8, %g1
cmp %o1, %g1
177,7 → 180,7
mov %g2, %g3
2:
jmp %o7 + 8 ! exit point
mov %o1, %o0
mov %o3, %o0
3:
and %g1, -8, %g1
cmp %o0, %g1
211,7 → 214,7
mov %g2, %g3
 
jmp %o7 + 8 ! exit point
mov %o1, %o0
mov %o3, %o0
 
.global memcpy_from_uspace_failover_address
.global memcpy_to_uspace_failover_address
274,6 → 277,8
wrpr %g0, 0, %cleanwin ! avoid information leak
 
mov %i2, %o0 ! uarg
xor %o1, %o1, %o1 ! %o1 is defined to hold pcb_ptr
! set it to 0
 
clr %i2
clr %i3
/branches/tracing/kernel/arch/ia64/include/mm/page.h
41,8 → 41,6
#define PAGE_SIZE FRAME_SIZE
#define PAGE_WIDTH FRAME_WIDTH
 
#define PAGE_COLOR_BITS 0 /* dummy */
 
#ifdef KERNEL
 
/** Bit width of the TLB-locked portion of kernel address space. */
/branches/tracing/kernel/arch/ia64/Makefile.inc
29,14 → 29,15
## Toolchain configuration
#
 
ifndef CROSS_PREFIX
CROSS_PREFIX = /usr/local
endif
 
BFD_NAME = elf64-little
BFD_ARCH = ia64-elf64
TARGET = ia64-pc-linux-gnu
TOOLCHAIN_DIR = /usr/local/ia64
TOOLCHAIN_DIR = $(CROSS_PREFIX)/ia64
 
INIT0_ADDRESS = 0xe000000004404000
INIT0_SIZE = 0x100000
 
CMN1 = -mconstant-gp -fno-unwind-tables -mfixed-range=f32-f127
GCC_CFLAGS += $(CMN1)
ICC_CFLAGS += $(CMN1)
44,9 → 45,8
LFLAGS += -EL
AFLAGS += -mconstant-gp
 
DEFS += -D__64_BITS__ -DINIT0_ADDRESS=$(INIT0_ADDRESS) -DINIT0_SIZE=$(INIT0_SIZE) -D$(MACHINE)
DEFS += -D__64_BITS__ -D$(MACHINE)
 
 
## Compile with page hash table support.
#
 
96,6 → 96,5
CONFIG_I8042 = y
DEFS += -DI460GX -DCONFIG_I8042
BFD = binary
 
endif
 
/branches/tracing/kernel/arch/ia64/src/asm.S
51,7 → 51,7
 
adds r14 = 7, in1
mov r2 = ar.lc
mov r8 = in1 ;;
mov r8 = in0
and r14 = -8, r14 ;;
cmp.ne p6, p7 = r14, in1
(p7) br.cond.dpnt 3f ;;
63,7 → 63,7
(p6) mov r17 = r0 ;;
(p6) mov ar.lc = r14
1:
add r14 = r16, r8
add r14 = r16, in1
add r15 = r16, in0
adds r17 = 1, r17 ;;
ld1 r14 = [r14]
72,7 → 72,6
br.cloop.sptk.few 1b ;;
2:
mov ar.lc = r2
 
mov ar.pfs = loc0
br.ret.sptk.many rp
3:
90,7 → 89,7
4:
shladd r14 = r16, 3, r0
adds r16 = 1, r17 ;;
add r15 = r8, r14
add r15 = in1, r14
add r14 = in0, r14
mov r17 = r16 ;;
ld8 r15 = [r15] ;;
104,7 → 103,7
cmp.eq p6, p7 = 0, r15
add in0 = r14, in0
adds r15 = -1, r15
add r17 = r14, r8
add r17 = r14, in1
(p6) br.cond.dpnt 2b ;;
mov ar.lc = r15
6:
116,7 → 115,6
st1 [r15] = r14
br.cloop.sptk.few 6b ;;
mov ar.lc = r2
 
mov ar.pfs = loc0
br.ret.sptk.many rp
163,6 → 161,9
 
xor r1 = r1, r1
/* r2 is defined to hold pcb_ptr - set it to 0 */
xor r2 = r2, r2
mov loc1 = cr.ifs
movl loc2 = PFM_MASK ;;
and loc1 = loc2, loc1 ;;
/branches/tracing/kernel/arch/arm32/include/mm/page.h
43,8 → 43,6
#define PAGE_WIDTH FRAME_WIDTH
#define PAGE_SIZE FRAME_SIZE
 
#define PAGE_COLOR_BITS 0 /* dummy */
 
#ifndef __ASM__
# define KA2PA(x) (((uintptr_t) (x)) - 0x80000000)
# define PA2KA(x) (((uintptr_t) (x)) + 0x80000000)
/branches/tracing/kernel/arch/arm32/Makefile.inc
29,11 → 29,15
## Toolchain configuration
#
 
ifndef CROSS_PREFIX
CROSS_PREFIX = /usr/local
endif
 
BFD_NAME = elf32-littlearm
BFD_ARCH = arm
BFD = binary
TARGET = arm-linux-gnu
TOOLCHAIN_DIR = /usr/local/arm
TOOLCHAIN_DIR = $(CROSS_PREFIX)/arm
 
KERNEL_LOAD_ADDRESS = 0x80200000
 
/branches/tracing/kernel/arch/arm32/src/asm.S
45,7 → 45,8
add r3, r1, #3
bic r3, r3, #3
cmp r1, r3
stmdb sp!, {r4, lr}
stmdb sp!, {r4, r5, lr}
mov r5, r0 /* save dst */
beq 4f
1:
cmp r2, #0
58,8 → 59,8
cmp ip, r2
bne 2b
3:
mov r0, r1
ldmia sp!, {r4, pc}
mov r0, r5
ldmia sp!, {r4, r5, pc}
4:
add r3, r0, #3
bic r3, r3, #3
94,5 → 95,5
 
memcpy_from_uspace_failover_address:
memcpy_to_uspace_failover_address:
mov r0, #0
ldmia sp!, {r4, pc}
mov r0, #0
ldmia sp!, {r4, r5, pc}
/branches/tracing/kernel/arch/arm32/src/userspace.c
70,8 → 70,11
/* set first parameter */
ustate.r0 = (uintptr_t) kernel_uarg->uspace_uarg;
 
/* %r1 is defined to hold pcb_ptr - set it to 0 */
ustate.r1 = 0;
 
/* clear other registers */
ustate.r1 = ustate.r2 = ustate.r3 = ustate.r4 = ustate.r5 =
ustate.r2 = ustate.r3 = ustate.r4 = ustate.r5 =
ustate.r6 = ustate.r7 = ustate.r8 = ustate.r9 = ustate.r10 =
ustate.r11 = ustate.r12 = ustate.lr = 0;
 
/branches/tracing/kernel/arch/ppc32/include/mm/page.h
40,8 → 40,6
#define PAGE_WIDTH FRAME_WIDTH
#define PAGE_SIZE FRAME_SIZE
 
#define PAGE_COLOR_BITS 0 /* dummy */
 
#ifdef KERNEL
 
#ifndef __ASM__
/branches/tracing/kernel/arch/ppc32/Makefile.inc
29,11 → 29,15
## Toolchain configuration
#
 
ifndef CROSS_PREFIX
CROSS_PREFIX = /usr/local
endif
 
BFD_NAME = elf32-powerpc
BFD_ARCH = powerpc:common
BFD = binary
TARGET = ppc-linux-gnu
TOOLCHAIN_DIR = /usr/local/ppc
TOOLCHAIN_DIR = $(CROSS_PREFIX)/ppc
 
GCC_CFLAGS += -mcpu=powerpc -msoft-float -m32
AFLAGS += -a32
/branches/tracing/kernel/arch/ppc32/src/asm.S
65,6 → 65,10
# set stack
mr sp, r4
 
# %r3 is defined to hold pcb_ptr - set it to 0
 
xor r3, r3, r3
# jump to userspace
199,47 → 203,7
rfi
memsetb:
rlwimi r5, r5, 8, 16, 23
rlwimi r5, r5, 16, 0, 15
addi r14, r3, -4
cmplwi 0, r4, 4
blt 7f
stwu r5, 4(r14)
beqlr
andi. r15, r14, 3
add r4, r15, r4
subf r14, r15, r14
srwi r15, r4, 2
mtctr r15
bdz 6f
1:
stwu r5, 4(r14)
bdnz 1b
6:
andi. r4, r4, 3
7:
cmpwi 0, r4, 0
beqlr
mtctr r4
addi r6, r6, 3
8:
stbu r5, 1(r14)
bdnz 8b
blr
b _memsetb
 
memcpy:
memcpy_from_uspace:
308,4 → 272,6
 
memcpy_from_uspace_failover_address:
memcpy_to_uspace_failover_address:
b memcpy_from_uspace_failover_address
# return zero, failure
xor r3, r3, r3
blr
/branches/tracing/kernel/arch/ppc32/src/mm/tlb.c
47,16 → 47,19
* The as->lock must be held on entry to this function
* if lock is true.
*
* @param as Address space.
* @param lock Lock/unlock the address space.
* @param badvaddr Faulting virtual address.
* @param access Access mode that caused the fault.
* @param istate Pointer to interrupted state.
* @param pfrc Pointer to variable where as_page_fault() return code will be stored.
* @return PTE on success, NULL otherwise.
* @param as Address space.
* @param lock Lock/unlock the address space.
* @param badvaddr Faulting virtual address.
* @param access Access mode that caused the fault.
* @param istate Pointer to interrupted state.
* @param pfrc Pointer to variable where as_page_fault() return code
* will be stored.
* @return PTE on success, NULL otherwise.
*
*/
static pte_t *find_mapping_and_check(as_t *as, bool lock, uintptr_t badvaddr, int access, istate_t *istate, int *pfrc)
static pte_t *
find_mapping_and_check(as_t *as, bool lock, uintptr_t badvaddr, int access,
istate_t *istate, int *pfrc)
{
/*
* Check if the mapping exists in page tables.
77,27 → 80,27
*/
page_table_unlock(as, lock);
switch (rc = as_page_fault(badvaddr, access, istate)) {
case AS_PF_OK:
/*
* The higher-level page fault handler succeeded,
* The mapping ought to be in place.
*/
page_table_lock(as, lock);
pte = page_mapping_find(as, badvaddr);
ASSERT((pte) && (pte->p));
*pfrc = 0;
return pte;
case AS_PF_DEFER:
page_table_lock(as, lock);
*pfrc = rc;
return NULL;
case AS_PF_FAULT:
page_table_lock(as, lock);
printf("Page fault.\n");
*pfrc = rc;
return NULL;
default:
panic("unexpected rc (%d)\n", rc);
case AS_PF_OK:
/*
* The higher-level page fault handler succeeded,
* The mapping ought to be in place.
*/
page_table_lock(as, lock);
pte = page_mapping_find(as, badvaddr);
ASSERT((pte) && (pte->p));
*pfrc = 0;
return pte;
case AS_PF_DEFER:
page_table_lock(as, lock);
*pfrc = rc;
return NULL;
case AS_PF_FAULT:
page_table_lock(as, lock);
printf("Page fault.\n");
*pfrc = rc;
return NULL;
default:
panic("unexpected rc (%d)\n", rc);
}
}
}
114,7 → 117,8
s = get_symtab_entry(istate->lr);
if (s)
sym2 = s;
panic("%p: PHT Refill Exception at %p (%s<-%s)\n", badvaddr, istate->pc, symbol, sym2);
panic("%p: PHT Refill Exception at %p (%s<-%s)\n", badvaddr,
istate->pc, symbol, sym2);
}
 
 
147,7 → 151,8
/* Find unused or colliding
PTE in PTEG */
for (i = 0; i < 8; i++) {
if ((!phte[base + i].v) || ((phte[base + i].vsid == vsid) && (phte[base + i].api == api))) {
if ((!phte[base + i].v) || ((phte[base + i].vsid == vsid) &&
(phte[base + i].api == api))) {
found = true;
break;
}
160,7 → 165,9
/* Find unused or colliding
PTE in PTEG */
for (i = 0; i < 8; i++) {
if ((!phte[base2 + i].v) || ((phte[base2 + i].vsid == vsid) && (phte[base2 + i].api == api))) {
if ((!phte[base2 + i].v) ||
((phte[base2 + i].vsid == vsid) &&
(phte[base2 + i].api == api))) {
found = true;
base = base2;
h = 1;
214,7 → 221,9
/* Find unused or colliding
PTE in PTEG */
for (i = 0; i < 8; i++) {
if ((!phte_physical[base + i].v) || ((phte_physical[base + i].vsid == vsid) && (phte_physical[base + i].api == api))) {
if ((!phte_physical[base + i].v) ||
((phte_physical[base + i].vsid == vsid) &&
(phte_physical[base + i].api == api))) {
found = true;
break;
}
227,7 → 236,9
/* Find unused or colliding
PTE in PTEG */
for (i = 0; i < 8; i++) {
if ((!phte_physical[base2 + i].v) || ((phte_physical[base2 + i].vsid == vsid) && (phte_physical[base2 + i].api == api))) {
if ((!phte_physical[base2 + i].v) ||
((phte_physical[base2 + i].vsid == vsid) &&
(phte_physical[base2 + i].api == api))) {
found = true;
base = base2;
h = 1;
254,8 → 265,8
 
/** Process Instruction/Data Storage Interrupt
*
* @param n Interrupt vector number.
* @param istate Interrupted register context.
* @param n Interrupt vector number.
* @param istate Interrupted register context.
*
*/
void pht_refill(int n, istate_t *istate)
284,21 → 295,22
page_table_lock(as, lock);
pte = find_mapping_and_check(as, lock, badvaddr, PF_ACCESS_READ /* FIXME */, istate, &pfrc);
pte = find_mapping_and_check(as, lock, badvaddr,
PF_ACCESS_READ /* FIXME */, istate, &pfrc);
if (!pte) {
switch (pfrc) {
case AS_PF_FAULT:
goto fail;
break;
case AS_PF_DEFER:
/*
* The page fault came during copy_from_uspace()
* or copy_to_uspace().
*/
page_table_unlock(as, lock);
return;
default:
panic("Unexpected pfrc (%d)\n", pfrc);
case AS_PF_FAULT:
goto fail;
break;
case AS_PF_DEFER:
/*
* The page fault came during copy_from_uspace()
* or copy_to_uspace().
*/
page_table_unlock(as, lock);
return;
default:
panic("Unexpected pfrc (%d)\n", pfrc);
}
}
316,8 → 328,8
 
/** Process Instruction/Data Storage Interrupt in Real Mode
*
* @param n Interrupt vector number.
* @param istate Interrupted register context.
* @param n Interrupt vector number.
* @param istate Interrupted register context.
*
*/
bool pht_real_refill(int n, istate_t *istate)
373,7 → 385,8
uint32_t i;
for (i = 0; i < 8192; i++) {
if ((phte[i].v) && (phte[i].vsid >= (asid << 4)) && (phte[i].vsid < ((asid << 4) + 16)))
if ((phte[i].v) && (phte[i].vsid >= (asid << 4)) &&
(phte[i].vsid < ((asid << 4) + 16)))
phte[i].v = 0;
}
tlb_invalidate_all();
407,7 → 420,11
} \
} else \
length = 0; \
printf(name ": page=%.*p frame=%.*p length=%d KB (mask=%#x)%s%s\n", sizeof(upper) * 2, upper & 0xffff0000, sizeof(lower) * 2, lower & 0xffff0000, length, mask, ((upper >> 1) & 1) ? " supervisor" : "", (upper & 1) ? " user" : "");
printf(name ": page=%.*p frame=%.*p length=%d KB (mask=%#x)%s%s\n", \
sizeof(upper) * 2, upper & 0xffff0000, sizeof(lower) * 2, \
lower & 0xffff0000, length, mask, \
((upper >> 1) & 1) ? " supervisor" : "", \
(upper & 1) ? " user" : "");
 
 
void tlb_print(void)
421,7 → 438,10
: "=r" (vsid)
: "r" (sr << 28)
);
printf("vsid[%d]: VSID=%.*p (ASID=%d)%s%s\n", sr, sizeof(vsid) * 2, vsid & 0xffffff, (vsid & 0xffffff) >> 4, ((vsid >> 30) & 1) ? " supervisor" : "", ((vsid >> 29) & 1) ? " user" : "");
printf("vsid[%d]: VSID=%.*p (ASID=%d)%s%s\n", sr,
sizeof(vsid) * 2, vsid & 0xffffff, (vsid & 0xffffff) >> 4,
((vsid >> 30) & 1) ? " supervisor" : "",
((vsid >> 29) & 1) ? " user" : "");
}
uint32_t upper;
/branches/tracing/kernel/arch/ppc32/src/mm/page.c
47,13 → 47,16
 
uintptr_t hw_map(uintptr_t physaddr, size_t size)
{
if (last_frame + ALIGN_UP(size, PAGE_SIZE) > KA2PA(KERNEL_ADDRESS_SPACE_END_ARCH))
panic("Unable to map physical memory %p (%" PRIs " bytes)", physaddr, size)
if (last_frame + ALIGN_UP(size, PAGE_SIZE) >
KA2PA(KERNEL_ADDRESS_SPACE_END_ARCH))
panic("Unable to map physical memory %p (%" PRIs " bytes)",
physaddr, size)
uintptr_t virtaddr = PA2KA(last_frame);
pfn_t i;
for (i = 0; i < ADDR2PFN(ALIGN_UP(size, PAGE_SIZE)); i++)
page_mapping_insert(AS_KERNEL, virtaddr + PFN2ADDR(i), physaddr + PFN2ADDR(i), PAGE_NOT_CACHEABLE | PAGE_WRITE);
page_mapping_insert(AS_KERNEL, virtaddr + PFN2ADDR(i),
physaddr + PFN2ADDR(i), PAGE_NOT_CACHEABLE | PAGE_WRITE);
last_frame = ALIGN_UP(last_frame + size, FRAME_SIZE);
/branches/tracing/kernel/arch/ia32xen/include/mm/page.h
40,8 → 40,6
#define PAGE_WIDTH FRAME_WIDTH
#define PAGE_SIZE FRAME_SIZE
 
#define PAGE_COLOR_BITS 0 /* dummy */
 
#ifdef KERNEL
 
#ifndef __ASM__
/branches/tracing/kernel/arch/ia32xen/Makefile.inc
29,11 → 29,15
## Toolchain configuration
#
 
ifndef CROSS_PREFIX
CROSS_PREFIX = /usr/local
endif
 
BFD_NAME = elf32-i386
BFD_ARCH = i386
BFD = elf32-i386
TARGET = i686-pc-linux-gnu
TOOLCHAIN_DIR = /usr/local/i686
TOOLCHAIN_DIR = $(CROSS_PREFIX)/i686
 
DEFS += -DMACHINE=$(MACHINE) -D__32_BITS__
 
/branches/tracing/kernel/arch/ia32xen/src/asm.S
67,7 → 67,7
* @param MEMCPY_SRC(%esp) Source address.
* @param MEMCPY_SIZE(%esp) Size.
*
* @return MEMCPY_SRC(%esp) on success and 0 on failure.
* @return MEMCPY_DST(%esp) on success and 0 on failure.
*/
memcpy:
memcpy_from_uspace:
92,7 → 92,7
0:
movl %edx, %edi
movl %eax, %esi
movl MEMCPY_SRC(%esp), %eax /* MEMCPY_SRC(%esp), success */
movl MEMCPY_DST(%esp), %eax /* MEMCPY_DST(%esp), success */
ret
/*
/branches/tracing/kernel/arch/ia32xen/src/userspace.c
68,6 → 68,10
"pushl %3\n"
"pushl %4\n"
"movl %5, %%eax\n"
 
/* %ebx is defined to hold pcb_ptr - set it to 0 */
"xorl %%ebx, %%ebx\n"
 
"iret\n"
:
: "i" (selector(UDATA_DES) | PL_USER),
/branches/tracing/kernel/arch/amd64/include/atomic.h
108,13 → 108,13
#endif
"mov %0, %1\n"
"testq %1, %1\n"
"jnz 0b\n" /* Lightweight looping on locked spinlock */
"jnz 0b\n" /* lightweight looping on locked spinlock */
"incq %1\n" /* now use the atomic operation */
"xchgq %0, %1\n"
"testq %1, %1\n"
"jnz 0b\n"
: "+m" (val->count), "=r"(tmp)
: "+m" (val->count), "=&r" (tmp)
);
/*
* Prevent critical section code from bleeding out this way up.
/branches/tracing/kernel/arch/amd64/include/mm/page.h
52,8 → 52,6
#define PAGE_WIDTH FRAME_WIDTH
#define PAGE_SIZE FRAME_SIZE
 
#define PAGE_COLOR_BITS 0 /* dummy */
 
#ifdef KERNEL
 
#ifndef __ASM__
/branches/tracing/kernel/arch/amd64/Makefile.inc
29,11 → 29,15
## Toolchain configuration
#
 
ifndef CROSS_PREFIX
CROSS_PREFIX = /usr/local
endif
 
BFD_NAME = elf64-x86-64
BFD_ARCH = i386:x86-64
BFD = binary
TARGET = amd64-linux-gnu
TOOLCHAIN_DIR = /usr/local/amd64
TOOLCHAIN_DIR = $(CROSS_PREFIX)/amd64
 
FPU_NO_CFLAGS = -mno-sse -mno-sse2
CMN1 = -m64 -mcmodel=kernel -mno-red-zone -fno-unwind-tables
/branches/tracing/kernel/arch/amd64/src/asm_utils.S
98,12 → 98,12
* @param MEMCPY_SRC Source address.
* @param MEMCPY_SIZE Number of bytes to copy.
*
* @retrun MEMCPY_SRC on success, 0 on failure.
* @retrun MEMCPY_DST on success, 0 on failure.
*/
memcpy:
memcpy_from_uspace:
memcpy_to_uspace:
movq MEMCPY_SRC, %rax
movq MEMCPY_DST, %rax
 
movq MEMCPY_SIZE, %rcx
shrq $3, %rcx /* size / 8 */
/branches/tracing/kernel/arch/amd64/src/userspace.c
61,6 → 61,8
"pushq %3\n"
"pushq %4\n"
"movq %5, %%rax\n"
/* %rdi is defined to hold pcb_ptr - set it to 0 */
"xorq %%rdi, %%rdi\n"
"iretq\n"
: :
"i" (gdtselector(UDATA_DES) | PL_USER),
/branches/tracing/kernel/arch/ppc64/include/mm/page.h
40,8 → 40,6
#define PAGE_WIDTH FRAME_WIDTH
#define PAGE_SIZE FRAME_SIZE
 
#define PAGE_COLOR_BITS 0 /* dummy */
 
#ifdef KERNEL
 
#ifndef __ASM__
/branches/tracing/kernel/arch/ppc64/Makefile.inc
29,11 → 29,15
## Toolchain configuration
#
 
ifndef CROSS_PREFIX
CROSS_PREFIX = /usr/local
endif
 
BFD_NAME = elf64-powerpc
BFD_ARCH = powerpc:common64
BFD = binary
TARGET = ppc64-linux-gnu
TOOLCHAIN_DIR = /usr/local/ppc64
TOOLCHAIN_DIR = $(CROSS_PREFIX)/ppc64
 
GCC_CFLAGS += -mcpu=powerpc64 -msoft-float -m64
AFLAGS += -a64
/branches/tracing/kernel/arch/ppc64/src/asm.S
66,6 → 66,10
mr sp, r4
# %r3 is defined to hold pcb_ptr - set it to 0
 
xor r3, r3, r3
 
# jump to userspace
rfi
/branches/tracing/kernel/arch/mips32/include/mm/page.h
40,8 → 40,6
#define PAGE_WIDTH FRAME_WIDTH
#define PAGE_SIZE FRAME_SIZE
 
#define PAGE_COLOR_BITS 0 /* dummy */
 
#ifndef __ASM__
# define KA2PA(x) (((uintptr_t) (x)) - 0x80000000)
# define PA2KA(x) (((uintptr_t) (x)) + 0x80000000)
/branches/tracing/kernel/arch/mips32/include/mm/tlb.h
35,6 → 35,9
#ifndef KERN_mips32_TLB_H_
#define KERN_mips32_TLB_H_
 
#include <arch/types.h>
#include <typedefs.h>
#include <arch/mm/asid.h>
#include <arch/exception.h>
 
#ifdef TLBCNT
46,7 → 49,13
#define TLB_WIRED 1
#define TLB_KSTACK_WIRED_INDEX 0
 
#define TLB_PAGE_MASK_16K (0x3<<13)
#define TLB_PAGE_MASK_4K (0x000 << 13)
#define TLB_PAGE_MASK_16K (0x003 << 13)
#define TLB_PAGE_MASK_64K (0x00f << 13)
#define TLB_PAGE_MASK_256K (0x03f << 13)
#define TLB_PAGE_MASK_1M (0x0ff << 13)
#define TLB_PAGE_MASK_4M (0x3ff << 13)
#define TLB_PAGE_MASK_16M (0xfff << 13)
 
#define PAGE_UNCACHED 2
#define PAGE_CACHEABLE_EXC_WRITE 5
159,6 → 168,8
extern void tlb_invalid(istate_t *istate);
extern void tlb_refill(istate_t *istate);
extern void tlb_modified(istate_t *istate);
extern void tlb_prepare_entry_lo(entry_lo_t *lo, bool g, bool v, bool d, bool cacheable, uintptr_t pfn);
extern void tlb_prepare_entry_hi(entry_hi_t *hi, asid_t asid, uintptr_t addr);
 
#endif
 
/branches/tracing/kernel/arch/mips32/include/mm/as.h
38,7 → 38,7
#define KERNEL_ADDRESS_SPACE_SHADOWED_ARCH 0
 
#define KERNEL_ADDRESS_SPACE_START_ARCH (unsigned long) 0x80000000
#define KERNEL_ADDRESS_SPACE_END_ARCH (unsigned long) 0xffffffff
#define KERNEL_ADDRESS_SPACE_END_ARCH (unsigned long) 0x9fffffff
#define USER_ADDRESS_SPACE_START_ARCH (unsigned long) 0x00000000
#define USER_ADDRESS_SPACE_END_ARCH (unsigned long) 0x7fffffff
 
/branches/tracing/kernel/arch/mips32/include/drivers/arc.h
File deleted
/branches/tracing/kernel/arch/mips32/include/drivers/serial.h
37,6 → 37,8
 
#include <console/chardev.h>
 
#define SERIAL_ADDRESS 0x98000000
 
#define SERIAL_MAX 4
#define SERIAL_COM1 0x3f8
#define SERIAL_COM1_IRQ 4
43,16 → 45,19
#define SERIAL_COM2 0x2f8
#define SERIAL_COM2_IRQ 3
 
#define P_WRITEB(where,what) (*((volatile char *) (0xB8000000+where))=what)
#define P_READB(where) (*((volatile char *)(0xB8000000+where)))
#define P_WRITEB(where, what) (*((volatile char *) (SERIAL_ADDRESS + where)) = what)
#define P_READB(where) (*((volatile char *) (SERIAL_ADDRESS + where)))
 
#define SERIAL_READ(x) P_READB(x)
#define SERIAL_WRITE(x,c) P_WRITEB(x,c)
#define SERIAL_READ(x) P_READB(x)
#define SERIAL_WRITE(x, c) P_WRITEB(x, c)
 
/* Interrupt enable register */
#define SERIAL_READ_IER(x) (P_READB((x) + 1))
#define SERIAL_WRITE_IER(x,c) (P_WRITEB((x)+1,c))
#define SERIAL_WRITE_IER(x,c) (P_WRITEB((x) + 1, c))
 
/* Interrupt identification register */
#define SERIAL_READ_IIR(x) (P_READB((x) + 2))
 
/* Line status register */
#define SERIAL_READ_LSR(x) (P_READB((x) + 5))
#define TRANSMIT_EMPTY_BIT 5
/branches/tracing/kernel/arch/mips32/include/drivers/msim.h
35,6 → 35,11
#ifndef KERN_mips32_MSIM_H_
#define KERN_mips32_MSIM_H_
 
/** Address of devices. */
#define MSIM_VIDEORAM 0x90000000
#define MSIM_KBD_ADDRESS 0x90000000
#define MSIM_KBD_IRQ 2
 
#include <console/chardev.h>
 
void msim_console(devno_t devno);
/branches/tracing/kernel/arch/mips32/Makefile.inc
29,17 → 29,19
## Toolchain configuration
#
 
ifndef CROSS_PREFIX
CROSS_PREFIX = /usr/local
endif
 
BFD_ARCH = mips
TARGET = mipsel-linux-gnu
TOOLCHAIN_DIR = /usr/local/mipsel
TOOLCHAIN_DIR = $(CROSS_PREFIX)/mipsel
 
KERNEL_LOAD_ADDRESS = 0x80100000
INIT_ADDRESS = 0x81000000
INIT_SIZE = 262144
 
GCC_CFLAGS += -mno-abicalls -G 0 -fno-zero-initialized-in-bss
 
DEFS += -D__32_BITS__ -DMACHINE=$(MACHINE) -DKERNEL_LOAD_ADDRESS=${KERNEL_LOAD_ADDRESS} -DINIT_ADDRESS=${INIT_ADDRESS} -DINIT_SIZE=${INIT_SIZE}
DEFS += -D__32_BITS__ -DMACHINE=$(MACHINE) -DKERNEL_LOAD_ADDRESS=${KERNEL_LOAD_ADDRESS}
 
## Compile with hierarchical page tables support.
#
56,20 → 58,6
## Accepted MACHINEs
#
 
ifeq ($(MACHINE),indy)
# GCC 4.0.1 compiled for mipsEL has problems compiling in
# BigEndian mode with the swl/swr/lwl/lwr instructions.
# We have to compile it with mips-sgi-irix5 to get it right.
BFD_NAME = elf32-bigmips
BFD = ecoff-bigmips --impure
TARGET = mips-sgi-irix5
TOOLCHAIN_DIR = /usr/local/mips/bin
KERNEL_LOAD_ADDRESS = 0x88002000
GCC_CFLAGS += -EB -DBIG_ENDIAN -DARCH_HAS_FPU -march=r4600
INIT_ADDRESS = 0
INIT_SIZE = 0
endif
ifeq ($(MACHINE),lgxemul)
BFD_NAME = elf32-tradlittlemips
BFD = binary
79,9 → 67,8
BFD_NAME = elf32-bigmips
BFD = ecoff-bigmips
TARGET = mips-sgi-irix5
TOOLCHAIN_DIR = /usr/local/mips/bin
TOOLCHAIN_DIR = $(CROSS_PREFIX)/mips/bin
GCC_CFLAGS += -EB -DBIG_ENDIAN -DARCH_HAS_FPU -mips3
INIT_ADDRESS = 0x81800000
endif
ifeq ($(MACHINE),simics)
# SIMICS 4kc emulation is broken, although for instructions
123,7 → 110,6
arch/$(ARCH)/src/mm/as.c \
arch/$(ARCH)/src/fpu_context.c \
arch/$(ARCH)/src/ddi/ddi.c \
arch/$(ARCH)/src/drivers/arc.c \
arch/$(ARCH)/src/drivers/msim.c \
arch/$(ARCH)/src/drivers/serial.c \
arch/$(ARCH)/src/smp/order.c
/branches/tracing/kernel/arch/mips32/src/asm.S
71,6 → 71,7
and $v0,$v0,$v1
beq $a1,$v0,3f
move $t0,$a0
move $t2,$a0 # save dst
 
0:
beq $a2,$zero,2f
86,7 → 87,7
 
2:
jr $ra
move $v0,$a1
move $v0,$t2
 
3:
addiu $v0,$a0,3
126,7 → 127,7
sb $a0,0($v1)
 
jr $ra
move $v0,$a1
move $v0,$t2
 
memcpy_from_uspace_failover_address:
memcpy_to_uspace_failover_address:
/branches/tracing/kernel/arch/mips32/src/console.c
34,18 → 34,15
 
#include <console/console.h>
#include <arch/console.h>
#include <arch/drivers/arc.h>
#include <arch/drivers/serial.h>
#include <arch/drivers/msim.h>
 
void console_init(devno_t devno)
{
if (!arc_console()) {
if (serial_init())
serial_console(devno);
else
msim_console(devno);
}
if (serial_init())
serial_console(devno);
else
msim_console(devno);
}
 
/** Acquire console back for kernel
/branches/tracing/kernel/arch/mips32/src/mips32.c
48,7 → 48,6
#include <sysinfo/sysinfo.h>
 
#include <arch/interrupt.h>
#include <arch/drivers/arc.h>
#include <console/chardev.h>
#include <arch/barrier.h>
#include <arch/debugger.h>
97,7 → 96,6
/* Initialize dispatch table */
exception_init();
arc_init();
 
/* Copy the exception vectors to the right places */
memcpy(TLB_EXC, (char *) tlb_refill_entry, EXCEPTION_JUMP_SIZE);
187,8 → 185,7
 
void arch_reboot(void)
{
if (!arc_reboot())
___halt();
___halt();
while (1)
;
/branches/tracing/kernel/arch/mips32/src/start.S
349,5 → 349,7
userspace_asm:
add $sp, $a0, 0
add $v0, $a1, 0
add $t9, $a2, 0 # Set up correct entry into PIC code
add $t9, $a2, 0 # Set up correct entry into PIC code
xor $a0, $a0, $a0 # $a0 is defined to hold pcb_ptr
# set it to 0
eret
/branches/tracing/kernel/arch/mips32/src/mm/tlb.c
47,18 → 47,14
#include <align.h>
#include <interrupt.h>
 
static void tlb_refill_fail(istate_t *istate);
static void tlb_invalid_fail(istate_t *istate);
static void tlb_modified_fail(istate_t *istate);
static void tlb_refill_fail(istate_t *);
static void tlb_invalid_fail(istate_t *);
static void tlb_modified_fail(istate_t *);
 
static pte_t *find_mapping_and_check(uintptr_t badvaddr, int access, istate_t *istate, int *pfrc);
static pte_t *find_mapping_and_check(uintptr_t, int, istate_t *, int *);
 
static void prepare_entry_lo(entry_lo_t *lo, bool g, bool v, bool d, bool cacheable, uintptr_t pfn);
static void prepare_entry_hi(entry_hi_t *hi, asid_t asid, uintptr_t addr);
 
/** Initialize TLB
/** Initialize TLB.
*
* Initialize TLB.
* Invalidate all entries and mark wired entries.
*/
void tlb_arch_init(void)
76,7 → 72,6
cp0_index_write(i);
tlbwi();
}
 
/*
* The kernel is going to make use of some wired
85,11 → 80,9
cp0_wired_write(TLB_WIRED);
}
 
/** Process TLB Refill Exception
/** Process TLB Refill Exception.
*
* Process TLB Refill Exception.
*
* @param istate Interrupted register context.
* @param istate Interrupted register context.
*/
void tlb_refill(istate_t *istate)
{
131,14 → 124,15
*/
pte->a = 1;
 
prepare_entry_hi(&hi, asid, badvaddr);
prepare_entry_lo(&lo, pte->g, pte->p, pte->d, pte->cacheable, pte->pfn);
tlb_prepare_entry_hi(&hi, asid, badvaddr);
tlb_prepare_entry_lo(&lo, pte->g, pte->p, pte->d, pte->cacheable,
pte->pfn);
 
/*
* New entry is to be inserted into TLB
*/
cp0_entry_hi_write(hi.value);
if ((badvaddr/PAGE_SIZE) % 2 == 0) {
if ((badvaddr / PAGE_SIZE) % 2 == 0) {
cp0_entry_lo0_write(lo.value);
cp0_entry_lo1_write(0);
}
157,11 → 151,9
tlb_refill_fail(istate);
}
 
/** Process TLB Invalid Exception
/** Process TLB Invalid Exception.
*
* Process TLB Invalid Exception.
*
* @param istate Interrupted register context.
* @param istate Interrupted register context.
*/
void tlb_invalid(istate_t *istate)
{
178,7 → 170,7
* Locate the faulting entry in TLB.
*/
hi.value = cp0_entry_hi_read();
prepare_entry_hi(&hi, hi.asid, badvaddr);
tlb_prepare_entry_hi(&hi, hi.asid, badvaddr);
cp0_entry_hi_write(hi.value);
tlbp();
index.value = cp0_index_read();
221,12 → 213,13
*/
pte->a = 1;
 
prepare_entry_lo(&lo, pte->g, pte->p, pte->d, pte->cacheable, pte->pfn);
tlb_prepare_entry_lo(&lo, pte->g, pte->p, pte->d, pte->cacheable,
pte->pfn);
 
/*
* The entry is to be updated in TLB.
*/
if ((badvaddr/PAGE_SIZE) % 2 == 0)
if ((badvaddr / PAGE_SIZE) % 2 == 0)
cp0_entry_lo0_write(lo.value);
else
cp0_entry_lo1_write(lo.value);
241,11 → 234,9
tlb_invalid_fail(istate);
}
 
/** Process TLB Modified Exception
/** Process TLB Modified Exception.
*
* Process TLB Modified Exception.
*
* @param istate Interrupted register context.
* @param istate Interrupted register context.
*/
void tlb_modified(istate_t *istate)
{
262,7 → 253,7
* Locate the faulting entry in TLB.
*/
hi.value = cp0_entry_hi_read();
prepare_entry_hi(&hi, hi.asid, badvaddr);
tlb_prepare_entry_hi(&hi, hi.asid, badvaddr);
cp0_entry_hi_write(hi.value);
tlbp();
index.value = cp0_index_read();
296,12 → 287,6
}
 
/*
* Fail if the page is not writable.
*/
if (!pte->w)
goto fail;
 
/*
* Read the faulting TLB entry.
*/
tlbr();
312,12 → 297,13
pte->a = 1;
pte->d = 1;
 
prepare_entry_lo(&lo, pte->g, pte->p, pte->w, pte->cacheable, pte->pfn);
tlb_prepare_entry_lo(&lo, pte->g, pte->p, pte->w, pte->cacheable,
pte->pfn);
 
/*
* The entry is to be updated in TLB.
*/
if ((badvaddr/PAGE_SIZE) % 2 == 0)
if ((badvaddr / PAGE_SIZE) % 2 == 0)
cp0_entry_lo0_write(lo.value);
else
cp0_entry_lo1_write(lo.value);
344,8 → 330,10
if (s)
sym2 = s;
 
fault_if_from_uspace(istate, "TLB Refill Exception on %p", cp0_badvaddr_read());
panic("%x: TLB Refill Exception at %x(%s<-%s)\n", cp0_badvaddr_read(), istate->epc, symbol, sym2);
fault_if_from_uspace(istate, "TLB Refill Exception on %p",
cp0_badvaddr_read());
panic("%x: TLB Refill Exception at %x(%s<-%s)\n", cp0_badvaddr_read(),
istate->epc, symbol, sym2);
}
 
 
356,8 → 344,10
char *s = get_symtab_entry(istate->epc);
if (s)
symbol = s;
fault_if_from_uspace(istate, "TLB Invalid Exception on %p", cp0_badvaddr_read());
panic("%x: TLB Invalid Exception at %x(%s)\n", cp0_badvaddr_read(), istate->epc, symbol);
fault_if_from_uspace(istate, "TLB Invalid Exception on %p",
cp0_badvaddr_read());
panic("%x: TLB Invalid Exception at %x(%s)\n", cp0_badvaddr_read(),
istate->epc, symbol);
}
 
void tlb_modified_fail(istate_t *istate)
367,23 → 357,27
char *s = get_symtab_entry(istate->epc);
if (s)
symbol = s;
fault_if_from_uspace(istate, "TLB Modified Exception on %p", cp0_badvaddr_read());
panic("%x: TLB Modified Exception at %x(%s)\n", cp0_badvaddr_read(), istate->epc, symbol);
fault_if_from_uspace(istate, "TLB Modified Exception on %p",
cp0_badvaddr_read());
panic("%x: TLB Modified Exception at %x(%s)\n", cp0_badvaddr_read(),
istate->epc, symbol);
}
 
/** Try to find PTE for faulting address
/** Try to find PTE for faulting address.
*
* Try to find PTE for faulting address.
* The AS->lock must be held on entry to this function.
*
* @param badvaddr Faulting virtual address.
* @param access Access mode that caused the fault.
* @param istate Pointer to interrupted state.
* @param pfrc Pointer to variable where as_page_fault() return code will be stored.
* @param badvaddr Faulting virtual address.
* @param access Access mode that caused the fault.
* @param istate Pointer to interrupted state.
* @param pfrc Pointer to variable where as_page_fault() return code
* will be stored.
*
* @return PTE on success, NULL otherwise.
* @return PTE on success, NULL otherwise.
*/
pte_t *find_mapping_and_check(uintptr_t badvaddr, int access, istate_t *istate, int *pfrc)
pte_t *
find_mapping_and_check(uintptr_t badvaddr, int access, istate_t *istate,
int *pfrc)
{
entry_hi_t hi;
pte_t *pte;
402,7 → 396,7
* Check if the mapping exists in page tables.
*/
pte = page_mapping_find(AS, badvaddr);
if (pte && pte->p) {
if (pte && pte->p && (pte->w || access != PF_ACCESS_WRITE)) {
/*
* Mapping found in page tables.
* Immediately succeed.
425,6 → 419,7
page_table_lock(AS, true);
pte = page_mapping_find(AS, badvaddr);
ASSERT(pte && pte->p);
ASSERT(pte->w || access != PF_ACCESS_WRITE);
return pte;
break;
case AS_PF_DEFER:
445,7 → 440,9
}
}
 
void prepare_entry_lo(entry_lo_t *lo, bool g, bool v, bool d, bool cacheable, uintptr_t pfn)
void
tlb_prepare_entry_lo(entry_lo_t *lo, bool g, bool v, bool d, bool cacheable,
uintptr_t pfn)
{
lo->value = 0;
lo->g = g;
455,7 → 452,7
lo->pfn = pfn;
}
 
void prepare_entry_hi(entry_hi_t *hi, asid_t asid, uintptr_t addr)
void tlb_prepare_entry_hi(entry_hi_t *hi, asid_t asid, uintptr_t addr)
{
hi->value = ALIGN_DOWN(addr, PAGE_SIZE * 2);
hi->asid = asid;
484,10 → 481,10
lo1.value = cp0_entry_lo1_read();
printf("%-2u %-4u %#6x %#4x %1u %1u %1u %1u %#6x\n",
i, hi.asid, hi.vpn2, mask.mask,
lo0.g, lo0.v, lo0.d, lo0.c, lo0.pfn);
i, hi.asid, hi.vpn2, mask.mask,
lo0.g, lo0.v, lo0.d, lo0.c, lo0.pfn);
printf(" %1u %1u %1u %1u %#6x\n",
lo1.g, lo1.v, lo1.d, lo1.c, lo1.pfn);
lo1.g, lo1.v, lo1.d, lo1.c, lo1.pfn);
}
cp0_entry_hi_write(hi_save.value);
564,11 → 561,12
cp0_entry_hi_write(hi_save.value);
}
 
/** Invalidate TLB entries for specified page range belonging to specified address space.
/** Invalidate TLB entries for specified page range belonging to specified
* address space.
*
* @param asid Address space identifier.
* @param page First page whose TLB entry is to be invalidated.
* @param cnt Number of entries to invalidate.
* @param asid Address space identifier.
* @param page First page whose TLB entry is to be invalidated.
* @param cnt Number of entries to invalidate.
*/
void tlb_invalidate_pages(asid_t asid, uintptr_t page, count_t cnt)
{
585,7 → 583,7
 
for (i = 0; i < cnt + 1; i += 2) {
hi.value = 0;
prepare_entry_hi(&hi, asid, page + i * PAGE_SIZE);
tlb_prepare_entry_hi(&hi, asid, page + i * PAGE_SIZE);
cp0_entry_hi_write(hi.value);
 
tlbp();
592,7 → 590,10
index.value = cp0_index_read();
 
if (!index.p) {
/* Entry was found, index register contains valid index. */
/*
* Entry was found, index register contains valid
* index.
*/
tlbr();
 
lo0.value = cp0_entry_lo0_read();
/branches/tracing/kernel/arch/mips32/src/mm/as.c
44,7 → 44,7
/** Architecture dependent address space init. */
void as_arch_init(void)
{
as_operations = &as_pt_operations;
as_operations = &as_pt_operations;
asid_fifo_init();
}
 
/branches/tracing/kernel/arch/mips32/src/mm/frame.c
32,27 → 32,238
/** @file
*/
 
#include <macros.h>
#include <arch/mm/frame.h>
#include <arch/mm/tlb.h>
#include <interrupt.h>
#include <mm/frame.h>
#include <mm/asid.h>
#include <config.h>
#include <arch/drivers/arc.h>
#include <arch/drivers/msim.h>
#include <arch/drivers/serial.h>
#include <print.h>
 
#define ZERO_PAGE_MASK TLB_PAGE_MASK_256K
#define ZERO_FRAMES 2048
#define ZERO_PAGE_WIDTH 18 /* 256K */
#define ZERO_PAGE_SIZE (1 << ZERO_PAGE_WIDTH)
#define ZERO_PAGE_ASID ASID_INVALID
#define ZERO_PAGE_TLBI 0
#define ZERO_PAGE_ADDR 0
#define ZERO_PAGE_OFFSET (ZERO_PAGE_SIZE / sizeof(uint32_t) - 1)
#define ZERO_PAGE_VALUE (((volatile uint32_t *) ZERO_PAGE_ADDR)[ZERO_PAGE_OFFSET])
 
#define ZERO_PAGE_VALUE_KSEG1(frame) (((volatile uint32_t *) (0xa0000000 + (frame << ZERO_PAGE_WIDTH)))[ZERO_PAGE_OFFSET])
 
#define MAX_REGIONS 32
 
typedef struct {
pfn_t start;
pfn_t count;
} phys_region_t;
 
static count_t phys_regions_count = 0;
static phys_region_t phys_regions[MAX_REGIONS];
 
 
/** Check whether frame is available
*
* Returns true if given frame is generally available for use.
* Returns false if given frame is used for physical memory
* mapped devices and cannot be used.
*
*/
static bool frame_available(pfn_t frame)
{
#if MACHINE == msim
/* MSIM device (dprinter) */
if (frame == (KA2PA(MSIM_VIDEORAM) >> ZERO_PAGE_WIDTH))
return false;
/* MSIM device (dkeyboard) */
if (frame == (KA2PA(MSIM_KBD_ADDRESS) >> ZERO_PAGE_WIDTH))
return false;
#endif
 
#if MACHINE == simics
/* Simics device (serial line) */
if (frame == (KA2PA(SERIAL_ADDRESS) >> ZERO_PAGE_WIDTH))
return false;
#endif
 
#if (MACHINE == lgxemul) || (MACHINE == bgxemul)
/* gxemul devices */
if (overlaps(frame << ZERO_PAGE_WIDTH, ZERO_PAGE_SIZE,
0x10000000, MB2SIZE(256)))
return false;
#endif
return true;
}
 
 
/** Check whether frame is safe to write
*
* Returns true if given frame is safe for read/write test.
* Returns false if given frame should not be touched.
*
*/
static bool frame_safe(pfn_t frame)
{
/* Kernel structures */
if ((frame << ZERO_PAGE_WIDTH) < KA2PA(config.base))
return false;
/* Kernel */
if (overlaps(frame << ZERO_PAGE_WIDTH, ZERO_PAGE_SIZE,
KA2PA(config.base), config.kernel_size))
return false;
/* Kernel stack */
if (overlaps(frame << ZERO_PAGE_WIDTH, ZERO_PAGE_SIZE,
KA2PA(config.stack_base), config.stack_size))
return false;
/* Init tasks */
bool safe = true;
count_t i;
for (i = 0; i < init.cnt; i++)
if (overlaps(frame << ZERO_PAGE_WIDTH, ZERO_PAGE_SIZE,
KA2PA(init.tasks[i].addr), init.tasks[i].size)) {
safe = false;
break;
}
return safe;
}
 
static void frame_add_region(pfn_t start_frame, pfn_t end_frame)
{
if (end_frame > start_frame) {
/* Convert 1M frames to 16K frames */
pfn_t first = ADDR2PFN(start_frame << ZERO_PAGE_WIDTH);
pfn_t count = ADDR2PFN((end_frame - start_frame) << ZERO_PAGE_WIDTH);
/* Interrupt vector frame is blacklisted */
pfn_t conf_frame;
if (first == 0)
conf_frame = 1;
else
conf_frame = first;
zone_create(first, count, conf_frame, 0);
if (phys_regions_count < MAX_REGIONS) {
phys_regions[phys_regions_count].start = first;
phys_regions[phys_regions_count].count = count;
phys_regions_count++;
}
}
}
 
 
/** Create memory zones
*
* If ARC is known, read information from ARC, otherwise
* assume some defaults.
* - blacklist first FRAME because there is an exception vector
* Walk through available 256 KB chunks of physical
* memory and create zones.
*
* Note: It is assumed that the TLB is not yet being
* used in any way, thus there is no interference.
*
*/
void frame_arch_init(void)
{
if (!arc_frame_init()) {
zone_create(0, ADDR2PFN(CONFIG_MEMORY_SIZE), 1, 0);
/*
* Blacklist interrupt vector
*/
frame_mark_unavailable(0, 1);
ipl_t ipl = interrupts_disable();
/* Clear and initialize TLB */
cp0_pagemask_write(ZERO_PAGE_MASK);
cp0_entry_lo0_write(0);
cp0_entry_lo1_write(0);
cp0_entry_hi_write(0);
 
count_t i;
for (i = 0; i < TLB_ENTRY_COUNT; i++) {
cp0_index_write(i);
tlbwi();
}
pfn_t start_frame = 0;
pfn_t frame;
bool avail = true;
/* Walk through all 1 MB frames */
for (frame = 0; frame < ZERO_FRAMES; frame++) {
if (!frame_available(frame))
avail = false;
else {
if (frame_safe(frame)) {
entry_lo_t lo0;
entry_lo_t lo1;
entry_hi_t hi;
tlb_prepare_entry_lo(&lo0, false, true, true, false, frame << (ZERO_PAGE_WIDTH - 12));
tlb_prepare_entry_lo(&lo1, false, false, false, false, 0);
tlb_prepare_entry_hi(&hi, ZERO_PAGE_ASID, ZERO_PAGE_ADDR);
cp0_pagemask_write(ZERO_PAGE_MASK);
cp0_entry_lo0_write(lo0.value);
cp0_entry_lo1_write(lo1.value);
cp0_entry_hi_write(hi.value);
cp0_index_write(ZERO_PAGE_TLBI);
tlbwi();
ZERO_PAGE_VALUE = 0;
if (ZERO_PAGE_VALUE != 0)
avail = false;
else {
ZERO_PAGE_VALUE = 0xdeadbeef;
if (ZERO_PAGE_VALUE != 0xdeadbeef)
avail = false;
#if (MACHINE == lgxemul) || (MACHINE == bgxemul)
else {
ZERO_PAGE_VALUE_KSEG1(frame) = 0xaabbccdd;
if (ZERO_PAGE_VALUE_KSEG1(frame) != 0xaabbccdd)
avail = false;
}
#endif
}
}
}
if (!avail) {
frame_add_region(start_frame, frame);
start_frame = frame + 1;
avail = true;
}
}
frame_add_region(start_frame, frame);
/* Blacklist interrupt vector frame */
frame_mark_unavailable(0, 1);
/* Cleanup */
cp0_pagemask_write(ZERO_PAGE_MASK);
cp0_entry_lo0_write(0);
cp0_entry_lo1_write(0);
cp0_entry_hi_write(0);
cp0_index_write(ZERO_PAGE_TLBI);
tlbwi();
interrupts_restore(ipl);
}
 
 
void physmem_print(void)
{
printf("Base Size\n");
printf("---------- ----------\n");
count_t i;
for (i = 0; i < phys_regions_count; i++) {
printf("%#010x %10u\n",
PFN2ADDR(phys_regions[i].start), PFN2ADDR(phys_regions[i].count));
}
}
 
/** @}
*/
/branches/tracing/kernel/arch/mips32/src/interrupt.c
38,7 → 38,6
#include <arch.h>
#include <arch/cp0.h>
#include <time/clock.h>
#include <arch/drivers/arc.h>
#include <ipc/sysipc.h>
#include <ddi/device.h>
 
/branches/tracing/kernel/arch/mips32/src/drivers/arc.c
File deleted
/branches/tracing/kernel/arch/mips32/src/drivers/msim.c
39,12 → 39,9
#include <arch/cp0.h>
#include <console/console.h>
#include <sysinfo/sysinfo.h>
#include <ddi/ddi.h>
 
/** Address of devices. */
#define MSIM_VIDEORAM 0xB0000000
#define MSIM_KBD_ADDRESS 0xB0000000
#define MSIM_KBD_IRQ 2
 
static parea_t msim_parea;
static chardev_t console;
static irq_t msim_irq;
 
158,6 → 155,16
sysinfo_set_item_val("kbd.devno", NULL, devno);
sysinfo_set_item_val("kbd.inr", NULL, MSIM_KBD_IRQ);
sysinfo_set_item_val("kbd.address.virtual", NULL, MSIM_KBD_ADDRESS);
msim_parea.pbase = KA2PA(MSIM_VIDEORAM);
msim_parea.vbase = MSIM_VIDEORAM;
msim_parea.frames = 1;
msim_parea.cacheable = false;
ddi_parea_register(&msim_parea);
sysinfo_set_item_val("fb", NULL, true);
sysinfo_set_item_val("fb.kind", NULL, 3);
sysinfo_set_item_val("fb.address.physical", NULL, KA2PA(MSIM_VIDEORAM));
}
 
/** @}
/branches/tracing/kernel/arch/ia32/include/atomic.h
113,7 → 113,7
"xchgl %0, %1\n"
"testl %1, %1\n"
"jnz 0b\n"
: "+m" (val->count), "=r"(tmp)
: "+m" (val->count), "=&r"(tmp)
);
/*
* Prevent critical section code from bleeding out this way up.
/branches/tracing/kernel/arch/ia32/include/mm/page.h
40,8 → 40,6
#define PAGE_WIDTH FRAME_WIDTH
#define PAGE_SIZE FRAME_SIZE
 
#define PAGE_COLOR_BITS 0 /* dummy */
 
#ifdef KERNEL
 
#ifndef __ASM__
/branches/tracing/kernel/arch/ia32/Makefile.inc
29,11 → 29,15
## Toolchain configuration
#
 
ifndef CROSS_PREFIX
CROSS_PREFIX = /usr/local
endif
 
BFD_NAME = elf32-i386
BFD_ARCH = i386
BFD = binary
TARGET = i686-pc-linux-gnu
TOOLCHAIN_DIR = /usr/local/i686
TOOLCHAIN_DIR = $(CROSS_PREFIX)/i686
 
DEFS += -DMACHINE=$(MACHINE) -D__32_BITS__
 
74,7 → 78,7
CONFIG_HT = n
endif
ifeq ($(MACHINE),core)
FPU_NO_CFLAGS = -mno-mmmx -mno-sse -mno-sse2 -mno-sse3
FPU_NO_CFLAGS = -mno-mmx -mno-sse -mno-sse2 -mno-sse3
CMN2 = -march=prescott
GCC_CFLAGS += $(CMN2)
ICC_CFLAGS += $(CMN2)
/branches/tracing/kernel/arch/ia32/src/asm.S
71,7 → 71,7
* @param MEMCPY_SRC(%esp) Source address.
* @param MEMCPY_SIZE(%esp) Size.
*
* @return MEMCPY_SRC(%esp) on success and 0 on failure.
* @return MEMCPY_DST(%esp) on success and 0 on failure.
*/
memcpy:
memcpy_from_uspace:
96,7 → 96,7
0:
movl %edx, %edi
movl %eax, %esi
movl MEMCPY_SRC(%esp), %eax /* MEMCPY_SRC(%esp), success */
movl MEMCPY_DST(%esp), %eax /* MEMCPY_DST(%esp), success */
ret
/*
/branches/tracing/kernel/arch/ia32/src/smp/smp.c
155,7 → 155,7
* Prepare new GDT for CPU in question.
*/
gdt_new = (struct descriptor *) malloc(GDT_ITEMS *
sizeof(struct descriptor), FRAME_ATOMIC);
sizeof(struct descriptor), FRAME_ATOMIC | FRAME_LOW_4_GiB);
if (!gdt_new)
panic("couldn't allocate memory for GDT\n");
 
/branches/tracing/kernel/arch/ia32/src/mm/as.c
39,9 → 39,7
/** Architecture dependent address space init. */
void as_arch_init(void)
{
#ifndef __OBJC__
as_operations = &as_pt_operations;
#endif
}
 
/** @}
/branches/tracing/kernel/arch/ia32/src/userspace.c
70,6 → 70,10
"pushl %3\n"
"pushl %4\n"
"movl %5, %%eax\n"
 
/* %ebx is defined to hold pcb_ptr - set it to 0 */
"xorl %%ebx, %%ebx\n"
 
"iret\n"
:
: "i" (selector(UDATA_DES) | PL_USER),
/branches/tracing/kernel/arch/ia32/src/drivers/ega.c
93,12 → 93,6
sysinfo_set_item_val("fb.width", NULL, ROW);
sysinfo_set_item_val("fb.height", NULL, ROWS);
sysinfo_set_item_val("fb.address.physical", NULL, VIDEORAM);
sysinfo_set_item_val("fb.address.color", NULL, PAGE_COLOR((uintptr_t)
videoram));
#ifndef CONFIG_FB
putchar('\n');
#endif
}
 
static void ega_display_char(char ch)