diff options
author | Peng Du <pengdu@marvell.com> | 2015-06-26 15:13:31 +0800 |
---|---|---|
committer | Qing Zhu <qzhu@marvell.com> | 2015-07-08 21:14:28 +0800 |
commit | 9101d5852c0f74ae9bf4aaa5103053861696c23e (patch) | |
tree | ea2576998ef12493508080f70f72dab90f552b33 | |
parent | a5771884872face8cca9f4c1ecffb68e29dfa15d (diff) | |
download | pxa-v3.14-9101d5852c0f74ae9bf4aaa5103053861696c23e.tar.gz |
media: i2c: ecs: add sp2529 drivers
Change-Id: Id1baab405b0c90051137a8b347e21a1327dcab02
Signed-off-by: Peng Du <pengdu@marvell.com>
-rw-r--r-- | drivers/media/i2c/ecs/Kconfig | 6 | ||||
-rw-r--r-- | drivers/media/i2c/ecs/Makefile | 1 | ||||
-rw-r--r-- | drivers/media/i2c/ecs/sp2529.c | 44 | ||||
-rw-r--r-- | drivers/media/i2c/ecs/sp2529.h | 1161 |
4 files changed, 1212 insertions, 0 deletions
diff --git a/drivers/media/i2c/ecs/Kconfig b/drivers/media/i2c/ecs/Kconfig index ae8d3ff4a35..0dddb7b2909 100644 --- a/drivers/media/i2c/ecs/Kconfig +++ b/drivers/media/i2c/ecs/Kconfig @@ -28,3 +28,9 @@ config SOC_CAMERA_SP0A20_ECS default y help Support for the sp0a20 0.3M camera sensor. +config SOC_CAMERA_SP2529_ECS + tristate "sp2529 support based on ECS" + depends on ECS_DRIVER_SUBDEV + default y + help + Support for the sp2529 2M camera sensor. diff --git a/drivers/media/i2c/ecs/Makefile b/drivers/media/i2c/ecs/Makefile index ab2394b4b2b..fe6d5d92143 100644 --- a/drivers/media/i2c/ecs/Makefile +++ b/drivers/media/i2c/ecs/Makefile @@ -2,3 +2,4 @@ obj-$(CONFIG_ECS_DRIVER) += ecs-core.o obj-$(CONFIG_ECS_DRIVER_SUBDEV) += ecs-subdev.o ecs-helper.o obj-$(CONFIG_SOC_CAMERA_OV5640_ECS) += ov5640.o obj-$(CONFIG_SOC_CAMERA_SP0A20_ECS) += sp0a20.o +obj-$(CONFIG_SOC_CAMERA_SP2529_ECS) += sp2529.o diff --git a/drivers/media/i2c/ecs/sp2529.c b/drivers/media/i2c/ecs/sp2529.c new file mode 100644 index 00000000000..49d693e7c84 --- /dev/null +++ b/drivers/media/i2c/ecs/sp2529.c @@ -0,0 +1,44 @@ +/* + * SP2529 sensor driver. + * + * Copyright (C) 2013 Marvell Internation Ltd. + * Copyright (C) 2013 GalaxyCore Ltd. + * + * This program is free software; you can redistribute it and/or modify + * it under the terms of the GNU General Public License version 2 as + * published by the Free Software Foundation. + */ + +#include <linux/init.h> +#include <linux/module.h> +#include "sp2529.h" + +char *sp2529_get_profile(const struct i2c_client *client) +{ + return "pxa-mipi"; +} + +static int sp2529_g_frame_interval(struct v4l2_subdev *sd, + struct v4l2_subdev_frame_interval *inter) +{ + inter->interval.numerator = 24; + inter->interval.denominator = 1; + + return 0; +} + +static int __init sp2529_mod_init(void) +{ + return xsd_add_driver(sp2529_drv_table); +} + +static void __exit sp2529_mod_exit(void) +{ + xsd_del_driver(sp2529_drv_table); +} + +module_init(sp2529_mod_init); +module_exit(sp2529_mod_exit); + +MODULE_LICENSE("GPL"); +MODULE_DESCRIPTION("sp2529 Camera Driver"); diff --git a/drivers/media/i2c/ecs/sp2529.h b/drivers/media/i2c/ecs/sp2529.h new file mode 100644 index 00000000000..c1d827855e0 --- /dev/null +++ b/drivers/media/i2c/ecs/sp2529.h @@ -0,0 +1,1161 @@ +/*sp_HK 2015-03-24 +//v1.1 +//\D0\C4֡\C2\CA */ + +#ifndef SP2529_H_ +#define SP2529_H_ + +#include <linux/types.h> +#include <media/v4l2-common.h> +#include <media/soc_camera.h> +#include <linux/platform_data/camera-mmp.h> +#include "ecs-subdev.h" + +#define SP2529_TERM 0xff + +char *sp2529_get_profile(const struct i2c_client *client); +static int sp2529_g_frame_interval(struct v4l2_subdev *sd, + struct v4l2_subdev_frame_interval *inter); +/********************************Register lists********************************/ + + +static struct reg_tab_bb sp2529_init_req[] = { +}; + +static struct reg_tab_bb sp2529_init_done[] = { + {0xfd, 0x01}, + {0x36, 0x00}, + {0xfd, 0x00}, + {0xac, 0x03}, + {0xa2, 0x19}, + {0xfd, 0x00}, + {0x31, 0x00}, + {0x33, 0x00}, + {0x95, 0x06}, + {0x94, 0x40}, + {0x97, 0x04}, + {0x96, 0xb0}, + {0x98, 0x3a}, + {0xfd, 0x00}, + {0x0c, 0x55}, + {0x27, 0xa5}, + {0x1a, 0x4b}, + {0x20, 0x2f}, + {0x22, 0x5a}, + {0x25, 0xbd}, + {0x21, 0x0d}, + {0x28, 0x08}, + {0x1d, 0x01}, + {0x7a, 0x5d}, + {0x70, 0x41}, + {0x74, 0x40}, + {0x75, 0x40}, + {0x15, 0x3e}, + {0x71, 0x3f}, + {0x7c, 0x3f}, + {0x76, 0x3f}, + {0x7e, 0x29}, + {0x72, 0x29}, + {0x77, 0x28}, + {0x1e, 0x01}, + {0x1c, 0x0f}, + {0x2e, 0xc0}, + {0x1f, 0xc0}, + {0x6c, 0x00}, + {0xfd, 0x01}, + {0x32, 0x00}, + {0xfd, 0x02}, + {0x85, 0x00}, + {0xfd, 0x00}, + {0x2f, 0x04}, + {0xfd, 0x00}, + {0x03, 0x02}, + {0x04, 0xe8}, + {0x05, 0x00}, + {0x06, 0x00}, + {0x07, 0x00}, + {0x08, 0x00}, + {0x09, 0x00}, + {0x0a, 0x7e}, + {0xfd, 0x01}, + {0xf0, 0x00}, + {0xf7, 0x7c}, + {0xf8, 0x67}, + {0x02, 0x0a}, + {0x03, 0x01}, + {0x06, 0x7c}, + {0x07, 0x00}, + {0x08, 0x01}, + {0x09, 0x00}, + {0xfd, 0x02}, + {0x3d, 0x0c}, + {0x3e, 0x67}, + {0x3f, 0x00}, + {0x88, 0x21}, + {0x89, 0xf8}, + {0x8a, 0x44}, + {0xfd, 0x02}, + {0xbe, 0xd8}, + {0xbf, 0x04}, + {0xd0, 0xd8}, + {0xd1, 0x04}, + {0xc9, 0xd8}, + {0xca, 0x04}, + {0xb8, 0x90}, + {0xb9, 0x85}, + {0xba, 0x30}, + {0xbb, 0x45}, + {0xbc, 0xc0}, + {0xbd, 0x60}, + {0xfd, 0x03}, + {0x77, 0x48}, + {0xfd, 0x01}, + {0xe0, 0x48}, + {0xe1, 0x38}, + {0xe2, 0x30}, + {0xe3, 0x2c}, + {0xe4, 0x2c}, + {0xe5, 0x2a}, + {0xe6, 0x2a}, + {0xe7, 0x28}, + {0xe8, 0x28}, + {0xe9, 0x28}, + {0xea, 0x26}, + {0xf3, 0x26}, + {0xf4, 0x26}, + {0xfd, 0x01}, + {0x04, 0xb0}, + {0x05, 0x26}, + {0x0a, 0x48}, + {0x0b, 0x26}, + {0xfd, 0x01}, + {0xf2, 0x09}, + {0xeb, 0x80}, + {0xec, 0x6c}, + {0xed, 0x06}, + {0xee, 0x0a}, + {0xfd, 0x03}, + {0x52, 0xff}, + {0x53, 0x60}, + {0x94, 0x00}, + {0x54, 0x00}, + {0x55, 0x00}, + {0x56, 0x80}, + {0x57, 0x80}, + {0x95, 0x00}, + {0x58, 0x00}, + {0x59, 0x00}, + {0x5a, 0xf6}, + {0x5b, 0x00}, + {0x5c, 0x88}, + {0x5d, 0x00}, + {0x96, 0x00}, + {0xfd, 0x03}, + {0x8a, 0x00}, + {0x8b, 0x00}, + {0x8c, 0xff}, + {0x22, 0xff}, + {0x23, 0xff}, + {0x24, 0xff}, + {0x25, 0xff}, + {0x5e, 0xff}, + {0x5f, 0xff}, + {0x60, 0xff}, + {0x61, 0xff}, + {0x62, 0x00}, + {0x63, 0x00}, + {0x64, 0x00}, + {0x65, 0x00}, + {0xfd, 0x01}, + {0x21, 0x00}, + {0x22, 0x00}, + {0x26, 0x60}, + {0x27, 0x14}, + {0x28, 0x05}, + {0x29, 0x00}, + {0x2a, 0x01}, + {0xfd, 0x01}, + {0xa1, 0x24}, + {0xa2, 0x23}, + {0xa3, 0x22}, + {0xa4, 0x24}, + {0xa5, 0x20}, + {0xa6, 0x1d}, + {0xa7, 0x1c}, + {0xa8, 0x1e}, + {0xa9, 0x1a}, + {0xaa, 0x1b}, + {0xab, 0x18}, + {0xac, 0x19}, + {0xad, 0x01}, + {0xae, 0x03}, + {0xaf, 0x01}, + {0xb0, 0x03}, + {0xb1, 0x03}, + {0xb2, 0x03}, + {0xb3, 0x03}, + {0xb4, 0x03}, + {0xb5, 0x05}, + {0xb6, 0x03}, + {0xb7, 0x05}, + {0xb8, 0x05}, + {0xfd, 0x02}, + {0x10, 0x00}, + {0x11, 0x00}, + {0x26, 0xa0}, + {0x27, 0x96}, + {0x28, 0xcc}, + {0x29, 0x01}, + {0x2a, 0x00}, + {0x2b, 0x00}, + {0x2c, 0x20}, + {0x2d, 0xdc}, + {0x2e, 0x20}, + {0x2f, 0x96}, + {0x1b, 0x80}, + {0x1a, 0x80}, + {0x18, 0x16}, + {0x19, 0x26}, + {0x1d, 0x04}, + {0x1f, 0x06}, + {0x66, 0x31}, + {0x67, 0x51}, + {0x68, 0xce}, + {0x69, 0xe5}, + {0x6a, 0xa5}, + {0x7c, 0x26}, + {0x7d, 0x4a}, + {0x7e, 0xe5}, + {0x7f, 0x05}, + {0x80, 0xa6}, + {0x70, 0x1f}, + {0x71, 0x3c}, + {0x72, 0x15}, + {0x73, 0x34}, + {0x74, 0xaa}, + {0x6b, 0x03}, + {0x6c, 0x1f}, + {0x6d, 0x16}, + {0x6e, 0x3d}, + {0x6f, 0xaa}, + {0x61, 0xcc}, + {0x62, 0xec}, + {0x63, 0x44}, + {0x64, 0x64}, + {0x65, 0x6a}, + {0x75, 0x00}, + {0x76, 0x09}, + {0x77, 0x02}, + {0x0e, 0x16}, + {0x3b, 0x09}, + {0xfd, 0x02}, + {0x02, 0x00}, + {0x03, 0x10}, + {0x04, 0xf0}, + {0xf5, 0xb3}, + {0xf6, 0x80}, + {0xf7, 0xe0}, + {0xf8, 0x89}, + {0xfd, 0x02}, + {0x08, 0x00}, + {0x09, 0x04}, + {0xfd, 0x02}, + {0x57, 0x30}, + {0x58, 0x10}, + {0x59, 0xe0}, + {0x5a, 0x00}, + {0x5b, 0x12}, + {0xcb, 0x0e}, + {0xcc, 0x10}, + {0xcd, 0x16}, + {0xce, 0x1c}, + {0xfd, 0x03}, + {0x87, 0x04}, + {0x88, 0x08}, + {0x89, 0x10}, + {0xfd, 0x02}, + {0xe8, 0x48}, + {0xec, 0x58}, + {0xe9, 0x48}, + {0xed, 0x58}, + {0xea, 0x40}, + {0xee, 0x50}, + {0xeb, 0x30}, + {0xef, 0x40}, + {0xfd, 0x02}, + {0xdc, 0x04}, + {0x05, 0x6f}, + {0xfd, 0x02}, + {0xf4, 0x30}, + {0xfd, 0x03}, + {0x97, 0x98}, + {0x98, 0x88}, + {0x99, 0x80}, + {0x9a, 0x78}, + {0xfd, 0x02}, + {0xe4, 0xff}, + {0xe5, 0xff}, + {0xe6, 0xff}, + {0xe7, 0xff}, + {0xfd, 0x03}, + {0x72, 0x18}, + {0x73, 0x28}, + {0x74, 0x28}, + {0x75, 0x38}, + {0xfd, 0x02}, + {0x78, 0x20}, + {0x79, 0x20}, + {0x7a, 0x14}, + {0x7b, 0x08}, + {0x81, 0x40}, + {0x82, 0x40}, + {0x83, 0x50}, + {0x84, 0x50}, + {0xfd, 0x03}, + {0x7e, 0x0c}, + {0x7f, 0x11}, + {0x80, 0x15}, + {0x81, 0x1a}, + {0x7c, 0xff}, + {0x82, 0x54}, + {0x83, 0x43}, + {0x84, 0x00}, + {0x85, 0x20}, + {0x86, 0x40}, + {0xfd, 0x03}, + {0x66, 0x18}, + {0x67, 0x28}, + {0x68, 0x20}, + {0x69, 0x88}, + {0x9b, 0x18}, + {0x9c, 0x28}, + {0x9d, 0x20}, + {0xfd, 0x01}, + {0x8b, 0x00}, + {0x8c, 0x0f}, + {0x8d, 0x21}, + {0x8e, 0x2c}, + {0x8f, 0x37}, + {0x90, 0x46}, + {0x91, 0x53}, + {0x92, 0x5e}, + {0x93, 0x6a}, + {0x94, 0x7d}, + {0x95, 0x8d}, + {0x96, 0x9e}, + {0x97, 0xac}, + {0x98, 0xba}, + {0x99, 0xc6}, + {0x9a, 0xd1}, + {0x9b, 0xda}, + {0x9c, 0xe4}, + {0x9d, 0xeb}, + {0x9e, 0xf2}, + {0x9f, 0xf9}, + {0xa0, 0xff}, + {0xfd, 0x02}, + {0x15, 0xaa}, + {0x16, 0x80}, + {0xa0, 0x99}, + {0xa1, 0xf4}, + {0xa2, 0xf4}, + {0xa3, 0xf6}, + {0xa4, 0xa6}, + {0xa5, 0xe4}, + {0xa6, 0xf6}, + {0xa7, 0xd5}, + {0xa8, 0xb5}, + {0xa9, 0x3c}, + {0xaa, 0x33}, + {0xab, 0x0f}, + {0xac, 0x90}, + {0xad, 0xde}, + {0xae, 0x12}, + {0xaf, 0xf2}, + {0xb0, 0xb3}, + {0xb1, 0xdc}, + {0xb2, 0xe4}, + {0xb3, 0x60}, + {0xb4, 0x3c}, + {0xb5, 0x0c}, + {0xb6, 0x33}, + {0xb7, 0x1f}, + {0xfd, 0x01}, + {0xd2, 0x2d}, + {0xd1, 0x38}, + {0xdd, 0x3b}, + {0xde, 0x37}, + + {0xfd, 0x02}, + {0xc1, 0x40}, + {0xc2, 0x40}, + {0xc3, 0x40}, + {0xc4, 0x40}, + {0xc5, 0x80}, + {0xc6, 0x60}, + {0xc7, 0x00}, + {0xc8, 0x00}, + {0xfd, 0x01}, + {0xd3, 0x80}, + {0xd4, 0x80}, + {0xd5, 0x70}, + {0xd6, 0x58}, + {0xd7, 0x80}, + {0xd8, 0x80}, + {0xd9, 0x70}, + {0xda, 0x58}, + {0xfd, 0x03}, + {0x76, 0x10}, + {0x7a, 0x40}, + {0x7b, 0x40}, + {0xfd, 0x01}, + {0xc2, 0xaa}, + {0xc3, 0xaa}, + {0xc4, 0x66}, + {0xc5, 0x66}, + {0xfd, 0x01}, + {0xcd, 0x08}, + {0xce, 0x18}, + {0xfd, 0x02}, + {0x32, 0x60}, + {0x35, 0x60}, + {0x37, 0x13}, + {0xfd, 0x01}, + {0xdb, 0x00}, + {0x10, 0x80}, + {0x11, 0x80}, + {0x12, 0x90}, + {0x13, 0x90}, + {0x14, 0xb0}, + {0x15, 0xa0}, + {0x16, 0x90}, + {0x17, 0x88}, + {0xfd, 0x03}, + {0x00, 0x80}, + {0x03, 0x68}, + {0x06, 0xd8}, + {0x07, 0x28}, + {0x0a, 0xfd}, + {0x01, 0x16}, + {0x02, 0x16}, + {0x04, 0x16}, + {0x05, 0x16}, + {0x0b, 0x40}, + {0x0c, 0x40}, + {0x0d, 0x40}, + {0x0e, 0x40}, + {0x08, 0x0c}, + {0x09, 0x0c}, + {0xfd, 0x02}, + {0x8e, 0x0a}, + {0x90, 0x40}, + {0x91, 0x40}, + {0x92, 0x60}, + {0x93, 0x80}, + {0x9e, 0x44}, + {0x9f, 0x44}, + {0xfd, 0x02}, + {0x85, 0x00}, + {0xfd, 0x01}, + {0x00, 0x00}, + {0xfb, 0x25}, + {0x32, 0x15}, + {0x33, 0xef}, + {0x34, 0xef}, + {0x35, 0x00}, + {0xfd, 0x00}, + {0x3f, 0x03}, + {0xfd, 0x01}, + {0x50, 0x00}, + {0x66, 0x00}, + {0xfd, 0x02}, + {0xd6, 0x0f}, + {SP2529_TERM, 0}, +}; + +static struct reg_tab_bb sp2529_stm_on[] = { + {0xfd, 0x00}, + {0x92, 0x81}, + {0xfd, 0x00}, + {SP2529_TERM, 0}, +}; + +static struct reg_tab_bb sp2529_stm_off[] = { + {0xfd, 0x00}, + {0x92, 0x00}, + {0xfd, 0x00}, + {SP2529_TERM, 0}, +}; + +static struct reg_tab_bb sp2529_fmt_yuyv[] = { + {SP2529_TERM, 0}, +}; + +static struct reg_tab_bb sp2529_fmt_yvyu[] = { + {SP2529_TERM, 0}, +}; + +static struct reg_tab_bb sp2529_fmt_uyvy[] = { + {SP2529_TERM, 0}, +}; + +static struct reg_tab_bb sp2529_fmt_vyuy[] = { + {SP2529_TERM, 0}, +}; + + +static struct reg_tab_bb sp2529_res_qcif[] = { + {0xfd, 0x00}, + {0x19, 0x00}, + {0x30, 0x0c}, + {0x31, 0x00}, + {0x33, 0x00}, + {0xfd, 0x02}, + {0x40, 0x01}, + {0x41, 0x0a}, + {0x42, 0x01}, + {0x43, 0x22}, + {0x44, 0x00}, + {0x45, 0x90}, + {0x46, 0x00}, + {0x47, 0xb0}, + {0x0f, 0x01}, + {0x8f, 0x02}, + {0xfd, 0x00}, + {0xfd, 0x00}, + {0x95, 0x00}, + {0x94, 0xb0}, + {0x97, 0x00}, + {0x96, 0x90}, + {0xfd, 0x00}, + {0x03, 0x02}, + {0x04, 0xe8}, + {0x05, 0x00}, + {0x06, 0x00}, + {0x07, 0x00}, + {0x08, 0x00}, + {0x09, 0x00}, + {0x0a, 0x7e}, + {0xfd, 0x01}, + {0xf0, 0x00}, + {0xf7, 0x7c}, + {0xf8, 0x67}, + {0x02, 0x0a}, + {0x03, 0x01}, + {0x06, 0x7c}, + {0x07, 0x00}, + {0x08, 0x01}, + {0x09, 0x00}, + {0xfd, 0x02}, + {0x3d, 0x0c}, + {0x3e, 0x67}, + {0x3f, 0x00}, + {0x88, 0x21}, + {0x89, 0xf8}, + {0x8a, 0x44}, + {0xfd, 0x02}, + {0xbe, 0xd8}, + {0xbf, 0x04}, + {0xd0, 0xd8}, + {0xd1, 0x04}, + {0xc9, 0xd8}, + {0xca, 0x04}, + {SP2529_TERM, 0}, +}; + +static struct reg_tab_bb sp2529_res_qvga[] = { + {0xfd, 0x00}, + {0x19, 0x00}, + {0x30, 0x0c}, + {0x31, 0x00}, + {0x33, 0x00}, + {0xfd, 0x02}, + {0x40, 0x00}, + {0x41, 0xa0}, + {0x42, 0x00}, + {0x43, 0xa0}, + {0x44, 0x00}, + {0x45, 0xf0}, + {0x46, 0x01}, + {0x47, 0x40}, + {0x0f, 0x01}, + {0x8f, 0x02}, + {0xfd, 0x00}, + {0xfd, 0x00}, + {0x95, 0x01}, + {0x94, 0x40}, + {0x97, 0x00}, + {0x96, 0xf0}, + {0xfd, 0x00}, + {0x03, 0x02}, + {0x04, 0xe8}, + {0x05, 0x00}, + {0x06, 0x00}, + {0x07, 0x00}, + {0x08, 0x00}, + {0x09, 0x00}, + {0x0a, 0x7e}, + {0xfd, 0x01}, + {0xf0, 0x00}, + {0xf7, 0x7c}, + {0xf8, 0x67}, + {0x02, 0x0a}, + {0x03, 0x01}, + {0x06, 0x7c}, + {0x07, 0x00}, + {0x08, 0x01}, + {0x09, 0x00}, + {0xfd, 0x02}, + {0x3d, 0x0c}, + {0x3e, 0x67}, + {0x3f, 0x00}, + {0x88, 0x21}, + {0x89, 0xf8}, + {0x8a, 0x44}, + {0xfd, 0x02}, + {0xbe, 0xd8}, + {0xbf, 0x04}, + {0xd0, 0xd8}, + {0xd1, 0x04}, + {0xc9, 0xd8}, + {0xca, 0x04}, + {SP2529_TERM, 0}, +}; + +static struct reg_tab_bb sp2529_res_vga[] = { + {0xfd, 0x00}, + {0x19, 0x00}, + {0x30, 0x0c}, + {0x31, 0x00}, + {0x33, 0x00}, + {0xfd, 0x02}, + {0x40, 0x00}, + {0x41, 0x50}, + {0x42, 0x00}, + {0x43, 0x50}, + {0x44, 0x01}, + {0x45, 0xe0}, + {0x46, 0x02}, + {0x47, 0x80}, + {0x0f, 0x01}, + {0x8f, 0x02}, + {0xfd, 0x00}, + {0xfd, 0x00}, + {0x95, 0x02}, + {0x94, 0x80}, + {0x97, 0x01}, + {0x96, 0xe0}, + {0xfd, 0x00}, + {0x03, 0x02}, + {0x04, 0xe8}, + {0x05, 0x00}, + {0x06, 0x00}, + {0x07, 0x00}, + {0x08, 0x00}, + {0x09, 0x00}, + {0x0a, 0x7e}, + {0xfd, 0x01}, + {0xf0, 0x00}, + {0xf7, 0x7c}, + {0xf8, 0x67}, + {0x02, 0x0a}, + {0x03, 0x01}, + {0x06, 0x7c}, + {0x07, 0x00}, + {0x08, 0x01}, + {0x09, 0x00}, + {0xfd, 0x02}, + {0x3d, 0x0c}, + {0x3e, 0x67}, + {0x3f, 0x00}, + {0x88, 0x21}, + {0x89, 0xf8}, + {0x8a, 0x44}, + {0xfd, 0x02}, + {0xbe, 0xd8}, + {0xbf, 0x04}, + {0xd0, 0xd8}, + {0xd1, 0x04}, + {0xc9, 0xd8}, + {0xca, 0x04}, + {SP2529_TERM, 0}, +}; +static struct reg_tab_bb sp2529_res_binning[] = { + {0xfd, 0x00}, + {0x19, 0x03}, + {0x30, 0x0c}, + {0x31, 0x04}, + {0x33, 0x01}, + {0xfd, 0x00}, + {0x95, 0x03}, + {0x94, 0x20}, + {0x97, 0x02}, + {0x96, 0x58}, + {0xfd, 0x02}, + {0x0f, 0x00}, + {0xfd, 0x00}, + {0x03, 0x02}, + {0x04, 0xe8}, + {0x05, 0x00}, + {0x06, 0x00}, + {0x07, 0x00}, + {0x08, 0x00}, + {0x09, 0x06}, + {0x0a, 0x2c}, + {0xfd, 0x01}, + {0xf0, 0x00}, + {0xf7, 0x7c}, + {0xf8, 0x67}, + {0x02, 0x0a}, + {0x03, 0x01}, + {0x06, 0x7c}, + {0x07, 0x00}, + {0x08, 0x01}, + {0x09, 0x00}, + {0xfd, 0x02}, + {0x3d, 0x0c}, + {0x3e, 0x67}, + {0x3f, 0x00}, + {0x88, 0x21}, + {0x89, 0xf8}, + {0x8a, 0x44}, + {0xfd, 0x02}, + {0xbe, 0xd8}, + {0xbf, 0x04}, + {0xd0, 0xd8}, + {0xd1, 0x04}, + {0xc9, 0xd8}, + {0xca, 0x04}, + {SP2529_TERM, 0}, +}; + +static struct reg_tab_bb sp2529_res_uxga[] = { + {0xfd, 0x00}, + {0x19, 0x00}, + {0x30, 0x0c}, + {0x31, 0x00}, + {0x33, 0x00}, + {0xfd, 0x00}, + {0x95, 0x06}, + {0x94, 0x40}, + {0x97, 0x04}, + {0x96, 0xb0}, + {0xfd, 0x02}, + {0x0f, 0x00}, + {0xfd, 0x00}, + {0x03, 0x02}, + {0x04, 0xe8}, + {0x05, 0x00}, + {0x06, 0x00}, + {0x07, 0x00}, + {0x08, 0x00}, + {0x09, 0x00}, + {0x0a, 0x7e}, + {0xfd, 0x01}, + {0xf0, 0x00}, + {0xf7, 0x7c}, + {0xf8, 0x67}, + {0x02, 0x0a}, + {0x03, 0x01}, + {0x06, 0x7c}, + {0x07, 0x00}, + {0x08, 0x01}, + {0x09, 0x00}, + {0xfd, 0x02}, + {0x3d, 0x0c}, + {0x3e, 0x67}, + {0x3f, 0x00}, + {0x88, 0x21}, + {0x89, 0xf8}, + {0x8a, 0x44}, + {0xfd, 0x02}, + {0xbe, 0xd8}, + {0xbf, 0x04}, + {0xd0, 0xd8}, + {0xd1, 0x04}, + {0xc9, 0xd8}, + {0xca, 0x04}, + {SP2529_TERM, 0}, +}; + +/*interface for mipi setting, based on 24MHz MCLK */ +static __attribute__((unused)) struct reg_tab_bb sp2529_mipi_24m_ld[] = { +}; + +static __attribute__((unused)) struct reg_tab_bb sp2529_mipi_24m_full[] = { +}; + +/**************************** register section end ****************************/ + +enum { + SP2529_PROP_INIT = 0, /* Initialize sequence */ + SP2529_PROP_STM, /* Stream on/off */ + SP2529_PROP_FMT, /* Output format */ + SP2529_PROP_RES, /* Output resolution */ + SP2529_PROP_IF, /* Interface behavior: a sensor output should be + * either MIPI or DVP, so MIPI and DVP share the + * same property ID */ + SP2529_PROP_MIPI = SP2529_PROP_IF, /* MIPI interface behavior */ + SP2529_PROP_DVP = SP2529_PROP_IF, /* DVP interface behavior */ + SP2529_PROP_END, +}; + +enum { + SP2529_INIT_REQ = 0, + SP2529_INIT_DONE, + SP2529_INIT_END, /* don't use it*/ +}; + +enum { + SP2529_STM_OFF = 0, + SP2529_STM_ON, + SP2529_STM_END, /* don't use it*/ +}; + +enum { + SP2529_FMT_YUYV = 0, + SP2529_FMT_YVYU, + SP2529_FMT_UYVY, + SP2529_FMT_VYUY, + SP2529_FMT_END, /* don't use it*/ +}; + +enum { + SP2529_RES_QCIF = 0, + SP2529_RES_QVGA, + SP2529_RES_VGA, + SP2529_RES_BINNING, + SP2529_RES_UXGA, + SP2529_RES_END, /* don't use it*/ +}; + +enum { /* P3:021x~0x2b */ + SP2529_IF_LD = 0, + SP2529_IF_FULL, + SP2529_IF_END, + + SP2529_MIPI_LD = SP2529_IF_LD, + SP2529_MIPI_FULL = SP2529_IF_FULL, + SP2529_MIPI_END = SP2529_IF_END, /* don't use it*/ +}; + +enum { + SP2529_ST_INVALID = 0, /* place holder, don't use 0 as state id*/ + SP2529_ST_UYVY_QCIF, + SP2529_ST_UYVY_QVGA, + SP2529_ST_UYVY_VGA, + SP2529_ST_UYVY_BINNING, + SP2529_ST_UYVY_UXGA, + SP2529_ST_END, /* don't use it*/ +}; + +static struct ecs_default_fmt_info sp2529_fmt_info_table[] = { + [SP2529_FMT_YUYV] = { + .code = V4L2_MBUS_FMT_YUYV8_2X8, + .clrspc = V4L2_COLORSPACE_JPEG, + .fourcc = V4L2_PIX_FMT_YUYV, + }, + [SP2529_FMT_YVYU] = { + .code = V4L2_MBUS_FMT_YVYU8_2X8, + .clrspc = V4L2_COLORSPACE_JPEG, + .fourcc = V4L2_PIX_FMT_YVYU, + }, + [SP2529_FMT_UYVY] = { + .code = V4L2_MBUS_FMT_UYVY8_2X8, + .clrspc = V4L2_COLORSPACE_JPEG, + .fourcc = V4L2_PIX_FMT_UYVY, + }, + [SP2529_FMT_VYUY] = { + .code = V4L2_MBUS_FMT_VYUY8_2X8, + .clrspc = V4L2_COLORSPACE_JPEG, + .fourcc = V4L2_PIX_FMT_VYUY, + }, +}; + +static struct ecs_default_res_info sp2529_res_info_table[] = { + [SP2529_RES_QCIF] = { + .h_act = 176, + .v_act = 144, + }, + [SP2529_RES_QVGA] = { + .h_act = 320, + .v_act = 240, + }, + [SP2529_RES_VGA] = { + .h_act = 640, + .v_act = 480, + }, + [SP2529_RES_BINNING] = { + .h_act = 800, + .v_act = 600, + }, + [SP2529_RES_UXGA] = { + .h_act = 1600, + .v_act = 1200, + }, +}; + +static struct csi_dphy_desc sp2529_mipi_24m_info_table[] = { + [SP2529_MIPI_LD] = { /* Controller config for low defination YUV */ + .clk_mul = 32, + .clk_div = 4, + .hs_prepare = 27, /* time count in clock period */ + .hs_zero = 53, /* time count in clock period */ + .nr_lane = 1, + }, + [SP2529_MIPI_FULL] = { /* FULL */ + .clk_mul = 32, + .clk_div = 4, + .hs_prepare = 27, /* time count in clock period */ + .hs_zero = 53, /* time count in clock period */ + .nr_lane = 1, + }, +}; + +#define SP2529_DECLARE_INIT_SETTING(VAL, val) \ + __DECLARE_SETTING(SP2529, sp2529, INIT, init, VAL, val) +static struct ecs_setting sp2529_init_stn_table[SP2529_INIT_END] = { + SP2529_DECLARE_INIT_SETTING(REQ, req), + SP2529_DECLARE_INIT_SETTING(DONE, done), +}; + +#define SP2529_DECLARE_STM_SETTING(VAL, val) \ + __DECLARE_SETTING(SP2529, sp2529, STM, stm, VAL, val) +static struct ecs_setting sp2529_stm_stn_table[SP2529_STM_END] = { + SP2529_DECLARE_STM_SETTING(OFF, off), + SP2529_DECLARE_STM_SETTING(ON, on), +}; + +#define SP2529_DECLARE_FMT_SETTING(VAL, val) \ + __DECLARE_SETTING_VS_INFO(SP2529, sp2529, FMT, fmt, VAL, val) +static struct ecs_setting sp2529_fmt_stn_table[SP2529_FMT_END] = { + SP2529_DECLARE_FMT_SETTING(YUYV, yuyv), + SP2529_DECLARE_FMT_SETTING(YVYU, yvyu), + SP2529_DECLARE_FMT_SETTING(UYVY, uyvy), + SP2529_DECLARE_FMT_SETTING(VYUY, vyuy), +}; + +#define SP2529_DECLARE_RES_SETTING(VAL, val) \ + __DECLARE_SETTING_VS_INFO(SP2529, sp2529, RES, res, VAL, val) +static struct ecs_setting sp2529_res_stn_table[SP2529_RES_END] = { + SP2529_DECLARE_RES_SETTING(QCIF, qcif), + SP2529_DECLARE_RES_SETTING(QVGA, qvga), + SP2529_DECLARE_RES_SETTING(VGA, vga), + SP2529_DECLARE_RES_SETTING(BINNING, binning), + SP2529_DECLARE_RES_SETTING(UXGA, uxga), +}; + +#define SP2529_DECLARE_MIPI_24M_SETTING(VAL, val) \ + __DECLARE_SETTING_VS_INFO(SP2529, sp2529, MIPI, mipi_24m, VAL, val) +static struct ecs_setting sp2529_mipi_stn_table[SP2529_MIPI_END] = { + SP2529_DECLARE_MIPI_24M_SETTING(LD, ld), + SP2529_DECLARE_MIPI_24M_SETTING(FULL, full), +}; + +static struct ecs_property sp2529_property_table[SP2529_PROP_END] = { + [SP2529_PROP_INIT] = { + .name = "INITIALIZE", + .id = SP2529_PROP_INIT, + .stn_tab = sp2529_init_stn_table, + .stn_num = SP2529_INIT_END, + .reg_low = 0, + .reg_high = 0, + .speculate = 1, + .value_now = UNSET, + .cfg_handler = NULL, + }, + [SP2529_PROP_STM] = { + .name = "STREAM", + .id = SP2529_PROP_STM, + .stn_tab = sp2529_stm_stn_table, + .stn_num = SP2529_STM_END, + .reg_low = 0, + .reg_high = 0, + .speculate = 1, + .value_now = UNSET, + .cfg_handler = NULL, + }, + [SP2529_PROP_FMT] = { + .name = "FORMAT", + .id = SP2529_PROP_FMT, + .stn_tab = sp2529_fmt_stn_table, + .stn_num = SP2529_FMT_END, + .reg_low = 0, + .reg_high = 0, + .speculate = 1, + .value_now = UNSET, + .cfg_handler = NULL, + }, + [SP2529_PROP_RES] = { + .name = "RESOLUTION", + .id = SP2529_PROP_RES, + .stn_tab = sp2529_res_stn_table, + .stn_num = SP2529_RES_END, + .reg_low = 0, + .reg_high = 0, + .speculate = 1, + .value_now = UNSET, + .cfg_handler = NULL, + }, + [SP2529_PROP_IF] = { + .name = "INTERFACE", + .id = SP2529_PROP_IF, + .stn_tab = NULL, + .stn_num = SP2529_IF_END, + .reg_low = 0, + .reg_high = 0, + .speculate = 1, + .value_now = UNSET, + .cfg_handler = NULL, + }, +}; + +/*********************************** state ***********************************/ +/* Default global init sequence */ +static struct ecs_state_cfg sp2529_state_uyvy_qcif[] = { + {SP2529_PROP_FMT, SP2529_FMT_UYVY}, + {SP2529_PROP_RES, SP2529_RES_QCIF}, + {SP2529_PROP_IF, SP2529_IF_LD}, +}; + +static struct ecs_state_cfg sp2529_state_uyvy_qvga[] = { + {SP2529_PROP_FMT, SP2529_FMT_UYVY}, + {SP2529_PROP_RES, SP2529_RES_QVGA}, + {SP2529_PROP_IF, SP2529_IF_LD}, +}; + +static struct ecs_state_cfg sp2529_state_uyvy_vga[] = { + {SP2529_PROP_FMT, SP2529_FMT_UYVY}, + {SP2529_PROP_RES, SP2529_RES_VGA}, + {SP2529_PROP_IF, SP2529_IF_LD}, +}; + +static struct ecs_state_cfg sp2529_state_uyvy_binning[] = { + {SP2529_PROP_FMT, SP2529_FMT_UYVY}, + {SP2529_PROP_RES, SP2529_RES_BINNING}, + {SP2529_PROP_IF, SP2529_IF_LD}, +}; + +static struct ecs_state_cfg sp2529_state_uyvy_uxga[] = { + {SP2529_PROP_FMT, SP2529_FMT_UYVY}, + {SP2529_PROP_RES, SP2529_RES_UXGA}, + {SP2529_PROP_IF, SP2529_IF_FULL}, +}; + + +#define SP2529_DECLARE_STATE(VAL, val) \ + __DECLARE_STATE(SP2529, sp2529, VAL, val) +static struct ecs_state sp2529_state_table[SP2529_ST_END] = { + SP2529_DECLARE_STATE(UYVY_QCIF, uyvy_qcif), + SP2529_DECLARE_STATE(UYVY_QVGA, uyvy_qvga), + SP2529_DECLARE_STATE(UYVY_VGA, uyvy_vga), + SP2529_DECLARE_STATE(UYVY_BINNING, uyvy_binning), + SP2529_DECLARE_STATE(UYVY_UXGA, uyvy_uxga), +}; + +static struct x_i2c sp2529_xic = { + .ident_addr = {0x02}, + .ident_mask = {0xFF}, + .ident_data = {0x25}, + .ident_regs = 1, + .read = xic_read_bb, + .write = xic_write_bb, + .write_array = xic_write_array_bb, + .write_burst = xic_write_burst_bb, + .detect = xic_detect_bb, +}; + +/* This struct is acually the code to instantize ECS to sp2529 driver */ +static struct ecs_sensor generic_sp2529 = { + .name = "sp2529", + .speculate = 1, + .prop_tab = sp2529_property_table, + .prop_num = SP2529_PROP_END, + .state_tab = sp2529_state_table, + .state_num = SP2529_ST_END, + .state_now = UNSET, + .hw_ctx = &sp2529_xic, +}; + +/* x_subdev related */ +/* The supported format*resolutions mapping table */ +static struct v4l2_mbus_framefmt sp2529_fmt_map[SP2529_ST_END]; +static int sp2529_enum_map[SP2529_FMT_END * 2]; + +struct v4l2_subdev_video_ops sp2529_video_ops = { + .g_frame_interval = sp2529_g_frame_interval, +}; + +struct v4l2_subdev_ops sp2529_ops = { + .video = &sp2529_video_ops, +}; + + + +static struct x_subdev sp2529_xsd = { + .ecs = &generic_sp2529, + .ops = &sp2529_ops, /* Contain specialized functions only */ + .cid_list = NULL, + .cid_cnt = 0, + .state_map = sp2529_fmt_map, + .enum_map = sp2529_enum_map, + .profile = -1, + .init_id = SP2529_PROP_INIT, + .fmt_id = SP2529_PROP_FMT, + .res_id = SP2529_PROP_RES, + .str_id = SP2529_PROP_STM, + .ifc_id = SP2529_PROP_IF, + .get_profile = &sp2529_get_profile, + .get_fmt_code = &xsd_default_get_fmt_code, + .get_res_desc = &xsd_default_get_res_desc, + .get_mbus_cfg = + (int (*)(void *, struct v4l2_mbus_config *))&csi2phy_desc_to_mbus_cfg, +}; + +/********************** platform specific configuration **********************/ + +static struct ecs_property pxa98x_spec_prop[] = { + { + .name = "MIPI", + .id = SP2529_PROP_MIPI, + .stn_tab = sp2529_mipi_stn_table, + .stn_num = SP2529_MIPI_END, + .speculate = 1, + }, +}; + +static struct ecs_sensor pxa98x_spec = { + .name = "pxa98x specific settings", + .prop_tab = pxa98x_spec_prop, + .prop_num = ARRAY_SIZE(pxa98x_spec_prop), +}; + +static __attribute__((unused)) int sp2529_state_list[] = { + SP2529_ST_UYVY_QCIF, + SP2529_ST_UYVY_QVGA, + SP2529_ST_UYVY_VGA, + SP2529_ST_UYVY_BINNING, + SP2529_ST_UYVY_UXGA, +}; + +struct xsd_spec_item sp2529_spec_list[] = { + { + .name = "pxa-mipi", + .state_list = sp2529_state_list, + .state_cnt = ARRAY_SIZE(sp2529_state_list), + .ecs = &pxa98x_spec, + }, +}; +/************************* Finally the big data boss *************************/ +static const struct xsd_driver_id sp2529_drv_table[] = { + { + .name = "sp2529", + .prototype = &sp2529_xsd, + .spec_list = sp2529_spec_list, + .spec_cnt = ARRAY_SIZE(sp2529_spec_list), + }, + /* TODO: add more driver structure above this end mark */ + {}, +}; + +#endif |