1
0
mirror of https://github.com/rcore-os/rCore.git synced 2024-11-22 08:06:17 +04:00

Merge pull request #24 from xy-plus/master

Improve fb driver for userspace gui programs
This commit is contained in:
Runji Wang 2019-11-02 15:07:24 +08:00 committed by GitHub
commit 3bf737eaad
No known key found for this signature in database
GPG Key ID: 4AEE18F83AFDEB23
5 changed files with 240 additions and 82 deletions

View File

@ -1,6 +1,5 @@
//! Framebuffer
use crate::fs::vga::{fb_fix_screeninfo, fb_var_screeninfo};
use alloc::string::String;
use core::fmt;
use lazy_static::lazy_static;
@ -235,20 +234,6 @@ impl Framebuffer {
pub fn clear(&mut self) {
self.fill(0, self.fb_info.screen_size, 0);
}
pub fn fill_var_screeninfo(&self, var_info: &mut fb_var_screeninfo) {
var_info.xres = self.fb_info.xres;
var_info.yres = self.fb_info.yres;
var_info.xres_virtual = self.fb_info.xres_virtual;
var_info.yres_virtual = self.fb_info.yres_virtual;
var_info.xoffset = self.fb_info.xoffset;
var_info.yoffset = self.fb_info.yoffset;
var_info.bits_per_pixel = self.fb_info.depth as u32;
}
pub fn fill_fix_screeninfo(&self, fix_info: &mut fb_fix_screeninfo) {
fix_info.line_length = self.fb_info.xres * self.fb_info.depth as u32 / 8
}
}
use rcore_console::embedded_graphics::prelude::*;

View File

