linux/drivers/staging/msm/logo.c
<<
>>
Prefs
   1/* drivers/video/msm/logo.c
   2 *
   3 * Show Logo in RLE 565 format
   4 *
   5 * Copyright (C) 2008 Google Incorporated
   6 *
   7 * This software is licensed under the terms of the GNU General Public
   8 * License version 2, as published by the Free Software Foundation, and
   9 * may be copied, distributed, and modified under those terms.
  10 *
  11 * This program is distributed in the hope that it will be useful,
  12 * but WITHOUT ANY WARRANTY; without even the implied warranty of
  13 * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
  14 * GNU General Public License for more details.
  15 *
  16 */
  17#include <linux/module.h>
  18#include <linux/types.h>
  19#include <linux/fb.h>
  20#include <linux/vt_kern.h>
  21#include <linux/unistd.h>
  22#include <linux/syscalls.h>
  23
  24#include <linux/irq.h>
  25#include <asm/system.h>
  26
  27#define fb_width(fb)    ((fb)->var.xres)
  28#define fb_height(fb)   ((fb)->var.yres)
  29#define fb_size(fb)     ((fb)->var.xres * (fb)->var.yres * 2)
  30
  31static void memset16(void *_ptr, unsigned short val, unsigned count)
  32{
  33        unsigned short *ptr = _ptr;
  34        count >>= 1;
  35        while (count--)
  36                *ptr++ = val;
  37}
  38
  39/* 565RLE image format: [count(2 bytes), rle(2 bytes)] */
  40int load_565rle_image(char *filename)
  41{
  42        struct fb_info *info;
  43        int fd, err = 0;
  44        unsigned count, max;
  45        unsigned short *data, *bits, *ptr;
  46
  47        info = registered_fb[0];
  48        if (!info) {
  49                printk(KERN_WARNING "%s: Can not access framebuffer\n",
  50                        __func__);
  51                return -ENODEV;
  52        }
  53
  54        fd = sys_open(filename, O_RDONLY, 0);
  55        if (fd < 0) {
  56                printk(KERN_WARNING "%s: Can not open %s\n",
  57                        __func__, filename);
  58                return -ENOENT;
  59        }
  60        count = (unsigned)sys_lseek(fd, (off_t)0, 2);
  61        if (count == 0) {
  62                sys_close(fd);
  63                err = -EIO;
  64                goto err_logo_close_file;
  65        }
  66        sys_lseek(fd, (off_t)0, 0);
  67        data = kmalloc(count, GFP_KERNEL);
  68        if (!data) {
  69                printk(KERN_WARNING "%s: Can not alloc data\n", __func__);
  70                err = -ENOMEM;
  71                goto err_logo_close_file;
  72        }
  73        if ((unsigned)sys_read(fd, (char *)data, count) != count) {
  74                err = -EIO;
  75                goto err_logo_free_data;
  76        }
  77
  78        max = fb_width(info) * fb_height(info);
  79        ptr = data;
  80        bits = (unsigned short *)(info->screen_base);
  81        while (count > 3) {
  82                unsigned n = ptr[0];
  83                if (n > max)
  84                        break;
  85                memset16(bits, ptr[1], n << 1);
  86                bits += n;
  87                max -= n;
  88                ptr += 2;
  89                count -= 4;
  90        }
  91
  92err_logo_free_data:
  93        kfree(data);
  94err_logo_close_file:
  95        sys_close(fd);
  96        return err;
  97}
  98EXPORT_SYMBOL(load_565rle_image);
  99