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.
teodori
Member
Posts: 103 Joined: Wed Nov 14, 2012 4:55 pm
Post
by teodori » Thu Sep 12, 2013 4:30 pm
Hello everyone, I managed to go into Long Mode with Compatibility SubMode, but what I wanted is Long Mode with 64-Bit SubMode. I created a 64 bit GDT an loaded it, but bochs tells me that I am in:
Code: Select all
00014090084i[BIOS ] Booting from 0000:7c00
00014173256i[CPU0 ] WARNING: HLT instruction with IF=0!
00243956000p[SDL ] >>PANIC<< User requested shutdown.
00243956000i[CPU0 ] CPU is in compatibility mode (halted)
00243956000i[CPU0 ] CS.d_b = 32 bit
00243956000i[CPU0 ] SS.d_b = 32 bit
00243956000i[CPU0 ] EFER = 0x00000500
00243956000i[CPU0 ] | RAX=000000003f224f22 RBX=0000000000200003
00243956000i[CPU0 ] | RCX=00000000c0000080 RDX=0000000000000000
00243956000i[CPU0 ] | RSP=0000000000000200 RBP=0000000000000099
00243956000i[CPU0 ] | RSI=00000000000e00bb RDI=0000000000005000
00243956000i[CPU0 ] | R8=0000000000000000 R9=0000000000000000
00243956000i[CPU0 ] | R10=0000000000000000 R11=0000000000000000
00243956000i[CPU0 ] | R12=0000000000000000 R13=0000000000000000
00243956000i[CPU0 ] | R14=0000000000000000 R15=0000000000000000
00243956000i[CPU0 ] | IOPL=0 id vip vif ac vm rf nt of df if tf sf zf af PF cf
00243956000i[CPU0 ] | SEG selector base limit G D
00243956000i[CPU0 ] | SEG sltr(index|ti|rpl) base limit G D
00243956000i[CPU0 ] | CS:0008( 0001| 0| 0) 00000000 ffffffff 1 1
00243956000i[CPU0 ] | DS:0010( 0002| 0| 0) 00000000 ffffffff 1 1
00243956000i[CPU0 ] | SS:0010( 0002| 0| 0) 00000000 ffffffff 1 1
00243956000i[CPU0 ] | ES:0010( 0002| 0| 0) 00000000 ffffffff 1 1
00243956000i[CPU0 ] | FS:0010( 0002| 0| 0) 00000000 ffffffff 1 1
00243956000i[CPU0 ] | GS:0010( 0002| 0| 0) 00000000 ffffffff 1 1
00243956000i[CPU0 ] | MSR_FS_BASE:0000000000000000
00243956000i[CPU0 ] | MSR_GS_BASE:0000000000000000
00243956000i[CPU0 ] | RIP=00000000000060ca (00000000000060ca)
00243956000i[CPU0 ] | CR0=0xe0000011 CR2=0x0000000000000000
00243956000i[CPU0 ] | CR3=0x00001000 CR4=0x000000b0
00243956000i[CPU0 ] 0x00000000000060ca>> jmp .-3 (0x000060c9) : EBFD
00243956000i[CMOS ] Last time is 1379024977 (Fri Sep 13 00:29:37 2013)
00243956000i[ ] restoring default signal behavior
00243956000i[CTRL ] quit_sim called with exit code 1
What am I doing wrong?
xenos
Member
Posts: 1121 Joined: Thu Aug 11, 2005 11:00 pm
Libera.chat IRC: xenos1984
Location: Tartu, Estonia
Contact:
Post
by xenos » Thu Sep 12, 2013 5:19 pm
Did you make a far jump to a 64 bit code segment?
teodori
Member
Posts: 103 Joined: Wed Nov 14, 2012 4:55 pm
Post
by teodori » Thu Sep 12, 2013 5:43 pm
Hm yeah I did one... but when I am in Compatibility Mode I can't use far jumps anymore. I know how to get to Long Mode, but I don't know how to get to 64-Bit Mode. Do I have to load the 64-Bit GDT before doing the far jump, like when I switch from 16-Bit to 32-Bit?
I looked up in
http://wiki.osdev.org/User:Stephanvansc ... it_Submode
Code: Select all
# Load Control Register CR4
# Enable Page Size Extension (Bit 4 in CR4)
# Enable Physical Address Extension (Bit 5 in CR4)
# Enable Page Global Enabled (Bit 7 in CR4)
# Store Control Register CR4
movl %cr4, %eax
orl $(1<<4), %eax
orl $(1<<5), %eax
orl $(1<<7), %eax
movl %eax, %cr4
# Use Model Specific Register 0xC0000080
# Read from MSR
# Enable Long Mode (Bit 8 in MSR)
# Write to MSR
movl $0xc0000080, %ecx
rdmsr
orl $(1<<8), %eax
wrmsr
# Load Control Register CR0
# Enable Paging (Bit 31 in CR0)
# Store Control Register CR0
movl %cr0, %eax
orl $(1<<31), %eax
movl %eax, %cr0
# Setup all Segment Registers
# and reload Code Segment, Instruction Pointer
movw $0x0010, %ax
movw %ax, %ds
movw %ax, %es
movw %ax, %fs
movw %ax, %gs
movw %ax, %ss
ljmp $0x0008, $(INITSEG * 0x10 + JumpToLM)
JumpToLM:
.code64
# Load Global Descriptor Table
lgdt gdt64ptr
xenos
Member
Posts: 1121 Joined: Thu Aug 11, 2005 11:00 pm
Libera.chat IRC: xenos1984
Location: Tartu, Estonia
Contact:
Post
by xenos » Fri Sep 13, 2013 12:03 am
teodori wrote: Hm yeah I did one... but when I am in Compatibility Mode I can't use far jumps anymore.
Of course you can. That's also what the code you quoted is doing - it enters Long Mode, reloads the segment registers and does a far jump.
Do I have to load the 64-Bit GDT before doing the far jump, like when I switch from 16-Bit to 32-Bit?
Yes - you need a 64-bit code segment to which you can do the far jump, and that should be in your 64-bit GDT.
xenos
Member
Posts: 1121 Joined: Thu Aug 11, 2005 11:00 pm
Libera.chat IRC: xenos1984
Location: Tartu, Estonia
Contact:
Post
by xenos » Fri Sep 13, 2013 11:09 am