APIC Timer doesnot even get a one-shot(x86_64)

Question about which tools to use, bugs, the best way to implement a function, etc should go here. Don't forget to see if your question is answered in the wiki first! When in doubt post here.
Post Reply
User avatar
lemonyii
Member
Member
Posts: 153
Joined: Thu Mar 25, 2010 11:28 pm
Location: China

APIC Timer doesnot even get a one-shot(x86_64)

Post by lemonyii »

Hi

I got stuck with the STI instruction for a long time.
after kernel's startup in x86_64 mode, i reset gdt,idt,tss after setup,
and then try to initlize the APIC (i tried 8259 for a long time but failed) according to
http://forum.osdev.org/viewtopic.php?f= ... =APIC+init
but after my sti,nothing happened.(my handler is not called,never!)
i check the IF flag,it has been 1,and the idt item is conrrect.

my code:

Code: Select all

extern i64 dev_task(){
	init_i8259(); //if not for this ,a double fault will happen
	APIC_init();
	enable_int();  //just an sti instruction
}
extern i64 init_i8259(){
	outbyte(INT_M_CTL,	0x11);			// Master 8259, ICW1.
	outbyte(INT_S_CTL,	0x11);			// Slave  8259, ICW1.
	outbyte(INT_M_CTLMASK,	INT_VECTOR_IRQ0);	// Master 8259, ICW2. 
	outbyte(INT_S_CTLMASK,	INT_VECTOR_IRQ8);	// Slave  8259, ICW2. 
	outbyte(INT_M_CTLMASK,	0x4);			// Master 8259, ICW3. 
	outbyte(INT_S_CTLMASK,	0x2);			// Slave  8259, ICW3. 
	outbyte(INT_M_CTLMASK,	0x1);			// Master 8259, ICW4.
	outbyte(INT_S_CTLMASK,	0x1);			// Slave  8259, ICW4.
	outbyte(INT_M_CTLMASK,	0xFF);	// Master 8259, OCW1. 
	outbyte(INT_S_CTLMASK,	0xFF);	// Slave  8259, OCW1. 
	return 0;
}
extern i64 APIC_init(){
	sys_call(0ULL,_SYSCALL_LEVEL0,init_apic);
	sys_call(1ULL,_SYSCALL_SET_INT,INT_VECTOR_IRQ0,_int_handler_timer,SYS_INT_HANDLER_TYPE_INT64,0ULL,0ULL);
	sys_call(0ULL,_SYSCALL_LEVEL0,set_apic_timer,0x64,0xB0,0x00020000|INT_VECTOR_IRQ0);
	return 0;
}

bits 	64
align 	16
init_apic: 				;init_apic()
		pushf					; save IF
		cli
		push	rcx
		push	rsi
				
		mov  	rcx,1Bh    		; MSR IA32_APIC_BASE
		rdmsr      				; IA32_APIC_BASE
		and  	rax,0xfffffffffffff000 
		mov  	rsi,rax    		
		mov		eax,0x000001FF	;0x000001FF -> 0xFFE000F0 - enable local APIC  and set spurious int vector to 0xFF
		mov  	[rsi+0xF0],eax   
		mov		eax,0xFFFFFFFF	;0xFFFFFFFF -> 0xFEE000E0 - set destination format register to flat model
		mov		[rsi+0xE0],eax	
		mov		eax,0x00000000	;0x00000000 -> 0xFEE00080 - set the task priority register to accept all interrupts
		mov		[rsi+0x80],eax	
		
		xor		rax,rax
		pop		rsi
		pop		rcx
		popf
		ret

align 	16
set_apic_timer:				;init_apic_timer(CR,DCR,LVT)
		;0x0000000B -> 0xFEE003E0 - set timer to divide by 1
		;0x00020040 -> 0xFEE00320 - enable timer, set periodic mode, set int vector to 0x40
		;0x00000064 -> 0xFEE00380 - set initial count to 100 (and make the timer start counting)
		pushf					;save IF
		cli
		push	rcx
		push	rsi
				
		mov  	rcx,1Bh    		 
		rdmsr      			
		and  	rax,0xfffffffffffff000 
		mov  	rsi,rax    		

		pop		rax				;DCR
		mov		[rsi+0x3E0],eax
		mov		[rsi+0x320],edx ;LVT	
		mov		[rsi+0x380],edi	;CR
		
		xor		rax,rax
		pop		rcx
		popf
		ret

align 	16
_int_handler_timer:
		push	rcx
		push	rsi
		push	rax
		push	rdi
		
		mov  	rcx,1Bh    		
		rdmsr      				
		and  	rax,0xfffffffffffff000 
		mov  	rsi,rax    		
		;EOI
		xor		rax,rax		
		mov		[rsi+0xB0],eax
		;do something
		mov		rcx,80*200
		mov		rdi,0xb8000
		mov		rax,0x7244
		rep
		stosw
		ud2
		pop		rdi
		pop		rax
		pop		rsi
		pop		rcx
		iretq
i am annoyed about this. :cry:
what i am hoping to see,is just an interrupt.
Thanks & Merci !
Enjoy my life!------A fish with a tattooed retina
geppyfx
Member
Member
Posts: 87
Joined: Tue Apr 28, 2009 4:58 pm

Re: APIC Timer doesnot even get a one-shot(x86_64)

Post by geppyfx »

While you are waiting for interrupt please read 'current count register' 0390h and see if value changes over time. If not, then indeed smth wrong with lapic setup.
When you do this you can change 100 to 0xffffffff to make sure you catch the change in case timer operates in one-shot mode (by accident).
User avatar
lemonyii
Member
Member
Posts: 153
Joined: Thu Mar 25, 2010 11:28 pm
Location: China

Re: APIC Timer doesnot even get a one-shot(x86_64)

Post by lemonyii »

Thank you for replying.
I turned 100 to 0x8000 and really got a decreasing in CCR.
but...still nothing happening.The IF is surely 1.
and i used an UD2 instruction at the beginning of the handler.Surely it is not called because my kernel surely can and had ever cought the #UD.
had i missed smth?
thx
Enjoy my life!------A fish with a tattooed retina
Post Reply