Page 1 of 2
a problem with TSS
Posted: Thu Oct 18, 2007 5:47 am
by mohammed
this the code
Code: Select all
#define ACS_TSS_GATE 0x09
#define stack_size 1024
#define max_tasks 1
unsigned char task_stack[stack_size];
task();
typedef struct {
unsigned long link,
esp0,
ss0,
esp1,
ss1,
esp2,
ss2,
cr3,
eip,
eflags,
eax,
ecx,
edx,
ebx,
esp,
ebp,
esi,
edi,
es,
cs,
ss,
ds,
fs,
gs,
ldtr;
unsigned int trace,
io_map_addr;
} TSS;
initialize_tasks()
{
TSS tss[max_tasks];
/* number base limit type granularity */
gdt_set_gate(3 , tss[0], sizeof(TSS), ACS_TSS_GATE, 0xCF); /*selector is 0x18*/
gdt_flush();
__asm__ __volatile__("lidt 0x0 \n\t");
tss[0].trace = 0;
tss[0].io_map_addr = sizeof(TSS);
tss[0].ldtr = 0;
tss[0].fs = 0;
tss[0].ds = tss[0].es = tss[0].ss = 0x10;
tss[0].esp = (unsigned int)&task_stack+stack_size;
tss[0].cs = 0x10;
tss[0].eip = (unsigned int)&task;
tss[0].eflags = 0x202L;
__asm__ __volatile__("ltr 0x18 ");
}
task()
{
puts("i am task one!!!\n");
for(;;);
}
when i call initialize_tasks from main it goes back to the grub menu
Code: Select all
void main()
{
gdt_install();
idt_install();
isrs_install();
irq_install();
keyboard_install();
__asm__ __volatile__ ("sti");
cls();
puts("Hello World!\n");
initialize_tasks();
for (;;);
}
Posted: Thu Oct 18, 2007 5:57 am
by AJ
OK - a couple of errors which may not be the cause of the problem:
1) You set CS = 0x10. Do you mean CS = 0x08?
2) You do not switch tasks with LTR. If you are using hardware task switching, you set up a blank TSS for the current task to save its state in to and call LTR on that. You would then have a second TSS for the new task and far jump to the new TSS to initialise it.
Do you have the output of bochsout.txt (or whatever your error log file is called)? That will help no end with trying to debug the problem further.
Cheers,
Adam
Posted: Thu Oct 18, 2007 6:08 am
by JamesM
1) iomap_addr and base are SIXTEEN BIT integers, that is "unsigned short" not "unsigned int" on 32 bit systems.
2) You're setting your code segment and data segment descriptors to the same value. EWRONG.
3) Why are you setting your iomap_base as sizeof(TSS)?!!?!?
4) are you doing software or hardware switching? This seems to be a mush of the two (not in a good way).
5) your debugging SUCKS. "It goes back to the grub menu". What is this supposed to mean? What I ASSUME you mean is "the system force-restarted and ended up back at the grub menu" which would make more sense.
6) your debugging SUCKS. Have you actually tried to isolate the line that kills your kernel? I assume it's the LTR line but it might not be.
7) The way you ask questions SUCKS. "This is my code, it doesn't work. Why doesn't it work? ?!?!?!!1 fix it 4 mez kthxbai lolz!!!111"
JamesM
Posted: Thu Oct 18, 2007 6:18 am
by os64dev
1) the TSS is on the stack
Posted: Thu Oct 18, 2007 7:11 am
by JamesM
os64dev: HA! I didnt even spot that!
Posted: Thu Oct 18, 2007 7:29 am
by AJ
at least you found more of the problems than I did!
Posted: Thu Oct 18, 2007 9:39 pm
by xyjamepa
Hi ...
Can we see your GDT init function...
Also about your code, in your initialize_tasks you have to disable ints at first,
and when you finish it enable it,
I think no need for this
Code: Select all
__asm__ __volatile__("lidt 0x0 \n\t");
your multitasking consists of two tasks main(),task() so this
should be
that means each task has its own tss.
Posted: Fri Oct 19, 2007 12:56 pm
by mohammed
Code: Select all
void gdt_set_gate(int num, unsigned long base, unsigned long limit, unsigned char access, unsigned char gran)
{
/* Setup the descriptor base address */
gdt[num].base_low = (base & 0xFFFF);
gdt[num].base_middle = (base >> 16) & 0xFF;
gdt[num].base_high = (base >> 24) & 0xFF;
/* Setup the descriptor limits */
gdt[num].limit_low = (limit & 0xFFFF);
gdt[num].granularity = ((limit >> 16) & 0x0F);
/* Finally, set up the granularity and access flags */
gdt[num].granularity |= (gran & 0xF0);
gdt[num].access = access;
}
is this correct to link the tss entry with the function by this
tss[0].eip = (unsigned int)&task;
i don't want to make any task switching now i just want to load the firts task and then return to main ..main is not a task
Code: Select all
#define ACS_TSS_GATE 0x09
#define stack_size 1024
#define max_tasks 1
unsigned char task_stack[stack_size];
task();
typedef struct {
unsigned long link,
esp0,
ss0,
esp1,
ss1,
esp2,
ss2,
cr3,
eip,
eflags,
eax,
ecx,
edx,
ebx,
esp,
ebp,
esi,
edi,
es,
cs,
ss,
ds,
fs,
gs,
ldtr;
unsigned int trace,
io_map_addr;
} TSS;
initialize_tasks()
{
TSS tss[max_tasks];
/* number base limit type granularity */
gdt_set_gate(3 , tss[0], sizeof(TSS), ACS_TSS_GATE, 0xCF); /*selector is 0x18*/
gdt_flush();
tss[0].cs = 0x08;
tss[0].ds=tss[0].fs=tss[0].gs=0x10;
tss[0].eip = (unsigned int)&task;
tss[0].eflags = 0x202L;
__asm__ __volatile__("ltr 0x18"); /*do i need to jmp to ox18 or load the TR is enough to load the task ?*/
}
task()
{
puts("i am task one!!!\n");
__asm__ __volatile__("iret");
}
is there a problem with that ??
Posted: Fri Oct 19, 2007 2:43 pm
by JamesM
Could you please at least TRY and debug it yourself? You are taking advantage of a free resource.
Posted: Fri Oct 19, 2007 3:46 pm
by os64dev
and you were given a lot of problem reports with respect to your code and managed to fix just one. could you at least make an effort to implement the changes we suggested. If you ask our help and disregard it in a moment, it leaves us no option then to disregard you.If you don't understand the subject completely read about it and tell what you don't understand. We are likely to help you better then.
Posted: Sat Oct 20, 2007 5:14 am
by mohammed
i changed all the errors that you told me about what errors that i didn't change????
Code: Select all
00051590620i[CPU0 ] >> : ltr word ptr ds:0x18
00051590620i[SYS ] bx_pc_system_c::Reset(SOFTWARE) called
00051590620i[APIC0] local apic in CPU 0 initializing
00051594360i[BIOS ] $Revision: 1.160 $ $Date: 2006/01/25 17:51:49 $
00051908297i[KBD ] reset-disable command received
00055968572e[HD ] ata0: device set to 0 which does not exist
00055968865e[HD ] ata0: device set to 1 which does not exist
00055969157e[HD ] ata1: device set to 0 which does not exist
00055969450e[HD ] ata1: device set to 1 which does not exist
00055971974i[FDD ] controller reset in software
00058507875i[BIOS ] int13_harddisk: function 41, unmapped device for ELDL=80
00058512631i[BIOS ] int13_harddisk: function 08, unmapped device for ELDL=80
00058517273i[BIOS ] *** int 15h function AX=00C0, BX=0000 not yet supported!
Posted: Sat Oct 20, 2007 7:22 am
by JamesM
first thing I spot (AGAIN!):
Code: Select all
typedef struct {
unsigned long link,
esp0,
ss0,
esp1,
ss1,
esp2,
ss2,
cr3,
eip,
eflags,
eax,
ecx,
edx,
ebx,
esp,
ebp,
esi,
edi,
es,
cs,
ss,
ds,
fs,
gs,
ldtr;
unsigned int trace,
io_map_addr;
} TSS;
I told you, the last two entries are 16-bit. That means "unsigned short" , not "unsigned int".
JamesM
Posted: Sat Oct 20, 2007 8:46 am
by os64dev
TSS still on the stack
Posted: Sun Oct 21, 2007 5:56 am
by mohammed
i changed it to unsigned short in my code but i forgot to change it here
what do you mean by the TSS is on the stack ?
mov ax,0x18
ltr ax
will that solve the problem ?
i read in the manual that loading the TR is not enough to make a task switching where should i jmp to the selector of the TSS descriptor or to the function itself ..or should i assign a selector for the cs of the task and then jmp to it ?
why this is happening ?
Code: Select all
00051590620i[CPU0 ] >> : ltr word ptr ds:0x18
00051590620i[SYS ] bx_pc_system_c::Reset(SOFTWARE) called
Posted: Sun Oct 21, 2007 2:09 pm
by AJ
mohammed wrote:
what do you mean by the TSS is on the stack ?
Your TSS is a local variable. Local variables are stored on the stack - this means that once your function returns, the TSS will at some point be overwritten with other data.
Cheers,
Adam