Subversion Repositories HelenOS-historic

Compare Revisions

Ignore whitespace Rev 26 → Rev 27

/SPARTAN/trunk/src/Makefile.config
22,7 → 22,7
#TEST_DIR=synch/rwlock1/
#TEST_DIR=synch/rwlock2/
#TEST_DIR=synch/rwlock3/
TEST_DIR=synch/rwlock4/
#TEST_DIR=synch/rwlock5/
#TEST_DIR=synch/rwlock4/
TEST_DIR=synch/rwlock5/
#TEST_DIR=synch/semaphore1/
#TEST_DIR=synch/semaphore2/
/SPARTAN/trunk/src/main/main.c
118,6 → 118,8
#ifdef __SMP__
mp_init(); /* Multiprocessor */
#endif /* __SMP__ */
printf("config.cpu_count=%d\n", config.cpu_count);
 
cpu_init();
calibrate_delay_loop();
/SPARTAN/trunk/arch/ia32/include/smp/apic.h
98,6 → 98,13
#define L_APIC_IDShift 24
#define L_APIC_IDMask 0xf
 
/* Local APIC Version Register */
#define LAVR (0x030/sizeof(__u32))
#define LAVR_Mask 0xff
#define is_local_apic(x) (((x)&LAVR_Mask&0xf0)==0x1)
#define is_82489DX_apic(x) ((((x)&LAVR_Mask&0xf0)==0x0))
#define is_local_xapic(x) (((x)&LAVR_Mask)==0x14)
 
/* IO APIC */
#define IOREGSEL (0x00/sizeof(__u32))
#define IOWIN (0x10/sizeof(__u32))
/SPARTAN/trunk/arch/ia32/include/asm.h
58,4 → 58,7
extern void halt_cpu(void);
extern void cpu_sleep(void);
 
extern void write_dr0(__u32 v);
extern __u32 read_dr0(void);
 
#endif
/SPARTAN/trunk/arch/ia32/include/cpu.h
34,7 → 34,7
#include <arch/pm.h>
 
#ifdef __SMP__
#define CPU_ID_ARCH ((config.cpu_active>1)?l_apic_id():0)
#define CPU_ID_ARCH (read_dr0())
#else
#define CPU_ID_ARCH (0)
#endif
/SPARTAN/trunk/arch/ia32/src/ia32.c
49,6 → 49,8
{
pm_init();
 
write_dr0(config.cpu_active - 1);
 
if (config.cpu_active == 1) {
i8042_init(); /* a20 bit */
i8259_init(); /* PIC */
/SPARTAN/trunk/arch/ia32/src/smp/apic.c
103,8 → 103,6
}
}
 
 
 
/*
* Configure the BSP's lapic.
*/
183,7 → 181,7
l_apic[ICRhi] = hi;
l_apic[ICRlo] = lo;
 
/*
* According to MP Specification, 20us should be enough to
* deliver the IPI.
195,7 → 193,7
lo = l_apic[ICRlo] & ICRloClear;
if (lo & SEND_PENDING)
printf("IPI is pending.\n");
 
l_apic[ICRlo] = lo | DLVRMODE_INIT | DESTMODE_PHYS | LEVEL_DEASSERT | SHORTHAND_DEST | TRGRMODE_LEVEL;
 
/*
203,18 → 201,19
*/
delay(10000);
 
/*
* MP specification says this should not be done for 82489DX-based
* l_apic's. However, everything is ok as long as STARTUP IPI is ignored
* by 8249DX.
*/
for (i = 0; i < 2; i++) {
lo = l_apic[ICRlo] & ICRloClear;
lo |= ((__address) ap_boot) / 4096; /* calculate the reset vector */
l_apic[ICRlo] = lo | DLVRMODE_STUP | DESTMODE_PHYS | LEVEL_ASSERT | SHORTHAND_DEST | TRGRMODE_LEVEL;
delay(200);
if (!is_82489DX_apic(l_apic[LAVR])) {
/*
* If this is not 82489DX-based l_apic we must send two STARTUP IPI's.
*/
for (i = 0; i<2; i++) {
lo = l_apic[ICRlo] & ICRloClear;
lo |= ((__address) ap_boot) / 4096; /* calculate the reset vector */
l_apic[ICRlo] = lo | DLVRMODE_STUP | DESTMODE_PHYS | LEVEL_ASSERT | SHORTHAND_DEST | TRGRMODE_LEVEL;
delay(200);
}
}
return apic_poll_errors();
}
 
221,20 → 220,7
void l_apic_init(void)
{
__u32 tmp, t1, t2;
int cpu_id = config.cpu_active - 1;
 
/*
* Here we set local APIC ID's so that they match operating system's CPU ID's
* This operation is dangerous as it is model specific.
* TODO: some care should be taken.
* NOTE: CPU may not be used to define APIC ID
*/
if (l_apic_id() != cpu_id) {
l_apic[L_APIC_ID] &= L_APIC_IDClear;
l_apic[L_APIC_ID] |= (l_apic[L_APIC_ID]&L_APIC_IDClear)|((cpu_id)<<L_APIC_IDShift);
}
 
l_apic[LVT_Err] |= (1<<16);
l_apic[LVT_LINT0] |= (1<<16);
l_apic[LVT_LINT1] |= (1<<16);
244,8 → 230,8
 
l_apic[TPR] &= TPRClear;
 
if (CPU->arch.family >= 6)
enable_l_apic_in_msr();
// if (CPU->arch.family >= 6)
// enable_l_apic_in_msr();
tmp = l_apic[ICRlo] & ICRloClear;
l_apic[ICRlo] = tmp | DLVRMODE_INIT | DESTMODE_PHYS | LEVEL_DEASSERT | SHORTHAND_INCL | TRGRMODE_LEVEL;
/SPARTAN/trunk/arch/ia32/src/smp/mp.c
486,12 → 486,17
*/
if (pr[i].cpu_flags & (1<<0) == 0)
continue;
 
/*
* The bootstrap processor is already up.
*/
if (pr[i].cpu_flags & (1<<1))
continue;
 
if (pr[i].l_apic_id == l_apic_id()) {
printf("%X: bad processor entry #%d, will not send IPI to myself\n", &pr[i], i);
continue;
}
/*
* Prepare new GDT for CPU in question.
501,7 → 506,7
 
memcopy(gdt, gdt_new, GDT_ITEMS*sizeof(struct descriptor));
gdtr.base = (__address) gdt_new;
 
if (l_apic_send_init_ipi(pr[i].l_apic_id)) {
/*
* There may be just one AP being initialized at
/SPARTAN/trunk/arch/ia32/src/asm.s
52,7 → 52,20
.global memsetb
.global memsetw
.global memcmp
.global write_dr0
.global read_dr0
 
write_dr0:
pushl %eax
movl 8(%esp),%eax
movl %eax,%dr0
popl %eax
ret
read_dr0:
movl %dr0,%eax
ret
 
#
# set priority level high
cpu_priority_high:
/SPARTAN/trunk/arch/ia32/src/interrupt.c
92,7 → 92,7
void syscall(__u8 n, __u32 stack[])
{
printf("cpu%d: syscall\n", CPU->id);
thread_usleep(600);
thread_usleep(1000000);
}
 
void tlb_shootdown_ipi(__u8 n, __u32 stack[])