The website "dmilvdv.narod.ru." is not registered with uCoz.
If you are absolutely sure your website must be here,
please contact our Support Team.
If you were searching for something on the Internet and ended up here, try again:

About uCoz web-service

Community

Legal information

Распечатка 9.3 Обычный драйвер кадрового буфера

Распечатка 9.3 Обычный драйвер кадрового буфера

Предыдущая  Содержание  Следующая V*D*V

Распечатка 9.3

 

/* sfb.c */

 

#include <linux/module.h>

#include <linux/kernel.h>

#include <linux/errno.h>

#include <linux/string.h>

#include <linux/mm.h>

#include <linux/tty.h>

#include <linux/slab.h>

#include <linux/vmalloc.h>

#include <linux/delay.h>

#include <linux/interrupt.h>

#include <asm/uaccess.h>

#include <linux/fb.h>

#include <linux/init.h>

 

static char *videomemory = VIDEOMEMSTART;

static u_long videomemorysize = VIDEOMEMSIZE;

static struct fb_info fb_info;

 

/* Устанавливаем начальную информацию экрана */

static struct fb_var_screeninfo sfb_default __initdata = {

    .xres            = SFB_MAX_X,

    .yres            = SFB_MAX_Y,

    .xres_virtual    = SFB_MAX_X,

    .yres_virtual    = SFB_MAX_Y,

    .bits_per_pixel  = 8,

    .red             = { 0, 8, 0 },

    .green           = { 0, 8, 0 },

    .blue            = { 0, 8, 0 },

    .activate        = FB_ACTIVATE_TEST,

    .height          = -1,

    .width           = -1,

    .left_margin     = 0,

    .right_margin    = 0,

    .upper_margin    = 0,

    .lower_margin    = 0,

    .vmode           = FB_VMODE_NONINTERLACED,

};

static struct fb_fix_screeninfo sfb_fix __initdata = {

    .id        = "SimpleFB",

    .type      = FB_TYPE_PACKED_PIXELS,

    .visual    = FB_VISUAL_PSEUDOCOLOR,

    .xpanstep  = 1,

    .ypanstep  = 1,

    .ywrapstep = 1,

    .accel     = FB_ACCEL_NONE,

};

 

/* Прототипы функций */

int sfb_init(void);

int sfb_setup(char *);

static int sfb_check_var(struct fb_var_screeninfo *var,

                         struct fb_info *info);

static int sfb_set_par(struct fb_info *info);

static int sfb_setcolreg(u_int regno, u_int red, u_int green,

                         u_int blue, u_int transp,

                         struct fb_info *info);

static int sfb_pan_display(struct fb_var_screeninfo *var,

                           struct fb_info *info);

static int sfb_mmap(struct fb_info *info, struct file *file,

                    struct vm_area_struct *vma);

 

/*

 * Определяем структуру fb_ops, которая регистрируется в ядре.

 * Замечание: процедуры cfb_xxx - это универсальные процедуры,

 * реализованные в ядре. Можно их переопределить в случае, если

 * ваше оборудование предоставляет функции ускорения графики

 */

static struct fb_ops sfb_ops = {

    .fb_check_var = sfb_check_var,

    .fb_set_par   = sfb_set_par,

    .fb_setcolreg = sfb_setcolreg,

    .fb_fillrect  = cfb_fillrect,

    .fb_copyarea  = cfb_copyarea,

    .fb_imageblit = cfb_imageblit,

};

 

/*

 * Вспомните обсуждение о line_length в разделе о графическом

 * оборудовании. Длина строки выражается в байтах, обозначая

 * число байтов в каждой строке.

 */

static u_long get_line_length(int xres_virtual, int bpp)

{

    u_long line_length;

    line_length = xres_virtual * bpp;

    line_length = (line_length + 31) & ~31;

    line_length >>= 3;

    return (line_length);

}

 

/*

 * xxxfb_check_var, не пишет что-то в оборудование, а только

 * проверяет пригодность, базируясь на данных оборудования

 */

static int sfb_check_var(struct fb_var_screeninfo *var,

                         struct fb_info *info)

{

    u_long line_length;

    /* Проверяем достоверность разрешения экрана */

    if (!var->xres)

        var->xres = SFB_MIN_XRES;

    if (!var->yres)

        var->yres = SFB_MIN_YRES;

    if (var->xres > var->xres_virtual)

        var->xres_virtual = var->xres;

    if (var->yres > var->yres_virtual)

        var->yres_virtual = var->yres;

    if (sfb_check_bpp(var)) return –EINVAL;

    if (var->xres_virtual < var->xoffset + var->xres)

        var->xres_virtual = var->xoffset + var->xres;

    if (var->yres_virtual < var->yoffset + var->yres)

        var->yres_virtual = var->yoffset + var->yres;

 

    /*

     * Убедимся, что карта имеет достаточно видеопамяти в этом режиме

     * Вызываем формулу

     * Память к/б = Ширина Дисплея * Высота Дисплея * Байтов На Пиксель

     */

    line_length = get_line_length(var->xres_virtual,

                            var->bits_per_pixel);

    if (line_length * var->yres_virtual > videomemorysize)

        return -ENOMEM;

    sfb_fixup_var_modes(var);

    return 0;

}

 

/*

 * Эта процедура реально устанавливает видеорежим. Все проверки уже

 * были сделаны

 */

static int sfb_set_par(struct fb_info *info)

{

    sfb_program_hardware(info);

    info->fix.line_length = get_line_length(

                    info->var.xres_virtual,

                    info->var.bits_per_pixel);

    return 0;

}

 

/*

 * Устанавливаем один регистр цвета. Полученные значения уже

 * подогнаны к возможностям оборудования (соответствуют записям

 * в структуре var). Возвращаем != 0 для неверного regno.

 */

static int sfb_setcolreg(u_int regno, u_int red, u_int green,

                         u_int blue, u_int transp,

                         struct fb_info *info)

{

unsigned int *palette = SFB_PALETTE_START;

 

    if (regno >= SFB_MAX_PALLETE_REG) //номера аппаратных регистров

        return 1;

    unsigned int v = (red << info->var.red.offset) |

                    (green << info->var.green.offset) |

                    (blue << info->var.blue.offset) |

                    (transp << info->var.transp.offset);

 

    /* Программируем оборудование */

    *(palette+regno) = v;

    return 0;

}

 

/* Точка входа в драйвер */

int __init sfb_init(void)

{

    /* Заполняем структуру fb_info */

    fb_info.screen_base = io_remap(videomemory, vidememory);

    fb_info.fbops = &sfb_ops;

    fb_info.var = sfb_default;

    fb_info.fix = sfb_fix;

    fb_info.flags = FBINFO_FLAG_DEFAULT;

 

    fb_alloc_cmap(&fb_info.cmap, 256, 0);

 

    /* Регистрируем драйвер */

    if (register_framebuffer(&fb_info) < 0) {

        return -EINVAL;

    }

 

    printk(KERN_INFO "fb%d: Sample frame buffer device

                    initialized \n", fb_info.node);

 

    return 0;

}

 

static void __exit sfb_cleanup(void)

{

    unregister_framebuffer(&fb_info);

}

 

module_init(sfb_init);

module_exit(sfb_cleanup);

MODULE_LICENSE("GPL");

 

Предыдущая  Содержание  Следующая