logo.c 2.5 KB

123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102103104
  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. #include <linux/irq.h>
  24. #include <asm/system.h>
  25. #define fb_width(fb) ((fb)->var.xres)
  26. #define fb_height(fb) ((fb)->var.yres)
  27. #define fb_size(fb) ((fb)->var.xres * (fb)->var.yres * 2)
  28. static void memset16(void *_ptr, unsigned short val, unsigned count)
  29. {
  30. unsigned short *ptr = _ptr;
  31. count >>= 1;
  32. while (count--)
  33. *ptr++ = val;
  34. }
  35. /* 565RLE image format: [count(2 bytes), rle(2 bytes)] */
  36. int load_565rle_image(char *filename, bool bf_supported)
  37. {
  38. struct fb_info *info;
  39. int fd, count, err = 0;
  40. unsigned max;
  41. unsigned short *data, *bits, *ptr;
  42. info = registered_fb[0];
  43. if (!info) {
  44. printk(KERN_WARNING "%s: Can not access framebuffer\n",
  45. __func__);
  46. return -ENODEV;
  47. }
  48. fd = sys_open(filename, O_RDONLY, 0);
  49. if (fd < 0) {
  50. printk(KERN_WARNING "%s: Can not open %s\n",
  51. __func__, filename);
  52. return -ENOENT;
  53. }
  54. count = sys_lseek(fd, (off_t)0, 2);
  55. if (count <= 0) {
  56. err = -EIO;
  57. goto err_logo_close_file;
  58. }
  59. sys_lseek(fd, (off_t)0, 0);
  60. data = kmalloc(count, GFP_KERNEL);
  61. if (!data) {
  62. printk(KERN_WARNING "%s: Can not alloc data\n", __func__);
  63. err = -ENOMEM;
  64. goto err_logo_close_file;
  65. }
  66. if (sys_read(fd, (char *)data, count) != count) {
  67. err = -EIO;
  68. goto err_logo_free_data;
  69. }
  70. max = fb_width(info) * fb_height(info);
  71. ptr = data;
  72. if (bf_supported && (info->node == 1 || info->node == 2)) {
  73. err = -EPERM;
  74. pr_err("%s:%d no info->creen_base on fb%d!\n",
  75. __func__, __LINE__, info->node);
  76. goto err_logo_free_data;
  77. }
  78. bits = (unsigned short *)(info->screen_base);
  79. while (count > 3) {
  80. unsigned n = ptr[0];
  81. if (n > max)
  82. break;
  83. memset16(bits, ptr[1], n << 1);
  84. bits += n;
  85. max -= n;
  86. ptr += 2;
  87. count -= 4;
  88. }
  89. err_logo_free_data:
  90. kfree(data);
  91. err_logo_close_file:
  92. sys_close(fd);
  93. return err;
  94. }
  95. EXPORT_SYMBOL(load_565rle_image);