soc_mediabus.c 4.8 KB

123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102103104105106107108109110111112113114115116117118119120121122123124125126127128129130131132133134135136137138139140141142143144145146147148149150151152153154155156157158159160161162163164165166167168169170171172173174175176177178179180181182183184185186187
  1. /*
  2. * soc-camera media bus helper routines
  3. *
  4. * Copyright (C) 2009, Guennadi Liakhovetski <g.liakhovetski@gmx.de>
  5. *
  6. * This program is free software; you can redistribute it and/or modify
  7. * it under the terms of the GNU General Public License version 2 as
  8. * published by the Free Software Foundation.
  9. */
  10. #include <linux/kernel.h>
  11. #include <linux/module.h>
  12. #include <media/v4l2-device.h>
  13. #include <media/v4l2-mediabus.h>
  14. #include <media/soc_mediabus.h>
  15. #define MBUS_IDX(f) (V4L2_MBUS_FMT_ ## f - V4L2_MBUS_FMT_FIXED - 1)
  16. static const struct soc_mbus_pixelfmt mbus_fmt[] = {
  17. [MBUS_IDX(YUYV8_2X8)] = {
  18. .fourcc = V4L2_PIX_FMT_YUYV,
  19. .name = "YUYV",
  20. .bits_per_sample = 8,
  21. .packing = SOC_MBUS_PACKING_2X8_PADHI,
  22. .order = SOC_MBUS_ORDER_LE,
  23. },
  24. [MBUS_IDX(YVYU8_2X8)] = {
  25. .fourcc = V4L2_PIX_FMT_YVYU,
  26. .name = "YVYU",
  27. .bits_per_sample = 8,
  28. .packing = SOC_MBUS_PACKING_2X8_PADHI,
  29. .order = SOC_MBUS_ORDER_LE,
  30. },
  31. [MBUS_IDX(UYVY8_2X8)] = {
  32. .fourcc = V4L2_PIX_FMT_UYVY,
  33. .name = "UYVY",
  34. .bits_per_sample = 8,
  35. .packing = SOC_MBUS_PACKING_2X8_PADHI,
  36. .order = SOC_MBUS_ORDER_LE,
  37. },
  38. [MBUS_IDX(VYUY8_2X8)] = {
  39. .fourcc = V4L2_PIX_FMT_VYUY,
  40. .name = "VYUY",
  41. .bits_per_sample = 8,
  42. .packing = SOC_MBUS_PACKING_2X8_PADHI,
  43. .order = SOC_MBUS_ORDER_LE,
  44. },
  45. [MBUS_IDX(RGB555_2X8_PADHI_LE)] = {
  46. .fourcc = V4L2_PIX_FMT_RGB555,
  47. .name = "RGB555",
  48. .bits_per_sample = 8,
  49. .packing = SOC_MBUS_PACKING_2X8_PADHI,
  50. .order = SOC_MBUS_ORDER_LE,
  51. },
  52. [MBUS_IDX(RGB555_2X8_PADHI_BE)] = {
  53. .fourcc = V4L2_PIX_FMT_RGB555X,
  54. .name = "RGB555X",
  55. .bits_per_sample = 8,
  56. .packing = SOC_MBUS_PACKING_2X8_PADHI,
  57. .order = SOC_MBUS_ORDER_LE,
  58. },
  59. [MBUS_IDX(RGB565_2X8_LE)] = {
  60. .fourcc = V4L2_PIX_FMT_RGB565,
  61. .name = "RGB565",
  62. .bits_per_sample = 8,
  63. .packing = SOC_MBUS_PACKING_2X8_PADHI,
  64. .order = SOC_MBUS_ORDER_LE,
  65. },
  66. [MBUS_IDX(RGB565_2X8_BE)] = {
  67. .fourcc = V4L2_PIX_FMT_RGB565X,
  68. .name = "RGB565X",
  69. .bits_per_sample = 8,
  70. .packing = SOC_MBUS_PACKING_2X8_PADHI,
  71. .order = SOC_MBUS_ORDER_LE,
  72. },
  73. [MBUS_IDX(SBGGR8_1X8)] = {
  74. .fourcc = V4L2_PIX_FMT_SBGGR8,
  75. .name = "Bayer 8 BGGR",
  76. .bits_per_sample = 8,
  77. .packing = SOC_MBUS_PACKING_NONE,
  78. .order = SOC_MBUS_ORDER_LE,
  79. },
  80. [MBUS_IDX(SBGGR10_1X10)] = {
  81. .fourcc = V4L2_PIX_FMT_SBGGR10,
  82. .name = "Bayer 10 BGGR",
  83. .bits_per_sample = 10,
  84. .packing = SOC_MBUS_PACKING_EXTEND16,
  85. .order = SOC_MBUS_ORDER_LE,
  86. },
  87. [MBUS_IDX(Y8_1X8)] = {
  88. .fourcc = V4L2_PIX_FMT_GREY,
  89. .name = "Grey",
  90. .bits_per_sample = 8,
  91. .packing = SOC_MBUS_PACKING_NONE,
  92. .order = SOC_MBUS_ORDER_LE,
  93. },
  94. [MBUS_IDX(Y10_1X10)] = {
  95. .fourcc = V4L2_PIX_FMT_Y10,
  96. .name = "Grey 10bit",
  97. .bits_per_sample = 10,
  98. .packing = SOC_MBUS_PACKING_EXTEND16,
  99. .order = SOC_MBUS_ORDER_LE,
  100. },
  101. [MBUS_IDX(SBGGR10_2X8_PADHI_LE)] = {
  102. .fourcc = V4L2_PIX_FMT_SBGGR10,
  103. .name = "Bayer 10 BGGR",
  104. .bits_per_sample = 8,
  105. .packing = SOC_MBUS_PACKING_2X8_PADHI,
  106. .order = SOC_MBUS_ORDER_LE,
  107. },
  108. [MBUS_IDX(SBGGR10_2X8_PADLO_LE)] = {
  109. .fourcc = V4L2_PIX_FMT_SBGGR10,
  110. .name = "Bayer 10 BGGR",
  111. .bits_per_sample = 8,
  112. .packing = SOC_MBUS_PACKING_2X8_PADLO,
  113. .order = SOC_MBUS_ORDER_LE,
  114. },
  115. [MBUS_IDX(SBGGR10_2X8_PADHI_BE)] = {
  116. .fourcc = V4L2_PIX_FMT_SBGGR10,
  117. .name = "Bayer 10 BGGR",
  118. .bits_per_sample = 8,
  119. .packing = SOC_MBUS_PACKING_2X8_PADHI,
  120. .order = SOC_MBUS_ORDER_BE,
  121. },
  122. [MBUS_IDX(SBGGR10_2X8_PADLO_BE)] = {
  123. .fourcc = V4L2_PIX_FMT_SBGGR10,
  124. .name = "Bayer 10 BGGR",
  125. .bits_per_sample = 8,
  126. .packing = SOC_MBUS_PACKING_2X8_PADLO,
  127. .order = SOC_MBUS_ORDER_BE,
  128. },
  129. };
  130. int soc_mbus_samples_per_pixel(const struct soc_mbus_pixelfmt *mf)
  131. {
  132. switch (mf->packing) {
  133. case SOC_MBUS_PACKING_NONE:
  134. case SOC_MBUS_PACKING_EXTEND16:
  135. return 1;
  136. case SOC_MBUS_PACKING_2X8_PADHI:
  137. case SOC_MBUS_PACKING_2X8_PADLO:
  138. return 2;
  139. }
  140. return -EINVAL;
  141. }
  142. EXPORT_SYMBOL(soc_mbus_samples_per_pixel);
  143. s32 soc_mbus_bytes_per_line(u32 width, const struct soc_mbus_pixelfmt *mf)
  144. {
  145. switch (mf->packing) {
  146. case SOC_MBUS_PACKING_NONE:
  147. return width * mf->bits_per_sample / 8;
  148. case SOC_MBUS_PACKING_2X8_PADHI:
  149. case SOC_MBUS_PACKING_2X8_PADLO:
  150. case SOC_MBUS_PACKING_EXTEND16:
  151. return width * 2;
  152. }
  153. return -EINVAL;
  154. }
  155. EXPORT_SYMBOL(soc_mbus_bytes_per_line);
  156. const struct soc_mbus_pixelfmt *soc_mbus_get_fmtdesc(
  157. enum v4l2_mbus_pixelcode code)
  158. {
  159. if (code - V4L2_MBUS_FMT_FIXED > ARRAY_SIZE(mbus_fmt) ||
  160. code <= V4L2_MBUS_FMT_FIXED)
  161. return NULL;
  162. return mbus_fmt + code - V4L2_MBUS_FMT_FIXED - 1;
  163. }
  164. EXPORT_SYMBOL(soc_mbus_get_fmtdesc);
  165. static int __init soc_mbus_init(void)
  166. {
  167. return 0;
  168. }
  169. static void __exit soc_mbus_exit(void)
  170. {
  171. }
  172. module_init(soc_mbus_init);
  173. module_exit(soc_mbus_exit);
  174. MODULE_DESCRIPTION("soc-camera media bus interface");
  175. MODULE_AUTHOR("Guennadi Liakhovetski <g.liakhovetski@gmx.de>");
  176. MODULE_LICENSE("GPL v2");