@ -399,6 +399,21 @@ pub fn virtio_gpu_init(node: &Node) {
setup_framebuffer(&mut driver);
use super::fb;
fb::init(fb::FramebufferInfo {
xres: driver.rect.width,
yres: driver.rect.height,
xres_virtual: driver.rect.width,
yres_virtual: driver.rect.height,
xoffset: 0,
yoffset: 0,
depth: fb::ColorDepth::ColorDepth32,
format: fb::ColorFormat::RGBA8888,
paddr: virt_to_phys(driver.frame_buffer),
vaddr: driver.frame_buffer,
screen_size: (driver.rect.width * driver.rect.height * 4) as usize,
});
let driver = Arc::new(VirtIOGpuDriver(Mutex::new(driver)));
IRQ_MANAGER.write().register_all(driver.clone());
DRIVERS.write().push(driver);

View File

@ -1,6 +1,6 @@
use rcore_fs::vfs::*;
use crate::drivers::gpu::fb::FRAME_BUFFER;
use crate::drivers::gpu::fb::{ColorFormat, FramebufferInfo, FRAME_BUFFER};
use crate::memory::phys_to_virt;
use alloc::{string::String, sync::Arc, vec::Vec};
use core::any::Any;
@ -56,19 +56,21 @@ impl INode for Vga {
})
}
fn io_control(&self, cmd: u32, data: usize) -> Result<()> {
info!("cmd {:#x} , data {:#x} vga not support ioctl !", cmd, data);
const FBIOGET_VSCREENINFO: u32 = 0x4600;
const FBIOGET_FSCREENINFO: u32 = 0x4602;
match cmd {
FBIOGET_FSCREENINFO => {
let fb_fix_info = unsafe { &mut *(data as *mut fb_fix_screeninfo) };
let fb_fix_info = unsafe { &mut *(data as *mut FbFixScreeninfo) };
if let Some(fb) = FRAME_BUFFER.lock().as_ref() {
fb.fill_fix_screeninfo(fb_fix_info);
fb_fix_info.fill_from(&fb.fb_info);
}
Ok(())
}
FBIOGET_VSCREENINFO => {
let fb_var_info = unsafe { &mut *(data as *mut fb_var_screeninfo) };
let fb_var_info = unsafe { &mut *(data as *mut FbVarScreeninfo) };
if let Some(fb) = FRAME_BUFFER.lock().as_ref() {
fb.fill_var_screeninfo(fb_var_info);
fb_var_info.fill_from(&fb.fb_info);
}
Ok(())
}
@ -77,84 +79,218 @@ impl INode for Vga {
Err(FsError::NotSupported)
}
}
//let fb_fix_info = unsafe{ &mut *(data as *mut fb_fix_screeninfo) };
//Ok(())
}
fn as_any_ref(&self) -> &dyn Any {
self
}
}
const FBIOGET_FSCREENINFO: u32 = 0x4602;
const FBIOGET_VSCREENINFO: u32 = 0x4600;
#[repr(u32)]
#[derive(Debug, Copy, Clone)]
enum FbType {
/// Packed Pixels
PackedPixels = 0,
/// Non interleaved planes
Planes = 1,
/// Interleaved planes
InterleavedPlanes = 2,
/// Text/attributes
Text = 3,
/// EGA/VGA planes
VgaPlanes = 4,
/// Type identified by a V4L2 FOURCC
FourCC = 5,
}
#[repr(u32)]
#[derive(Debug, Copy, Clone)]
enum FbVisual {
/// Monochr. 1=Black 0=White
Mono01 = 0,
/// Monochr. 1=White 0=Black
Mono10 = 1,
/// True color
TrueColor = 2,
/// Pseudo color (like atari)
PseudoColor = 3,
/// Direct color
DirectColor = 4,
/// Pseudo color readonly
StaticPseudoColor = 5,
/// Visual identified by a V4L2 FOURCC
FourCC = 6,
}
/// No hardware accelerator
const FB_ACCEL_NONE: u32 = 0;
#[repr(C)]
pub struct fb_fix_screeninfo {
pub id: [u8; 16], /* identification string eg "TT Builtin" */
pub smem_start: u64, /* Start of frame buffer mem */
/* (physical address) */
pub smem_len: u32, /* Length of frame buffer mem */
pub _type: u32, /* see FB_TYPE_* */
pub type_aux: u32, /* Interleave for interleaved Planes */
pub visual: u32, /* see FB_VISUAL_* */
pub xpanstep: u16, /* zero if no hardware panning */
pub ypanstep: u16, /* zero if no hardware panning */
pub ywrapstep: u16, /* zero if no hardware ywrap */
pub line_length: u32, /* length of a line in bytes */
pub mmio_start: u64, /* Start of Memory Mapped I/O */
/* (physical address) */
pub mmio_len: u32, /* Length of Memory Mapped I/O */
pub accel: u32, /* Indicate to driver which */
/* specific chip/card we have */
pub capabilities: u16, /* see FB_CAP_* */
pub reserved: [u16; 2], /* Reserved for future compatibility */
#[derive(Debug)]
struct FbFixScreeninfo {
/// identification string eg "TT Builtin"
id: [u8; 16],
/// Start of frame buffer mem (physical address)
smem_start: u64,
/// Length of frame buffer mem
smem_len: u32,
/// see FB_TYPE_*
type_: FbType,
/// Interleave for interleaved Planes
type_aux: u32,
/// see FB_VISUAL_*
visual: FbVisual,
/// zero if no hardware panning
xpanstep: u16,
/// zero if no hardware panning
ypanstep: u16,
/// zero if no hardware ywrap
ywrapstep: u16,
/// length of a line in bytes
line_length: u32,
/// Start of Memory Mapped I/O (physical address)
mmio_start: u64,
/// Length of Memory Mapped I/O
mmio_len: u32,
/// Indicate to driver which specific chip/card we have
accel: u32,
/// see FB_CAP_*
capabilities: u16,
/// Reserved for future compatibility
reserved: [u16; 2],
}
#[repr(C)]
pub struct fb_var_screeninfo {
pub xres: u32, /* visible resolution */
pub yres: u32,
pub xres_virtual: u32, /* virtual resolution */
pub yres_virtual: u32,
pub xoffset: u32, /* offset from virtual to visible */
pub yoffset: u32, /* resolution */
#[derive(Debug)]
struct FbVarScreeninfo {
/// visible resolution x
xres: u32,
/// visible resolution y
yres: u32,
/// virtual resolution x
xres_virtual: u32,
/// virtual resolution y
yres_virtual: u32,
/// offset from virtual to visible x
xoffset: u32,
/// offset from virtual to visible y
yoffset: u32,
pub bits_per_pixel: u32, /* guess what */
pub grayscale: u32, /* 0 = color, 1 = grayscale, */
/* >1 = FOURCC */
pub red: fb_bitfield, /* bitfield in fb mem if true color, */
pub green: fb_bitfield, /* else only length is significant */
pub blue: fb_bitfield,
pub transp: fb_bitfield, /* transparency */
/// guess what
bits_per_pixel: u32,
/// 0 = color, 1 = grayscale, >1 = FOURCC
grayscale: u32,
/// bitfield in fb mem if true color, else only length is significant
red: FbBitfield,
green: FbBitfield,
blue: FbBitfield,
transp: FbBitfield,
pub nonstd: u32, /* != 0 Non standard pixel format */
/// != 0 Non standard pixel format
nonstd: u32,
pub activate: u32, /* see FB_ACTIVATE_* */
/// see FB_ACTIVATE_*
activate: u32,
pub height: u32, /* height of picture in mm */
pub width: u32, /* width of picture in mm */
pub accel_flags: u32, /* (OBSOLETE) see fb_info.flags */
/// height of picture in mm
height: u32,
/// width of picture in mm
width: u32,
/// (OBSOLETE) see fb_info.flags
accel_flags: u32,
/* Timing: All values in pixclocks, except pixclock (of course) */
pub pixclock: u32, /* pixel clock in ps (pico seconds) */
pub left_margin: u32, /* time from sync to picture */
pub right_margin: u32, /* time from picture to sync */
pub upper_margin: u32, /* time from sync to picture */
pub lower_margin: u32,
pub hsync_len: u32, /* length of horizontal sync */
pub vsync_len: u32, /* length of vertical sync */
pub sync: u32, /* see FB_SYNC_* */
pub vmode: u32, /* see FB_VMODE_* */
pub rotate: u32, /* angle we rotate counter clockwise */
pub colorspace: u32, /* colorspace for FOURCC-based modes */
pub reserved: [u32; 4], /* Reserved for future compatibility */
/// pixel clock in ps (pico seconds)
pixclock: u32,
/// time from sync to picture
left_margin: u32,
/// time from picture to sync
right_margin: u32,
/// time from sync to picture
upper_margin: u32,
lower_margin: u32,
/// length of horizontal sync
hsync_len: u32,
/// length of vertical sync
vsync_len: u32,
/// see FB_SYNC_*
sync: u32,
/// see FB_VMODE_*
vmode: u32,
/// angle we rotate counter clockwise
rotate: u32,
/// colorspace for FOURCC-based modes
colorspace: u32,
/// Reserved for future compatibility
reserved: [u32; 4],
}
#[repr(C)]
pub struct fb_bitfield {
pub offset: u32, /* beginning of bitfield */
pub length: u32, /* length of bitfield */
pub msb_right: u32, /* != 0 : Most significant bit is */
/* right */
#[derive(Debug)]
struct FbBitfield {
/// beginning of bitfield
offset: u32,
/// length of bitfield
length: u32,
/// != 0 : Most significant bit is right
msb_right: u32,
}
impl FbVarScreeninfo {
fn fill_from(&mut self, fb_info: &FramebufferInfo) {
self.xres = fb_info.xres;
self.yres = fb_info.yres;
self.xres_virtual = fb_info.xres_virtual;
self.yres_virtual = fb_info.yres_virtual;
self.xoffset = fb_info.xoffset;
self.yoffset = fb_info.yoffset;
self.bits_per_pixel = fb_info.depth as u32;
let (rl, gl, bl, al, ro, go, bo, ao) = match fb_info.format {
ColorFormat::RGB332 => (3, 3, 2, 0, 5, 3, 0, 0),
ColorFormat::RGB565 => (5, 6, 5, 0, 11, 5, 0, 0),
ColorFormat::RGBA8888 => (8, 8, 8, 8, 16, 8, 0, 24),
ColorFormat::BGRA8888 => (8, 8, 8, 8, 0, 8, 16, 24),
ColorFormat::VgaPalette => unimplemented!(),
};
self.blue = FbBitfield {
offset: bo,
length: bl,
msb_right: 1,
};
self.green = FbBitfield {
offset: go,
length: gl,
msb_right: 1,
};
self.red = FbBitfield {
offset: ro,
length: rl,
msb_right: 1,
};
self.transp = FbBitfield {
offset: ao,
length: al,
msb_right: 1,
};
}
}
impl FbFixScreeninfo {
fn fill_from(&mut self, fb_info: &FramebufferInfo) {
self.smem_start = fb_info.paddr as u64;
self.smem_len = fb_info.screen_size as u32;
self.type_ = FbType::PackedPixels;
// self.type_aux = fb_info.type_aux;
self.visual = FbVisual::TrueColor;
// self.xpanstep = 0;
// self.ypanstep = 0;
// self.ywrapstep = 0;
self.line_length = fb_info.xres * fb_info.depth as u32 / 8;
self.mmio_start = 0;
self.mmio_len = 0;
self.accel = FB_ACCEL_NONE;
}
}

View File

@ -147,6 +147,18 @@ impl Syscall<'_> {
})
}
pub fn sys_pselect6(
&mut self,
nfds: usize,
read: *mut u32,
write: *mut u32,
err: *mut u32,
timeout: *const TimeVal,
_sigset: *const u32,
) -> SysResult {
self.sys_select(nfds, read, write, err, timeout)
}
pub fn sys_select(
&mut self,
nfds: usize,
@ -159,7 +171,9 @@ impl Syscall<'_> {
"select: nfds: {}, read: {:?}, write: {:?}, err: {:?}, timeout: {:?}",
nfds, read, write, err, timeout
);
if nfds as u64 == 0 {
return Ok(0);
}
let proc = self.process();
let mut read_fds = FdSet::new(&self.vm(), read, nfds)?;
let mut write_fds = FdSet::new(&self.vm(), write, nfds)?;

View File

@ -154,6 +154,14 @@ impl Syscall<'_> {
),
// io multiplexing
SYS_PSELECT6 => self.sys_pselect6(
args[0],
args[1] as *mut u32,
args[2] as *mut u32,
args[3] as *mut u32,
args[4] as *const TimeVal,
args[5] as *const u32,
),
SYS_PPOLL => {
self.sys_ppoll(args[0] as *mut PollFd, args[1], args[2] as *const TimeSpec)
} // ignore sigmask