FrameBuffer cpu reset while trying to draw a pixel
Posted: Tue Mar 02, 2021 7:31 am
I'm trying to implement a framebuffer on my 64bit kernel, i decided to use multiboot2 tags to enable it.
So far i managed to enable the framebuffer and get information back from it.
The multiboot header is the following:
And when i boot into the kernel i can find a framebuffer_tag structure in the info passed by the bootloader. I also tried to print the information and they looks pretty accurate:
But now i wrote a small function that was just trying to put a pixel somewhere, but no matter what value i write in the video memory i always get the same error. The funcion is this one:
I tried to write different value on pixel address and change values but whatever i try to write, or whatever position i try to get i always get a cpu reset (probably a triple fault)
So what can be the reason?
Actually i haven't implemente interrupt handling yet was trying to sortout basic screen i/o first.
I'm in 64bit long mode. So paging is already enabled (loaded in boot phase), gdt loaded.
I was wondering if the problem can be the address returned by the bootloader that is not mapped ?
But well why in the multiboot2 example should works properly?
Another thing that is not clear to me, while looking at different tutorials vesa mode and framebuffer are more or less the same thing? writing into both of them is done the same way? Becasue sometime i read of them like different options, but then thet tutorials mention the vesa driver as the same thing.
So far i managed to enable the framebuffer and get information back from it.
The multiboot header is the following:
Code: Select all
section .multiboot_header
header_start:
align 8
dd 0xe85250d6 ;magic_number
dd 0 ;Protected mode
dd header_end - header_start ;Header length
;compute checksum
dd 0x100000000 - (0xe85250d6 + 0 + (header_end - header_start))
framebuffer_tag_start:
dw 0x05 ;Type: framebuffer
dw 0x01 ;Optional tag
dd framebuffer_tag_end - framebuffer_tag_start ;size
dd 0 ;Width - if 0 we let the bootloader decide
dd 0 ;Height - same as above
dd 0 ;Depth - same as above
framebuffer_tag_end:
;here ends the required part of the multiboot header
;The following is the end tag, must be always present
;end tag
align 8
dw 0 ;type
dw 0 ;flags
dd 8 ;size
header_end:
All numbers above are Hex numbers!Found Multiboot framebuffer: 8
---framebuffer-type: 1
---framebuffer-width: 400
---framebuffer-height: 300
---framebuffer-address: FD000000
---framebuffer-bpp: 20
But now i wrote a small function that was just trying to put a pixel somewhere, but no matter what value i write in the video memory i always get the same error. The funcion is this one:
Code: Select all
void *FRAMEBUFFER_MEM = 0;
unsigned int FRAMEBUFFER_PITCH = 0;
unsigned int FRAMEBUFFER_POS_X = 0;
unsigned int FRAMEBUFFER_POS_Y = 0;
unsigned char FRAMEBUFFER_BPP = 0;
void set_fb_data(struct multiboot_tag_framebuffer *fbtag){
FRAMEBUFFER_MEM = (void*)(unsigned long)fbtag->common.framebuffer_addr;
FRAMEBUFFER_PITCH = fbtag->common.framebuffer_pitch;
FRAMEBUFFER_BPP = fbtag->common.framebuffer_bpp;
multiboot_uint32_t *pixel = FRAMEBUFFER_MEM + fbtag->common.framebuffer_pitch * 1 + 4 * 1;
*pixel = 0xFFFFFFFF;
//*FRAMEBUFFER_MEM=4;
//multiboot_uint16_t *pixel =
// unsigned int *px_addr = FRAMEBUFFER_MEM + 3 * FRAMEBUFFER_BPP + 10 * FRAMEBUFFER_BPP;
// *px_addr++ = 4;
}
So what can be the reason?
Actually i haven't implemente interrupt handling yet was trying to sortout basic screen i/o first.
I'm in 64bit long mode. So paging is already enabled (loaded in boot phase), gdt loaded.
I was wondering if the problem can be the address returned by the bootloader that is not mapped ?
But well why in the multiboot2 example should works properly?
Another thing that is not clear to me, while looking at different tutorials vesa mode and framebuffer are more or less the same thing? writing into both of them is done the same way? Becasue sometime i read of them like different options, but then thet tutorials mention the vesa driver as the same thing.