Loading drivers/media/video/vivi.c +135 −30 Original line number Diff line number Diff line Loading @@ -94,6 +94,16 @@ static struct vivi_fmt formats[] = { .fourcc = V4L2_PIX_FMT_UYVY, .depth = 16, }, { .name = "4:2:2, packed, YVYU", .fourcc = V4L2_PIX_FMT_YVYU, .depth = 16, }, { .name = "4:2:2, packed, VYUY", .fourcc = V4L2_PIX_FMT_VYUY, .depth = 16, }, { .name = "RGB565 (LE)", .fourcc = V4L2_PIX_FMT_RGB565, /* gggbbbbb rrrrrggg */ Loading @@ -114,6 +124,26 @@ static struct vivi_fmt formats[] = { .fourcc = V4L2_PIX_FMT_RGB555X, /* arrrrrgg gggbbbbb */ .depth = 16, }, { .name = "RGB24 (LE)", .fourcc = V4L2_PIX_FMT_RGB24, /* rgb */ .depth = 24, }, { .name = "RGB24 (BE)", .fourcc = V4L2_PIX_FMT_BGR24, /* bgr */ .depth = 24, }, { .name = "RGB32 (LE)", .fourcc = V4L2_PIX_FMT_RGB32, /* argb */ .depth = 32, }, { .name = "RGB32 (BE)", .fourcc = V4L2_PIX_FMT_BGR32, /* bgra */ .depth = 32, }, }; static struct vivi_fmt *get_format(struct v4l2_format *f) Loading Loading @@ -205,7 +235,8 @@ struct vivi_dev { unsigned int field_count; u8 bars[9][3]; u8 line[MAX_WIDTH * 4]; u8 line[MAX_WIDTH * 8]; unsigned int pixelsize; }; /* ------------------------------------------------------------------ Loading Loading @@ -284,6 +315,8 @@ static void precalculate_bars(struct vivi_dev *dev) switch (dev->fmt->fourcc) { case V4L2_PIX_FMT_YUYV: case V4L2_PIX_FMT_UYVY: case V4L2_PIX_FMT_YVYU: case V4L2_PIX_FMT_VYUY: is_yuv = 1; break; case V4L2_PIX_FMT_RGB565: Loading @@ -298,6 +331,11 @@ static void precalculate_bars(struct vivi_dev *dev) g >>= 3; b >>= 3; break; case V4L2_PIX_FMT_RGB24: case V4L2_PIX_FMT_BGR24: case V4L2_PIX_FMT_RGB32: case V4L2_PIX_FMT_BGR32: break; } if (is_yuv) { Loading @@ -317,7 +355,8 @@ static void precalculate_bars(struct vivi_dev *dev) #define TSTAMP_INPUT_X 10 #define TSTAMP_MIN_X (54 + TSTAMP_INPUT_X) static void gen_twopix(struct vivi_dev *dev, u8 *buf, int colorpos) /* 'odd' is true for pixels 1, 3, 5, etc. and false for pixels 0, 2, 4, etc. */ static void gen_twopix(struct vivi_dev *dev, u8 *buf, int colorpos, bool odd) { u8 r_y, g_u, b_v; int color; Loading @@ -327,46 +366,56 @@ static void gen_twopix(struct vivi_dev *dev, u8 *buf, int colorpos) g_u = dev->bars[colorpos][1]; /* G or precalculated U */ b_v = dev->bars[colorpos][2]; /* B or precalculated V */ for (color = 0; color < 4; color++) { for (color = 0; color < dev->pixelsize; color++) { p = buf + color; switch (dev->fmt->fourcc) { case V4L2_PIX_FMT_YUYV: switch (color) { case 0: case 2: *p = r_y; break; case 1: *p = g_u; break; case 3: *p = b_v; *p = odd ? b_v : g_u; break; } break; case V4L2_PIX_FMT_UYVY: switch (color) { case 0: *p = odd ? b_v : g_u; break; case 1: case 3: *p = r_y; break; } break; case V4L2_PIX_FMT_YVYU: switch (color) { case 0: *p = r_y; break; case 1: *p = odd ? g_u : b_v; break; } break; case V4L2_PIX_FMT_VYUY: switch (color) { case 0: *p = g_u; *p = odd ? g_u : b_v; break; case 2: *p = b_v; case 1: *p = r_y; break; } break; case V4L2_PIX_FMT_RGB565: switch (color) { case 0: case 2: *p = (g_u << 5) | b_v; break; case 1: case 3: *p = (r_y << 3) | (g_u >> 3); break; } Loading @@ -374,11 +423,9 @@ static void gen_twopix(struct vivi_dev *dev, u8 *buf, int colorpos) case V4L2_PIX_FMT_RGB565X: switch (color) { case 0: case 2: *p = (r_y << 3) | (g_u >> 3); break; case 1: case 3: *p = (g_u << 5) | b_v; break; } Loading @@ -386,11 +433,9 @@ static void gen_twopix(struct vivi_dev *dev, u8 *buf, int colorpos) case V4L2_PIX_FMT_RGB555: switch (color) { case 0: case 2: *p = (g_u << 5) | b_v; break; case 1: case 3: *p = (r_y << 2) | (g_u >> 3); break; } Loading @@ -398,15 +443,71 @@ static void gen_twopix(struct vivi_dev *dev, u8 *buf, int colorpos) case V4L2_PIX_FMT_RGB555X: switch (color) { case 0: case 2: *p = (r_y << 2) | (g_u >> 3); break; case 1: case 3: *p = (g_u << 5) | b_v; break; } break; case V4L2_PIX_FMT_RGB24: switch (color) { case 0: *p = r_y; break; case 1: *p = g_u; break; case 2: *p = b_v; break; } break; case V4L2_PIX_FMT_BGR24: switch (color) { case 0: *p = b_v; break; case 1: *p = g_u; break; case 2: *p = r_y; break; } break; case V4L2_PIX_FMT_RGB32: switch (color) { case 0: *p = 0; break; case 1: *p = r_y; break; case 2: *p = g_u; break; case 3: *p = b_v; break; } break; case V4L2_PIX_FMT_BGR32: switch (color) { case 0: *p = b_v; break; case 1: *p = g_u; break; case 2: *p = r_y; break; case 3: *p = 0; break; } break; } } } Loading @@ -415,10 +516,10 @@ static void precalculate_line(struct vivi_dev *dev) { int w; for (w = 0; w < dev->width * 2; w += 2) { int colorpos = (w / (dev->width / 8) % 8); for (w = 0; w < dev->width * 2; w++) { int colorpos = w / (dev->width / 8) % 8; gen_twopix(dev, dev->line + w * 2, colorpos); gen_twopix(dev, dev->line + w * dev->pixelsize, colorpos, w & 1); } } Loading @@ -434,7 +535,7 @@ static void gen_text(struct vivi_dev *dev, char *basep, /* Print stream time */ for (line = y; line < y + 16; line++) { int j = 0; char *pos = basep + line * dev->width * 2 + x * 2; char *pos = basep + line * dev->width * dev->pixelsize + x * dev->pixelsize; char *s; for (s = text; *s; s++) { Loading @@ -444,9 +545,9 @@ static void gen_text(struct vivi_dev *dev, char *basep, for (i = 0; i < 7; i++, j++) { /* Draw white font on black background */ if (chr & (1 << (7 - i))) gen_twopix(dev, pos + j * 2, WHITE); gen_twopix(dev, pos + j * dev->pixelsize, WHITE, (x+y) & 1); else gen_twopix(dev, pos + j * 2, TEXT_BLACK); gen_twopix(dev, pos + j * dev->pixelsize, TEXT_BLACK, (x+y) & 1); } } } Loading @@ -467,7 +568,9 @@ static void vivi_fillbuff(struct vivi_dev *dev, struct vivi_buffer *buf) return; for (h = 0; h < hmax; h++) memcpy(vbuf + h * wmax * 2, dev->line + (dev->mv_count % wmax) * 2, wmax * 2); memcpy(vbuf + h * wmax * dev->pixelsize, dev->line + (dev->mv_count % wmax) * dev->pixelsize, wmax * dev->pixelsize); /* Updates stream time */ Loading Loading @@ -662,7 +765,7 @@ static int queue_setup(struct vb2_queue *vq, const struct v4l2_format *fmt, struct vivi_dev *dev = vb2_get_drv_priv(vq); unsigned long size; size = dev->width * dev->height * 2; size = dev->width * dev->height * dev->pixelsize; if (0 == *nbuffers) *nbuffers = 32; Loading Loading @@ -726,7 +829,7 @@ static int buffer_prepare(struct vb2_buffer *vb) dev->height < 32 || dev->height > MAX_HEIGHT) return -EINVAL; size = dev->width * dev->height * 2; size = dev->width * dev->height * dev->pixelsize; if (vb2_plane_size(vb, 0) < size) { dprintk(dev, 1, "%s data will not fit into plane (%lu < %lu)\n", __func__, vb2_plane_size(vb, 0), size); Loading Loading @@ -920,6 +1023,7 @@ static int vidioc_s_fmt_vid_cap(struct file *file, void *priv, } dev->fmt = get_format(f); dev->pixelsize = dev->fmt->depth / 8; dev->width = f->fmt.pix.width; dev->height = f->fmt.pix.height; dev->field = f->fmt.pix.field; Loading Loading @@ -1266,6 +1370,7 @@ static int __init vivi_create_instance(int inst) dev->fmt = &formats[0]; dev->width = 640; dev->height = 480; dev->pixelsize = dev->fmt->depth / 8; hdl = &dev->ctrl_handler; v4l2_ctrl_handler_init(hdl, 11); dev->volume = v4l2_ctrl_new_std(hdl, &vivi_ctrl_ops, Loading Loading
drivers/media/video/vivi.c +135 −30 Original line number Diff line number Diff line Loading @@ -94,6 +94,16 @@ static struct vivi_fmt formats[] = { .fourcc = V4L2_PIX_FMT_UYVY, .depth = 16, }, { .name = "4:2:2, packed, YVYU", .fourcc = V4L2_PIX_FMT_YVYU, .depth = 16, }, { .name = "4:2:2, packed, VYUY", .fourcc = V4L2_PIX_FMT_VYUY, .depth = 16, }, { .name = "RGB565 (LE)", .fourcc = V4L2_PIX_FMT_RGB565, /* gggbbbbb rrrrrggg */ Loading @@ -114,6 +124,26 @@ static struct vivi_fmt formats[] = { .fourcc = V4L2_PIX_FMT_RGB555X, /* arrrrrgg gggbbbbb */ .depth = 16, }, { .name = "RGB24 (LE)", .fourcc = V4L2_PIX_FMT_RGB24, /* rgb */ .depth = 24, }, { .name = "RGB24 (BE)", .fourcc = V4L2_PIX_FMT_BGR24, /* bgr */ .depth = 24, }, { .name = "RGB32 (LE)", .fourcc = V4L2_PIX_FMT_RGB32, /* argb */ .depth = 32, }, { .name = "RGB32 (BE)", .fourcc = V4L2_PIX_FMT_BGR32, /* bgra */ .depth = 32, }, }; static struct vivi_fmt *get_format(struct v4l2_format *f) Loading Loading @@ -205,7 +235,8 @@ struct vivi_dev { unsigned int field_count; u8 bars[9][3]; u8 line[MAX_WIDTH * 4]; u8 line[MAX_WIDTH * 8]; unsigned int pixelsize; }; /* ------------------------------------------------------------------ Loading Loading @@ -284,6 +315,8 @@ static void precalculate_bars(struct vivi_dev *dev) switch (dev->fmt->fourcc) { case V4L2_PIX_FMT_YUYV: case V4L2_PIX_FMT_UYVY: case V4L2_PIX_FMT_YVYU: case V4L2_PIX_FMT_VYUY: is_yuv = 1; break; case V4L2_PIX_FMT_RGB565: Loading @@ -298,6 +331,11 @@ static void precalculate_bars(struct vivi_dev *dev) g >>= 3; b >>= 3; break; case V4L2_PIX_FMT_RGB24: case V4L2_PIX_FMT_BGR24: case V4L2_PIX_FMT_RGB32: case V4L2_PIX_FMT_BGR32: break; } if (is_yuv) { Loading @@ -317,7 +355,8 @@ static void precalculate_bars(struct vivi_dev *dev) #define TSTAMP_INPUT_X 10 #define TSTAMP_MIN_X (54 + TSTAMP_INPUT_X) static void gen_twopix(struct vivi_dev *dev, u8 *buf, int colorpos) /* 'odd' is true for pixels 1, 3, 5, etc. and false for pixels 0, 2, 4, etc. */ static void gen_twopix(struct vivi_dev *dev, u8 *buf, int colorpos, bool odd) { u8 r_y, g_u, b_v; int color; Loading @@ -327,46 +366,56 @@ static void gen_twopix(struct vivi_dev *dev, u8 *buf, int colorpos) g_u = dev->bars[colorpos][1]; /* G or precalculated U */ b_v = dev->bars[colorpos][2]; /* B or precalculated V */ for (color = 0; color < 4; color++) { for (color = 0; color < dev->pixelsize; color++) { p = buf + color; switch (dev->fmt->fourcc) { case V4L2_PIX_FMT_YUYV: switch (color) { case 0: case 2: *p = r_y; break; case 1: *p = g_u; break; case 3: *p = b_v; *p = odd ? b_v : g_u; break; } break; case V4L2_PIX_FMT_UYVY: switch (color) { case 0: *p = odd ? b_v : g_u; break; case 1: case 3: *p = r_y; break; } break; case V4L2_PIX_FMT_YVYU: switch (color) { case 0: *p = r_y; break; case 1: *p = odd ? g_u : b_v; break; } break; case V4L2_PIX_FMT_VYUY: switch (color) { case 0: *p = g_u; *p = odd ? g_u : b_v; break; case 2: *p = b_v; case 1: *p = r_y; break; } break; case V4L2_PIX_FMT_RGB565: switch (color) { case 0: case 2: *p = (g_u << 5) | b_v; break; case 1: case 3: *p = (r_y << 3) | (g_u >> 3); break; } Loading @@ -374,11 +423,9 @@ static void gen_twopix(struct vivi_dev *dev, u8 *buf, int colorpos) case V4L2_PIX_FMT_RGB565X: switch (color) { case 0: case 2: *p = (r_y << 3) | (g_u >> 3); break; case 1: case 3: *p = (g_u << 5) | b_v; break; } Loading @@ -386,11 +433,9 @@ static void gen_twopix(struct vivi_dev *dev, u8 *buf, int colorpos) case V4L2_PIX_FMT_RGB555: switch (color) { case 0: case 2: *p = (g_u << 5) | b_v; break; case 1: case 3: *p = (r_y << 2) | (g_u >> 3); break; } Loading @@ -398,15 +443,71 @@ static void gen_twopix(struct vivi_dev *dev, u8 *buf, int colorpos) case V4L2_PIX_FMT_RGB555X: switch (color) { case 0: case 2: *p = (r_y << 2) | (g_u >> 3); break; case 1: case 3: *p = (g_u << 5) | b_v; break; } break; case V4L2_PIX_FMT_RGB24: switch (color) { case 0: *p = r_y; break; case 1: *p = g_u; break; case 2: *p = b_v; break; } break; case V4L2_PIX_FMT_BGR24: switch (color) { case 0: *p = b_v; break; case 1: *p = g_u; break; case 2: *p = r_y; break; } break; case V4L2_PIX_FMT_RGB32: switch (color) { case 0: *p = 0; break; case 1: *p = r_y; break; case 2: *p = g_u; break; case 3: *p = b_v; break; } break; case V4L2_PIX_FMT_BGR32: switch (color) { case 0: *p = b_v; break; case 1: *p = g_u; break; case 2: *p = r_y; break; case 3: *p = 0; break; } break; } } } Loading @@ -415,10 +516,10 @@ static void precalculate_line(struct vivi_dev *dev) { int w; for (w = 0; w < dev->width * 2; w += 2) { int colorpos = (w / (dev->width / 8) % 8); for (w = 0; w < dev->width * 2; w++) { int colorpos = w / (dev->width / 8) % 8; gen_twopix(dev, dev->line + w * 2, colorpos); gen_twopix(dev, dev->line + w * dev->pixelsize, colorpos, w & 1); } } Loading @@ -434,7 +535,7 @@ static void gen_text(struct vivi_dev *dev, char *basep, /* Print stream time */ for (line = y; line < y + 16; line++) { int j = 0; char *pos = basep + line * dev->width * 2 + x * 2; char *pos = basep + line * dev->width * dev->pixelsize + x * dev->pixelsize; char *s; for (s = text; *s; s++) { Loading @@ -444,9 +545,9 @@ static void gen_text(struct vivi_dev *dev, char *basep, for (i = 0; i < 7; i++, j++) { /* Draw white font on black background */ if (chr & (1 << (7 - i))) gen_twopix(dev, pos + j * 2, WHITE); gen_twopix(dev, pos + j * dev->pixelsize, WHITE, (x+y) & 1); else gen_twopix(dev, pos + j * 2, TEXT_BLACK); gen_twopix(dev, pos + j * dev->pixelsize, TEXT_BLACK, (x+y) & 1); } } } Loading @@ -467,7 +568,9 @@ static void vivi_fillbuff(struct vivi_dev *dev, struct vivi_buffer *buf) return; for (h = 0; h < hmax; h++) memcpy(vbuf + h * wmax * 2, dev->line + (dev->mv_count % wmax) * 2, wmax * 2); memcpy(vbuf + h * wmax * dev->pixelsize, dev->line + (dev->mv_count % wmax) * dev->pixelsize, wmax * dev->pixelsize); /* Updates stream time */ Loading Loading @@ -662,7 +765,7 @@ static int queue_setup(struct vb2_queue *vq, const struct v4l2_format *fmt, struct vivi_dev *dev = vb2_get_drv_priv(vq); unsigned long size; size = dev->width * dev->height * 2; size = dev->width * dev->height * dev->pixelsize; if (0 == *nbuffers) *nbuffers = 32; Loading Loading @@ -726,7 +829,7 @@ static int buffer_prepare(struct vb2_buffer *vb) dev->height < 32 || dev->height > MAX_HEIGHT) return -EINVAL; size = dev->width * dev->height * 2; size = dev->width * dev->height * dev->pixelsize; if (vb2_plane_size(vb, 0) < size) { dprintk(dev, 1, "%s data will not fit into plane (%lu < %lu)\n", __func__, vb2_plane_size(vb, 0), size); Loading Loading @@ -920,6 +1023,7 @@ static int vidioc_s_fmt_vid_cap(struct file *file, void *priv, } dev->fmt = get_format(f); dev->pixelsize = dev->fmt->depth / 8; dev->width = f->fmt.pix.width; dev->height = f->fmt.pix.height; dev->field = f->fmt.pix.field; Loading Loading @@ -1266,6 +1370,7 @@ static int __init vivi_create_instance(int inst) dev->fmt = &formats[0]; dev->width = 640; dev->height = 480; dev->pixelsize = dev->fmt->depth / 8; hdl = &dev->ctrl_handler; v4l2_ctrl_handler_init(hdl, 11); dev->volume = v4l2_ctrl_new_std(hdl, &vivi_ctrl_ops, Loading