mirror of
https://github.com/Mathewnd/Astral.git
synced 2026-11-01 15:08:21 +00:00
framebuffer: changes to mmap and how the ioctl information is stored and accessed
This commit is contained in:
+126
-116
@@ -4,6 +4,67 @@
|
|||||||
#include <errno.h>
|
#include <errno.h>
|
||||||
#include <arch/mmu.h>
|
#include <arch/mmu.h>
|
||||||
#include <arch/cls.h>
|
#include <arch/cls.h>
|
||||||
|
#include <kernel/alloc.h>
|
||||||
|
#include <kernel/pmm.h>
|
||||||
|
|
||||||
|
struct fb_bitfield {
|
||||||
|
uint32_t offset;
|
||||||
|
uint32_t length;
|
||||||
|
uint32_t msb_right;
|
||||||
|
};
|
||||||
|
|
||||||
|
typedef struct{
|
||||||
|
uint32_t xres;
|
||||||
|
uint32_t yres;
|
||||||
|
uint32_t xres_virtual;
|
||||||
|
uint32_t yres_virtual;
|
||||||
|
uint32_t xoffset;
|
||||||
|
uint32_t yoffset;
|
||||||
|
uint32_t bits_per_pixel;
|
||||||
|
uint32_t grayscale;
|
||||||
|
struct fb_bitfield red;
|
||||||
|
struct fb_bitfield green;
|
||||||
|
struct fb_bitfield blue;
|
||||||
|
struct fb_bitfield transp;
|
||||||
|
uint32_t nonstd;
|
||||||
|
uint32_t activate;
|
||||||
|
uint32_t height;
|
||||||
|
uint32_t width;
|
||||||
|
uint32_t accel_flags;
|
||||||
|
uint32_t pixclock;
|
||||||
|
uint32_t left_margin;
|
||||||
|
uint32_t right_margin;
|
||||||
|
uint32_t upper_margin;
|
||||||
|
uint32_t lower_margin;
|
||||||
|
uint32_t hsync_len;
|
||||||
|
uint32_t vsync_len;
|
||||||
|
uint32_t sync;
|
||||||
|
uint32_t vmode;
|
||||||
|
uint32_t rotate;
|
||||||
|
uint32_t colorspace;
|
||||||
|
uint32_t reserved[4];
|
||||||
|
}fb_var_screeninfo;
|
||||||
|
|
||||||
|
typedef struct {
|
||||||
|
char id[16];
|
||||||
|
unsigned long smem_start;
|
||||||
|
uint32_t smem_len;
|
||||||
|
uint32_t type;
|
||||||
|
uint32_t type_aux;
|
||||||
|
uint32_t visual;
|
||||||
|
uint16_t xpanstep;
|
||||||
|
uint16_t ypanstep;
|
||||||
|
uint16_t ywrapstep;
|
||||||
|
uint32_t line_length;
|
||||||
|
unsigned long mmio_start;
|
||||||
|
uint32_t mmio_len;
|
||||||
|
uint32_t accel;
|
||||||
|
uint16_t capabilities;
|
||||||
|
uint16_t reserved[2];
|
||||||
|
} fb_fix_screeninfo;
|
||||||
|
|
||||||
|
#define FB_VISUAL_TRUECOLOR 2
|
||||||
|
#define FB_TYPE_PACKED_PIXELS 0
|
||||||
|
|
||||||
static volatile struct limine_framebuffer_request fbreq = {
|
static volatile struct limine_framebuffer_request fbreq = {
|
||||||
.id = LIMINE_FRAMEBUFFER_REQUEST,
|
.id = LIMINE_FRAMEBUFFER_REQUEST,
|
||||||
@@ -12,6 +73,8 @@ static volatile struct limine_framebuffer_request fbreq = {
|
|||||||
|
|
||||||
static struct limine_framebuffer** fbs;
|
static struct limine_framebuffer** fbs;
|
||||||
static size_t fbcount;
|
static size_t fbcount;
|
||||||
|
fb_var_screeninfo* fbvs;
|
||||||
|
fb_fix_screeninfo* fbfs;
|
||||||
|
|
||||||
static int devchecks(int fb, size_t* count, size_t offset){
|
static int devchecks(int fb, size_t* count, size_t offset){
|
||||||
|
|
||||||
@@ -75,66 +138,7 @@ static int isseekable(int minor, size_t* max){
|
|||||||
#define FBIOGET_VSCREENINFO 0x4600
|
#define FBIOGET_VSCREENINFO 0x4600
|
||||||
#define FBIOPUT_VSCREENINFO 0x4601
|
#define FBIOPUT_VSCREENINFO 0x4601
|
||||||
#define FBIOGET_FSCREENINFO 0x4602
|
#define FBIOGET_FSCREENINFO 0x4602
|
||||||
|
#define FBIOBLANK 0x4611
|
||||||
struct fb_bitfield {
|
|
||||||
uint32_t offset;
|
|
||||||
uint32_t length;
|
|
||||||
uint32_t msb_right;
|
|
||||||
};
|
|
||||||
|
|
||||||
typedef struct{
|
|
||||||
uint32_t xres;
|
|
||||||
uint32_t yres;
|
|
||||||
uint32_t xres_virtual;
|
|
||||||
uint32_t yres_virtual;
|
|
||||||
uint32_t xoffset;
|
|
||||||
uint32_t yoffset;
|
|
||||||
uint32_t bits_per_pixel;
|
|
||||||
uint32_t grayscale;
|
|
||||||
struct fb_bitfield red;
|
|
||||||
struct fb_bitfield green;
|
|
||||||
struct fb_bitfield blue;
|
|
||||||
struct fb_bitfield transp;
|
|
||||||
uint32_t nonstd;
|
|
||||||
uint32_t activate;
|
|
||||||
uint32_t height;
|
|
||||||
uint32_t width;
|
|
||||||
uint32_t accel_flags;
|
|
||||||
uint32_t pixclock;
|
|
||||||
uint32_t left_margin;
|
|
||||||
uint32_t right_margin;
|
|
||||||
uint32_t upper_margin;
|
|
||||||
uint32_t lower_margin;
|
|
||||||
uint32_t hsync_len;
|
|
||||||
uint32_t vsync_len;
|
|
||||||
uint32_t sync;
|
|
||||||
uint32_t vmode;
|
|
||||||
uint32_t rotate;
|
|
||||||
uint32_t colorspace;
|
|
||||||
uint32_t reserved[4];
|
|
||||||
}fb_var_screeninfo;
|
|
||||||
|
|
||||||
typedef struct {
|
|
||||||
char id[16];
|
|
||||||
unsigned long smem_start;
|
|
||||||
uint32_t smem_len;
|
|
||||||
uint32_t type;
|
|
||||||
uint32_t type_aux;
|
|
||||||
uint32_t visual;
|
|
||||||
uint16_t xpanstep;
|
|
||||||
uint16_t ypanstep;
|
|
||||||
uint16_t ywrapstep;
|
|
||||||
uint32_t line_length;
|
|
||||||
unsigned long mmio_start;
|
|
||||||
uint32_t mmio_len;
|
|
||||||
uint32_t accel;
|
|
||||||
uint16_t capabilities;
|
|
||||||
uint16_t reserved[2];
|
|
||||||
} fb_fix_screeninfo;
|
|
||||||
|
|
||||||
#define FB_VISUAL_TRUECOLOR 2
|
|
||||||
#define FB_TYPE_PACKED_PIXELS 0
|
|
||||||
|
|
||||||
|
|
||||||
static int ioctl(int minor, unsigned long req, void* arg){
|
static int ioctl(int minor, unsigned long req, void* arg){
|
||||||
|
|
||||||
@@ -143,63 +147,24 @@ static int ioctl(int minor, unsigned long req, void* arg){
|
|||||||
|
|
||||||
struct limine_framebuffer* fb = fbs[minor];
|
struct limine_framebuffer* fb = fbs[minor];
|
||||||
switch(req){
|
switch(req){
|
||||||
case FBIOPUT_VSCREENINFO: // TODO maybe this should be done properly
|
case FBIOBLANK:
|
||||||
|
break;
|
||||||
|
case FBIOPUT_VSCREENINFO:
|
||||||
|
{
|
||||||
|
fb_var_screeninfo* i = arg;
|
||||||
|
fbvs[minor] = *i;
|
||||||
|
}
|
||||||
break;
|
break;
|
||||||
case FBIOGET_FSCREENINFO:
|
case FBIOGET_FSCREENINFO:
|
||||||
{
|
{
|
||||||
fb_fix_screeninfo* i = arg;
|
fb_fix_screeninfo* i = arg;
|
||||||
strcpy(i->id, "LIMINE FB");
|
*i = fbfs[minor];
|
||||||
i->smem_start = fb->address;
|
|
||||||
i->smem_len = fb->pitch*fb->height;
|
|
||||||
i->type = FB_TYPE_PACKED_PIXELS;
|
|
||||||
i->visual = FB_VISUAL_TRUECOLOR;
|
|
||||||
i->xpanstep = 0;
|
|
||||||
i->ypanstep = 0;
|
|
||||||
i->line_length = fb->pitch;
|
|
||||||
i->mmio_start = 0;
|
|
||||||
i->mmio_len = 0;
|
|
||||||
i->accel = 0;
|
|
||||||
i->capabilities = 0;
|
|
||||||
}
|
}
|
||||||
break;
|
break;
|
||||||
case FBIOGET_VSCREENINFO:
|
case FBIOGET_VSCREENINFO:
|
||||||
{
|
{
|
||||||
fb_var_screeninfo* i = arg;
|
fb_var_screeninfo* i = arg;
|
||||||
i->xres = fb->width;
|
*i = fbvs[minor];
|
||||||
i->yres = fb->height;
|
|
||||||
i->xres_virtual = fb->width;
|
|
||||||
i->yres_virtual = fb->height;
|
|
||||||
i->xoffset = 0;
|
|
||||||
i->yoffset = 0;
|
|
||||||
i->bits_per_pixel = fb->bpp;
|
|
||||||
i->grayscale = 0;
|
|
||||||
i->red.msb_right = 1;
|
|
||||||
i->green.msb_right = 1;
|
|
||||||
i->blue.msb_right = 1;
|
|
||||||
i->transp.msb_right = 1;
|
|
||||||
i->red.offset = fb->red_mask_shift;
|
|
||||||
i->red.length = fb->red_mask_size;
|
|
||||||
i->blue.offset = fb->blue_mask_shift;
|
|
||||||
i->blue.length = fb->blue_mask_size;
|
|
||||||
i->green.offset = fb->green_mask_shift;
|
|
||||||
i->green.length = fb->green_mask_size;
|
|
||||||
i->transp.offset = 28;
|
|
||||||
i->transp.length = 8;
|
|
||||||
i->nonstd = 0;
|
|
||||||
i->activate = 0;
|
|
||||||
i->height = 0;
|
|
||||||
i->width = 0;
|
|
||||||
i->accel_flags = 0;
|
|
||||||
i->pixclock = 0;
|
|
||||||
i->left_margin = 0;
|
|
||||||
i->upper_margin = 0;
|
|
||||||
i->lower_margin = 0;
|
|
||||||
i->right_margin = 0;
|
|
||||||
i->hsync_len = 0;
|
|
||||||
i->vsync_len = 0;
|
|
||||||
i->vmode = 0;
|
|
||||||
i->rotate = 0;
|
|
||||||
i->colorspace = 0;
|
|
||||||
}
|
}
|
||||||
break;
|
break;
|
||||||
default:
|
default:
|
||||||
@@ -216,17 +181,19 @@ static map(int minor, void* addr, size_t len, size_t offset, size_t mmuflags){
|
|||||||
|
|
||||||
int err = devchecks(minor, &properlen, offset);
|
int err = devchecks(minor, &properlen, offset);
|
||||||
|
|
||||||
|
if(properlen % PAGE_SIZE)
|
||||||
|
properlen += PAGE_SIZE;
|
||||||
|
|
||||||
properlen /= PAGE_SIZE;
|
properlen /= PAGE_SIZE;
|
||||||
|
|
||||||
if(properlen % PAGE_SIZE)
|
|
||||||
++properlen;
|
|
||||||
|
|
||||||
if(err)
|
if(err)
|
||||||
return err;
|
return err;
|
||||||
|
|
||||||
for(uintmax_t page = 0; page < len; ++page){
|
for(uintmax_t page = 0; page < properlen; ++page){
|
||||||
if(page < properlen)
|
if(page < properlen){
|
||||||
arch_mmu_map(arch_getcls()->context->context, fbs[minor]->address + offset, addr, mmuflags);
|
arch_mmu_map(arch_getcls()->context->context, (fbs[minor]->address - (size_t)limine_hhdm_offset)+ offset + PAGE_SIZE*page, addr + page*PAGE_SIZE, mmuflags);
|
||||||
|
}
|
||||||
|
|
||||||
}
|
}
|
||||||
|
|
||||||
@@ -246,14 +213,57 @@ void fb_init(){
|
|||||||
fbcount = fbreq.response->framebuffer_count;
|
fbcount = fbreq.response->framebuffer_count;
|
||||||
fbs = fbreq.response->framebuffers;
|
fbs = fbreq.response->framebuffers;
|
||||||
|
|
||||||
|
fbfs = alloc(sizeof(fb_fix_screeninfo) * fbcount);
|
||||||
|
fbvs = alloc(sizeof(fb_var_screeninfo) * fbcount);
|
||||||
|
|
||||||
|
if(fbfs == NULL || fbvs == NULL)
|
||||||
|
_panic("Out of memory", 0);
|
||||||
|
|
||||||
char name[] = { 'f', 'b', '0', 0};
|
char name[] = { 'f', 'b', '0', 0};
|
||||||
|
|
||||||
for(uintmax_t fb = 0; fb < fbcount; ++fb){
|
for(uintmax_t ifb = 0; ifb < fbcount; ++ifb){
|
||||||
|
|
||||||
devman_newdevice(name, TYPE_CHARDEV, MAJOR_FB, fb, &calls);
|
|
||||||
|
|
||||||
|
devman_newdevice(name, TYPE_CHARDEV, MAJOR_FB, ifb, &calls);
|
||||||
++name[2]; // increase the fbX num
|
++name[2]; // increase the fbX num
|
||||||
|
|
||||||
|
// initialise info
|
||||||
|
|
||||||
|
struct limine_framebuffer* fb = fbs[ifb];
|
||||||
|
|
||||||
|
// variable
|
||||||
|
{
|
||||||
|
fb_var_screeninfo* i = &fbvs[ifb];
|
||||||
|
|
||||||
|
i->xres = fb->width;
|
||||||
|
i->yres = fb->height;
|
||||||
|
i->xres_virtual = fb->width;
|
||||||
|
i->yres_virtual = fb->height;
|
||||||
|
i->bits_per_pixel = fb->bpp;
|
||||||
|
i->red.msb_right = 1;
|
||||||
|
i->green.msb_right = 1;
|
||||||
|
i->blue.msb_right = 1;
|
||||||
|
i->transp.msb_right = 1;
|
||||||
|
i->red.offset = fb->red_mask_shift;
|
||||||
|
i->red.length = fb->red_mask_size;
|
||||||
|
i->blue.offset = fb->blue_mask_shift;
|
||||||
|
i->blue.length = fb->blue_mask_size;
|
||||||
|
i->green.offset = fb->green_mask_shift;
|
||||||
|
i->green.length = fb->green_mask_size;
|
||||||
|
i->height = -1;
|
||||||
|
i->width = -1;
|
||||||
|
}
|
||||||
|
// fixed
|
||||||
|
{
|
||||||
|
fb_fix_screeninfo* i = &fbfs[ifb];
|
||||||
|
strcpy(i->id, "LIMINE FB");
|
||||||
|
i->smem_len = fb->pitch*fb->height;
|
||||||
|
i->type = FB_TYPE_PACKED_PIXELS;
|
||||||
|
i->visual = FB_VISUAL_TRUECOLOR;
|
||||||
|
i->line_length = fb->pitch;
|
||||||
|
i->mmio_len = fb->pitch*fb->height;
|
||||||
|
}
|
||||||
|
|
||||||
|
|
||||||
}
|
}
|
||||||
|
|
||||||
}
|
}
|
||||||
|
|||||||
Reference in New Issue
Block a user