9 #include <linux/kernel.h>
10 #include <linux/module.h>
11 #include <linux/device.h>
12 #include <linux/list.h>
13 #include <linux/pci.h>
17 #include <linux/videodev2.h>
38 static bool flip_image;
41 "If set, the sensor will be instructed to flip the image "
44 static bool override_serial;
47 "The camera driver will normally refuse to load if "
48 "the XO 1.5 serial port is enabled. Set this option "
49 "to force-enable the camera.");
55 #define VGA_HEIGHT 480
56 #define QCIF_WIDTH 176
57 #define QCIF_HEIGHT 144
122 #define CF_DMA_ACTIVE 0
123 #define CF_CONFIG_NEEDED 1
129 #define sensor_call(cam, optype, func, args...) \
130 v4l2_subdev_call(cam->sensor, optype, func, ##args)
135 #define cam_err(cam, fmt, arg...) \
136 dev_err(&(cam)->platdev->dev, fmt, ##arg);
137 #define cam_warn(cam, fmt, arg...) \
138 dev_warn(&(cam)->platdev->dev, fmt, ##arg);
139 #define cam_dbg(cam, fmt, arg...) \
140 dev_dbg(&(cam)->platdev->dev, fmt, ##arg);
148 static struct via_format {
155 .desc =
"YUYV 4:2:2",
165 #define N_VIA_FMTS ARRAY_SIZE(via_formats)
172 if (via_formats[i].pixelformat == pixelformat)
173 return via_formats +
i;
213 static void via_sensor_power_up(
struct via_camera *cam)
222 static void via_sensor_power_down(
struct via_camera *cam)
229 static void via_sensor_power_release(
struct via_camera *cam)
231 via_sensor_power_down(cam);
242 static int viacam_set_flip(
struct via_camera *cam)
248 ctrl.value = flip_image;
256 static int viacam_configure_sensor(
struct via_camera *cam)
258 struct v4l2_mbus_framefmt mbus_fmt;
264 ret =
sensor_call(cam, video, s_mbus_fmt, &mbus_fmt);
269 ret = viacam_set_flip(cam);
283 static inline void viacam_write_reg(
struct via_camera *cam,
289 static inline int viacam_read_reg(
struct via_camera *cam,
int reg)
294 static inline void viacam_write_reg_mask(
struct via_camera *cam,
297 int tmp = viacam_read_reg(cam, reg);
299 tmp = (tmp & ~mask) | (value & mask);
300 viacam_write_reg(cam, reg, tmp);
317 spin_lock(&cam->
viadev->reg_lock);
324 spin_unlock(&cam->
viadev->reg_lock);
342 if (!waitqueue_active(&buf->
done)) {
349 spin_unlock_irqrestore(&cam->
viadev->reg_lock, flags);
367 vb = viacam_next_buffer(cam);
397 static void viacam_int_enable(
struct via_camera *cam)
404 static void viacam_int_disable(
struct via_camera *cam)
418 static int viacam_ctlr_cbufs(
struct via_camera *cam)
431 }
else if (nbuf == 2) {
435 cam_warn(cam,
"Insufficient frame buffer memory\n");
468 static void viacam_set_scale(
struct via_camera *cam)
470 unsigned int avscale;
490 static void viacam_ctlr_image(
struct via_camera *cam)
505 viacam_set_scale(cam);
541 static int viacam_config_controller(
struct via_camera *cam)
547 ret = viacam_ctlr_cbufs(cam);
549 viacam_ctlr_image(cam);
550 spin_unlock_irqrestore(&cam->
viadev->reg_lock, flags);
558 static void viacam_start_engine(
struct via_camera *cam)
560 spin_lock_irq(&cam->
viadev->reg_lock);
563 viacam_int_enable(cam);
566 spin_unlock_irq(&cam->
viadev->reg_lock);
570 static void viacam_stop_engine(
struct via_camera *cam)
572 spin_lock_irq(&cam->
viadev->reg_lock);
573 viacam_int_disable(cam);
577 spin_unlock_irq(&cam->
viadev->reg_lock);
595 if (*count == 0 || *count > 6)
653 .buf_setup = viacam_vb_buf_setup,
654 .buf_prepare = viacam_vb_buf_prepare,
655 .buf_queue = viacam_vb_buf_queue,
656 .buf_release = viacam_vb_buf_release,
662 static int viacam_open(
struct file *filp)
672 if (cam->
users == 0) {
673 int ret = viafb_request_dma();
679 via_sensor_power_up(cam);
694 static int viacam_release(
struct file *filp)
704 if (filp == cam->
owner) {
713 viacam_stop_engine(cam);
719 if (cam->
users == 0) {
721 via_sensor_power_down(cam);
732 size_t len, loff_t *
pos)
750 ret = viacam_configure_sensor(cam);
752 ret = viacam_config_controller(cam);
762 viacam_start_engine(cam);
765 viacam_stop_engine(cam);
794 .release = viacam_release,
806 static int viacam_g_chip_ident(
struct file *
file,
void *
priv,
823 static int viacam_queryctrl(
struct file *filp,
void *priv,
836 static int viacam_g_ctrl(
struct file *filp,
void *priv,
849 static int viacam_s_ctrl(
struct file *filp,
void *priv,
864 static int viacam_enum_input(
struct file *filp,
void *priv,
867 if (input->
index != 0)
876 static int viacam_g_input(
struct file *filp,
void *priv,
unsigned int *i)
882 static int viacam_s_input(
struct file *filp,
void *priv,
unsigned int i)
889 static int viacam_s_std(
struct file *filp,
void *priv,
v4l2_std_id *
std)
909 static int viacam_enum_fmt_vid_cap(
struct file *filp,
void *priv,
927 *sensorfmt = *userfmt;
943 struct via_format *
f = via_find_format(userfmt->
pixelformat);
957 static int viacam_do_try_fmt(
struct via_camera *cam,
961 struct v4l2_mbus_framefmt mbus_fmt;
962 struct via_format *
f = via_find_format(upix->
pixelformat);
965 viacam_fmt_pre(upix, spix);
966 v4l2_fill_mbus_format(&mbus_fmt, spix, f->mbus_code);
967 ret =
sensor_call(cam, video, try_mbus_fmt, &mbus_fmt);
968 v4l2_fill_pix_format(spix, &mbus_fmt);
969 viacam_fmt_post(upix, spix);
975 static int viacam_try_fmt_vid_cap(
struct file *filp,
void *priv,
983 ret = viacam_do_try_fmt(cam, &fmt->
fmt.
pix, &sfmt.fmt.pix);
989 static int viacam_g_fmt_vid_cap(
struct file *filp,
void *priv,
1000 static int viacam_s_fmt_vid_cap(
struct file *filp,
void *priv,
1006 struct via_format *
f = via_find_format(fmt->
fmt.
pix.pixelformat);
1021 ret = viacam_do_try_fmt(cam, &fmt->
fmt.
pix, &sfmt.fmt.pix);
1030 ret = viacam_configure_sensor(cam);
1032 ret = viacam_config_controller(cam);
1038 static int viacam_querycap(
struct file *filp,
void *priv,
1052 static int viacam_reqbufs(
struct file *filp,
void *priv,
1060 static int viacam_querybuf(
struct file *filp,
void *priv,
1068 static int viacam_qbuf(
struct file *filp,
void *priv,
struct v4l2_buffer *buf)
1075 static int viacam_dqbuf(
struct file *filp,
void *priv,
struct v4l2_buffer *buf)
1082 static int viacam_streamon(
struct file *filp,
void *priv,
enum v4l2_buf_type t)
1107 ret = viacam_configure_sensor(cam);
1110 ret = viacam_config_controller(cam);
1127 viacam_start_engine(cam);
1133 static int viacam_streamoff(
struct file *filp,
void *priv,
enum v4l2_buf_type t)
1146 viacam_stop_engine(cam);
1161 static int viacam_g_parm(
struct file *filp,
void *priv,
1174 static int viacam_s_parm(
struct file *filp,
void *priv,
1187 static int viacam_enum_framesizes(
struct file *filp,
void *priv,
1190 if (sizes->
index != 0)
1201 static int viacam_enum_frameintervals(
struct file *filp,
void *priv,
1208 ret =
sensor_call(cam, video, enum_frameintervals, interval);
1216 .vidioc_g_chip_ident = viacam_g_chip_ident,
1217 .vidioc_queryctrl = viacam_queryctrl,
1218 .vidioc_g_ctrl = viacam_g_ctrl,
1219 .vidioc_s_ctrl = viacam_s_ctrl,
1220 .vidioc_enum_input = viacam_enum_input,
1221 .vidioc_g_input = viacam_g_input,
1222 .vidioc_s_input = viacam_s_input,
1223 .vidioc_s_std = viacam_s_std,
1224 .vidioc_enum_fmt_vid_cap = viacam_enum_fmt_vid_cap,
1225 .vidioc_try_fmt_vid_cap = viacam_try_fmt_vid_cap,
1226 .vidioc_g_fmt_vid_cap = viacam_g_fmt_vid_cap,
1227 .vidioc_s_fmt_vid_cap = viacam_s_fmt_vid_cap,
1228 .vidioc_querycap = viacam_querycap,
1229 .vidioc_reqbufs = viacam_reqbufs,
1230 .vidioc_querybuf = viacam_querybuf,
1231 .vidioc_qbuf = viacam_qbuf,
1232 .vidioc_dqbuf = viacam_dqbuf,
1233 .vidioc_streamon = viacam_streamon,
1234 .vidioc_streamoff = viacam_streamoff,
1235 .vidioc_g_parm = viacam_g_parm,
1236 .vidioc_s_parm = viacam_s_parm,
1237 .vidioc_enum_framesizes = viacam_enum_framesizes,
1238 .vidioc_enum_frameintervals = viacam_enum_frameintervals,
1248 static int viacam_suspend(
void *priv)
1254 viacam_stop_engine(cam);
1261 static int viacam_resume(
void *priv)
1269 via_write_reg_mask(
VIASR, 0x78, 0, 0x80);
1270 via_write_reg_mask(
VIASR, 0x1e, 0xc0, 0xc0);
1271 viacam_int_disable(cam);
1277 via_sensor_power_up(cam);
1279 via_sensor_power_down(cam);
1285 ret = viacam_configure_sensor(cam);
1287 ret = viacam_config_controller(cam);
1290 viacam_start_engine(cam);
1296 static struct viafb_pm_hooks viacam_pm_hooks = {
1297 .suspend = viacam_suspend,
1298 .resume = viacam_resume
1308 .name =
"via-camera",
1312 .fops = &viacam_fops,
1313 .ioctl_ops = &viacam_ioctl_ops,
1323 #define VIACAM_SERIAL_DEVFN 0x88
1324 #define VIACAM_SERIAL_CREG 0x46
1325 #define VIACAM_SERIAL_BIT 0x40
1327 static __devinit bool viacam_serial_is_enabled(
void)
1338 if (override_serial == 0) {
1340 "refusing to load.\n");
1342 "module loading.\n");
1364 .platform_data = &sensor_cfg,
1392 if (machine_is_olpc() && viacam_serial_is_enabled())
1412 cam->
fb_offset = viadev->camera_fbmem_offset;
1420 dev_err(&pdev->
dev,
"Unable to register v4l2 device\n");
1426 pdev->
dev.dma_mask = &viadev->
pdev->dma_mask;
1432 via_write_reg_mask(
VIASR, 0x78, 0, 0x80);
1433 via_write_reg_mask(
VIASR, 0x1e, 0xc0, 0xc0);
1437 ret = via_sensor_power_setup(cam);
1439 goto out_unregister;
1440 via_sensor_power_up(cam);
1448 &ov7670_info,
NULL);
1450 dev_err(&pdev->
dev,
"Unable to find the sensor!\n");
1452 goto out_power_down;
1457 viacam_int_disable(cam);
1461 goto out_power_down;
1465 cam->
vdev = viacam_v4l_template;
1470 video_set_drvdata(&cam->
vdev, cam);
1476 viacam_pm_hooks.private = cam;
1477 viafb_pm_register(&viacam_pm_hooks);
1481 via_sensor_power_down(cam);
1487 via_sensor_power_release(cam);
1501 via_sensor_power_release(cam);
1502 via_cam_info =
NULL;
1508 .name =
"viafb-camera",
1510 .probe = viacam_probe,
1511 .remove = viacam_remove,