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.
If you haven't enabled paging then you are not getting a page fault.
As you have told us nothing about your code, or environment, other than something that is patently false it is difficult to say much more.
Edit: I note from your previous posts, and the minimal code you show here, that you are using long mode. Paging is a requisite for this. I'm not sure what happens if you use 64-bit instructions without enabling paging. Before anything else you need to set up a page table and enable paging.
iansjack wrote:Edit: I note from your previous posts, and the minimal code you show here, that you are using long mode. Paging is a requisite for this. I'm not sure what happens if you use 64-bit instructions without enabling paging.
Nothing. It is impossible to be in long mode without paging enabled. Indeed, enabling the PG bit (while EFER.LME=1 and CR4.PAE=1 and CR3 is valid) is what makes the CPU go into long mode. However, when coming from UEFI, you will be in an identity-mapped environment. But that might be fragmented; not everything will be mapped.
@OP: Why did you show us the instructions from a different place than was reported by your exception handler? And if that is indeed the faulting instruction, your RDI is misaligned, since it is a 4-byte access, but CR2 is not divisible by 4. In any case, if you are using UEFI, allocate what memory you need for your own page tables and switch to them after ExitBootServices(). And if you just identity map all physical memory for the time being, that is good enough. Gigabyte pages are available.
Probably I use paging, but only to enter long mode. I did it with some "minimal example" guide. I thought that paging was enabled in it in such a way that CPU would be happy, and in practice I'll never use it. Is it possible?
The address shown in %cr2 is way away from anything you would expect, so I suspect the problem lies in the value of %rdi. But that's just a guess - it's very difficult to say anything sensible without seeing your code. Why not provide a link to an on-line repository?
I did it with some "minimal example" guide.
It certainly looks that way. It would be beter to do a little reading so that you understand what you are doing rather than just blindly following some example you have found.
antoni wrote:Probably I use paging, but only to enter long mode. I did it with some "minimal example" guide. I thought that paging was enabled in it in such a way that CPU would be happy, and in practice I'll never use it. Is it possible?
If you have to ask, then this is the problem
Listen to @iansjack, you should understand what the loader does, and how it sets up the environment for your kernel. You might need to tweak that according to your kernel's needs.
Take a look at my image receiver. It reads the kernel over serial line (that part you won't need), and if what received is an ELF64 executable, then it sets up long mode with identity mapping the first 1G RAM (the ACPI tables should be in it, but you can easily map 4G to be sure).
@@: stosd
add edi, 4
add eax, 2*1024*1024
dec ecx
jnz @b
You are increasing edi by 4 but entries in long mode are 8 bytes long...
Yes. The paging table is constructed in protmode, where you have only 32 bits, and we don't map over 4G (all addresses fit into 32 bits). So "stosd" puts the first 4 bytes with the address and flags, "add" simply skips another 4 bytes leaving that part as zero, that's 8 bytes in total for each entry.
It looks like I successfully addressed first gigabyte of memory and now... I get general protection fault in this same function also on mov instruction...