2 ** Copyright 2001, Travis Geiselbrecht. All rights reserved.
3 ** Distributed under the terms of the NewOS License.
5 #include <kernel/arch/cpu.h>
6 #include <kernel/debug.h>
7 #include <kernel/int.h>
8 #include <boot/stage2.h>
10 static vcpu_struct
*vcpu
;
12 int arch_cpu_preboot_init(kernel_args
*ka
)
17 int arch_cpu_init(kernel_args
*ka
)
19 vcpu
= ka
->arch_args
.vcpu
;
21 vcpu
->kernel_asid
= 0;
27 int arch_cpu_init2(kernel_args
*ka
)
32 void sh4_set_kstack(addr_t kstack
)
34 // dprintf("sh4_set_kstack: setting kstack to 0x%x\n", kstack);
35 vcpu
->kstack
= (unsigned int *)kstack
;
38 void sh4_set_user_pgdir(addr_t pgdir
)
40 // dprintf("sh4_set_user_pgdir: setting pgdir to 0x%x\n", pgdir);
41 if((addr_t
)vcpu
->user_pgdir
!= pgdir
)
42 arch_cpu_global_TLB_invalidate();
43 vcpu
->user_pgdir
= (unsigned int *)pgdir
;
46 void sh4_invl_page(addr_t va
)
50 va
= ROUNDOWN(va
, PAGE_SIZE
);
52 int_disable_interrupts();
54 // wipe it out of the data tlbs
55 for(i
=0; i
<UTLB_COUNT
; i
++) {
56 struct utlb_addr_array
*ua
= (struct utlb_addr_array
*)(UTLB
+ (i
<< UTLB_ADDR_SHIFT
));
57 if(ua
->vpn
== (va
>> 10))
61 // wipe it out of the instruction tlbs
62 for(i
=0; i
<ITLB_COUNT
; i
++) {
63 struct itlb_addr_array
*ia
= (struct itlb_addr_array
*)(ITLB
+ (i
<< ITLB_ADDR_SHIFT
));
64 if(ia
->vpn
== (va
>> 10))
68 int_restore_interrupts();
71 void arch_cpu_invalidate_TLB_range(addr_t start
, addr_t end
)
73 for(; start
< end
; start
+= PAGE_SIZE
) {
78 void arch_cpu_invalidate_TLB_list(addr_t pages
[], int num_pages
)
81 for(i
=0; i
<num_pages
; i
++) {
82 sh4_invl_page(pages
[i
]);
86 void arch_cpu_global_TLB_invalidate()
90 int_disable_interrupts();
92 // wipe out the data tlbs
93 for(i
=0; i
<UTLB_COUNT
; i
++) {
94 struct utlb_addr_array
*ua
= (struct utlb_addr_array
*)(UTLB
+ (i
<< UTLB_ADDR_SHIFT
));
98 // wipe out the instruction tlbs
99 for(i
=0; i
<ITLB_COUNT
; i
++) {
100 struct itlb_addr_array
*ia
= (struct itlb_addr_array
*)(ITLB
+ (i
<< ITLB_ADDR_SHIFT
));
104 int_restore_interrupts();
107 void arch_cpu_sync_icache(void *address
, size_t len
)
109 PANIC_UNIMPLEMENTED();
112 int arch_cpu_user_memcpy(void *to
, const void *from
, size_t size
, addr_t
*fault_handler
)
114 char *tmp
= (char *)to
;
115 char *s
= (char *)from
;
117 *fault_handler
= (addr_t
)&&error
;
127 return ERR_VM_BAD_USER_MEMORY
;
130 int arch_cpu_user_strcpy(char *to
, const char *from
, addr_t
*fault_handler
)
132 *fault_handler
= (addr_t
)&&error
;
134 while((*to
++ = *from
++) != '\0')
142 return ERR_VM_BAD_USER_MEMORY
;
145 int arch_cpu_user_strncpy(char *to
, const char *from
, size_t size
, addr_t
*fault_handler
)
147 *fault_handler
= (addr_t
)&&error
;
149 while(size
-- && (*to
++ = *from
++) != '\0')
157 return ERR_VM_BAD_USER_MEMORY
;
160 int arch_cpu_user_memset(void *s
, char c
, size_t count
, addr_t
*fault_handler
)
162 char *xs
= (char *) s
;
164 *fault_handler
= (addr_t
)&&error
;
174 return ERR_VM_BAD_USER_MEMORY
;
177 void arch_cpu_idle(void)