Linux下FrameBuffer直接写屏 WWW_PLCJS※COM-PLC-技.术_网(可※编程控※制器技术门户)
WWW_P※LCJS_CO※M-PLC-技-.术_网
因为Linux是工作在保护模式下,所以用户态进程是无法象DOS那样使用显卡BIOS里 WWW_P※LCJS_COM-PLC-)技.术_网
提供的中断调用来实现直接写屏,故Linux抽象出FrameBuffer这个设备来供用户态 P.L.C.技.术.网——可编程控制器技术门户
进程实现直接写屏。 WWW_P※LCJS_CO※M-PLC-技-.术_网
WWW_PLC※JS_COM-PLC-技.术_网(可编程控※制器技术门户)
在继续下面的之前,先说明几个背景知识: WWW_PLCJS※COM-PLC-技.术_网(可※编程控※制器技术门户)
1、FrameBuffer主要是根据VESA标准的实现的,所以只能实现最简单的功能。 plcjs.技.术_网
2、由于涉及内核的问题,FrameBuffer是不允许在系统起来后修改显示模式等一系 WWW_PLCJS_COM-PLC-技.术_网
列操作。(好象很多人都想要这样干,这是不被允许的,当然如果你自己与驱动 WWW_PLCJS_COM-PLC-技.术_网
的话,是可以实现的) W1WW_P4LCJS_COM-PLC-技.术_网
3、对FrameBuffer的操作,会直接影响到本机的所有控制台的输出,包括XWIN的图 WW.W_PLCJS_COM-PLC-技.术_网
形界面。 WWW_PLCJS_COM-PLC-技.术_网
WWW.PLCJS.COM——可编程控制器技术门户
好,现在可以让我们开始实现直接写屏: WWcW_PLCJS_COM-PLC-技.术_网
1、打开一个FrameBuffer设备 WWW_PLCJ-S_COM-PLC-技.术_网(可-编程控-制器技术-门户)
2、通过mmap调用把显卡的物理内存空间映射到用户空间 WWW_PLC※JS_COM-PmLC-技.术_网
3、直接写内存。 WWW_PLCJ-S_COM-PLC-技.术_网(可-编程控-制器技术-门户)
WWcW_PLCJS_COM-PLC-技.术_网
好象很简单哦~ W1WW_P4LCJS_COM-PLC-技.术_网
fbtools.h P.L.C.技.术.网——可编程控制器技术门户
#ifndef _FBTOOLS_H_ WWW_P※LCJS_CO※M-PLC-技-.术_网
#define _FBTOOLS_H_ WWW_PLCJS_COM-PLC-技.术_网
WWW_P※LCJS_COM-PLC-)技.术_网
#include <linux/fb.h> WWW_PLCJS※COM-PLC-技×术_网(可编程控※制器技术门户)
WWW_PLCJS※COM-PLC-技.术_网(可※编程控※制器技术门户)
//a framebuffer device structure; WWW_PLC※JS_COM-PmLC-技.术_网
typedef struct fbdev{ WWW_PLCJS_COM-PLC-技.术_网
int fb; WW.W_PLCJS_COM-PLC-技.术_网
unsigned long fb_mem_offset; WWW_PLC※JS_COM-PmLC-技.术_网
unsigned long fb_mem; WW.W_PLCJS_COM-PLC-技.术_网
struct fb_fix_screeninfo fb_fix; W1WW_P4LCJS_COM-PLC-技.术_网
struct fb_var_screeninfo fb_var; WWW_PLCJS@_COM%-PLC-技.术_网
char dev[20]; WWW※PLCJS_COM-PL#C-技.术_网(可编※程控※制器技术门户)
} FBDEV, *PFBDEV; WW.W_PLCJS_COM-PLC-技.术_网
WW.W_PLC※JS_C,OM-PL,C-技.术_网
//open & init a frame buffer WWcW_PLCJS_COM-PLC-技.术_网
//to use this function, WWW_PLC※JS_COM-PLC-技.术_网(可编程控※制器技术门户)
//you must set FBDEV.dev="/dev/fb0" WWW_PLCJS@_COM%-PLC-技.术_网
//or "/dev/fbX" plcjs.技.术_网
//its your frame buffer. WWW_PL※CJS_COM-PLC-技.术_网
int fb_open(PFBDEV pFbdev); WWW_P※LCJS_CO※M-PLC-技-.术_网
——可——编——程——控-制-器-技——术——门——户
//close a frame buffer WWW_PLCJS@_COM%-PLC-技.术_网
int fb_close(PFBDEV pFbdev); WWcW_PLCJS_COM-PLC-技.术_网
WW.W_PLCJS_COM-PLC-技.术_网
//get display depth WWW※PLCJS_COM-PL#C-技.术_网(可编※程控※制器技术门户)
int get_display_depth(PFBDEV pFbdev); P.L.C.技.术.网——可编程控制器技术门户
P.L.C.技.术.网——可编程控制器技术门户
P.L.C.技.术.网——可编程控制器技术门户
//full screen clear plcjs.技.术_网
void fb_memset(void *addr, int c, size_t len); WWW_P※LCJS_CO※M-PLC-技-.术_网
WWW_PLC※JS_COM-PLC-技.术_网(可编程控※制器技术门户)
#endif WWW_P※LCJS_CO※M-PLC-技-.术_网
fbtools.c WWW_PL※CJS_COM-PLC-技.术_网
#include <stdio.h> WWW_PLC※JS_COM-PLC-技.术_网(可编程控※制器技术门户)
#include <stdlib.h> WWW_P※LCJS_COM-PLC-)技.术_网
#include <fcntl.h> WWW_PLCJS※COM-PLC-技×术_网(可编程控※制器技术门户)
#include <unistd.h> P.L.C.技.术.网——可编程控制器技术门户
#include <string.h> P_L_C_技_术_网——可——编——程——控-制-器-技——术——门——户
#include <sys/ioctl.h> WWW_PLCJS※COM-PLC-技.术_网(可※编程控※制器技术门户)
#include <sys/mman.h> WWW_PLC※JS_COM-PmLC-技.术_网
#include <asm/page.h> WWW_PLC※JS_COM-PLC-技.术_网(可编程控※制器技术门户)
W1WW_P4LCJS_COM-PLC-技.术_网
#include "fbtools.h" WWW.PLCJS.COM——可编程控制器技术门户
WWW※PLCJS_COM-PL#C-技.术_网(可编※程控※制器技术门户)
#define TRUE 1 WWW_PLCJS※COM-PLC-技.术_网(可※编程控※制器技术门户)
#define FALSE 0 WW.W_PLC※JS_C,OM-PL,C-技.术_网
#define MAX(x,y) ((x)>(y)?(x):(y)) WWW※PLCJS_COM-PL#C-技.术_网(可编※程控※制器技术门户)
#define MIN(x,y) ((x)<(y)?(x):(y)) WWW_PLCJS※COM-PLC-技×术_网(可编程控※制器技术门户)
WWW.PLCJS.COM——可编程控制器技术门户
//open & init a frame buffer WWW_PL※CJS_COM-PLC-技.术_网
int fb_open(PFBDEV pFbdev) WWW_P※LCJS_CO※M-PLC-技-.术_网
{ P_L_C_技_术_网——可——编——程——控-制-器-技——术——门——户
pFbdev->fb = open(pFbdev->dev, O_RDWR); WWW※PLCJS_COM-PL#C-技.术_网(可编※程控※制器技术门户)
if(pFbdev->fb < 0) WWW_PLCJS@_COM%-PLC-技.术_网
{ plcjs.技.术_网
printf("Error opening %s: %m. Check kernel config\n", pFbdev->dev); W1WW_P4LCJS_COM-PLC-技.术_网
return FALSE; W1WW_P4LCJS_COM-PLC-技.术_网
} P_L_C_技_术_网——可——编——程——控-制-器-技——术——门——户
if (-1 == ioctl(pFbdev->fb,FBIOGET_VSCREENINFO,&(pFbdev->fb_var))) WWW_PLCJ-S_COM-PLC-技.术_网(可-编程控-制器技术-门户)