Advertisement
Not a member of Pastebin yet?
Sign Up,
it unlocks many cool features!
- #define pr_fmt(fmt) KBUILD_MODNAME ": " fmt
- #include <linux/clk.h>
- #include <linux/delay.h>
- #include <linux/gpio/consumer.h>
- #include <linux/i2c.h>
- #include <linux/log2.h>
- #include <linux/mutex.h>
- #include <linux/of.h>
- #include <linux/regmap.h>
- #include <linux/slab.h>
- #include <linux/videodev2.h>
- #include <linux/v4l2-mediabus.h>
- #include <linux/module.h>
- #include <media/v4l2-ctrls.h>
- #include <media/v4l2-device.h>
- #include <media/v4l2-of.h>
- #include <media/v4l2-subdev.h>
- struct ar0135 {
- struct v4l2_subdev subdev;
- struct media_pad pad;
- struct v4l2_mbus_framefmt format;
- struct v4l2_rect crop;
- struct {
- struct v4l2_ctrl *link_freq;
- };
- struct mutex power_lock;
- int power_count;
- struct regmap *regmap;
- struct gpio_desc *reset_gpio;
- struct clk *xclk;
- int xclk_freq;
- };
- static struct ar0135 *to_ar0135(struct v4l2_subdev *sd)
- {
- return container_of(sd, struct ar0135, subdev);
- }
- static int ar0135_s_stream(struct v4l2_subdev *subdev, int enable)
- {
- return 0;
- }
- /* -----------------------------------------------------------------------------
- * V4L2 subdev core operations
- */
- static int ar0135_set_power(struct v4l2_subdev *subdev, int on)
- {
- return 0;
- }
- /* -----------------------------------------------------------------------------
- * V4L2 subdev internal operations
- */
- static int ar0135_registered(struct v4l2_subdev *subdev)
- {
- pr_info("registered");
- return 0;
- }
- static struct v4l2_subdev_core_ops ar0135_subdev_core_ops = {
- .s_power = ar0135_set_power,
- };
- static struct v4l2_subdev_video_ops ar0135_subdev_video_ops = {
- .s_stream = ar0135_s_stream,
- };
- static struct v4l2_subdev_ops ar0135_subdev_ops = {
- .core = &ar0135_subdev_core_ops,
- .video = &ar0135_subdev_video_ops,
- };
- static const struct v4l2_subdev_internal_ops ar0135_subdev_internal_ops = {
- .registered = ar0135_registered,
- };
- /* -----------------------------------------------------------------------------
- * Driver initialization and probing
- */
- static int ar0135_probe(struct i2c_client *client,
- const struct i2c_device_id *did)
- {
- struct ar0135 *ar0135;
- int ret;
- pr_info("starting probe");
- ar0135 = devm_kzalloc(&client->dev, sizeof(*ar0135), GFP_KERNEL);
- if (!ar0135)
- return -ENOMEM;
- v4l2_i2c_subdev_init(&ar0135->subdev, client, &ar0135_subdev_ops);
- ar0135->subdev.flags |= V4L2_SUBDEV_FL_HAS_DEVNODE;
- ar0135->subdev.internal_ops = &ar0135_subdev_internal_ops;
- ar0135->pad.flags = MEDIA_PAD_FL_SOURCE;
- ar0135->subdev.entity.function = MEDIA_ENT_F_CAM_SENSOR;
- ret = media_entity_pads_init(&ar0135->subdev.entity, 1, &ar0135->pad);
- if (ret < 0)
- goto err;
- ar0135->subdev.dev = &client->dev;
- ret = v4l2_async_register_subdev(&ar0135->subdev);
- if (ret < 0)
- goto err;
- pr_info("finished probe");
- return 0;
- err:
- media_entity_cleanup(&ar0135->subdev.entity);
- return ret;
- }
- static int ar0135_remove(struct i2c_client *client)
- {
- struct v4l2_subdev *subdev = i2c_get_clientdata(client);
- v4l2_async_unregister_subdev(subdev);
- media_entity_cleanup(&subdev->entity);
- return 0;
- }
- static const struct i2c_device_id ar0135_id[] = {
- { "ar0135", 0 },
- {}
- };
- MODULE_DEVICE_TABLE(i2c, ar0135_id);
- #if IS_ENABLED(CONFIG_OF)
- static const struct of_device_id ar0135_of_match[] = {
- { .compatible = "onsemi,ar0135" },
- {}
- };
- MODULE_DEVICE_TABLE(of, ar0135_of_match);
- #endif
- static struct i2c_driver ar0135_driver = {
- .driver = {
- .name = "ar0135",
- .of_match_table = of_match_ptr(ar0135_of_match),
- },
- .probe = ar0135_probe,
- .remove = ar0135_remove,
- .id_table = ar0135_id,
- };
- module_i2c_driver(ar0135_driver);
- MODULE_DESCRIPTION("ON Semiconductor AR0135 Sensor");
- MODULE_AUTHOR("Jack Mitchell <jack@embed.me.uk>");
- MODULE_LICENSE("GPL");
Advertisement
Add Comment
Please, Sign In to add comment
Advertisement