// SPDX-License-Identifier: GPL-2.0-only
 /*
 * USB Driver for ALi m5602 based webcams
 *
 * Copyright (C) 2008 Erik Andrén
 * Copyright (C) 2007 Ilyes Gouta. Based on the m5603x Linux Driver Project.
 * Copyright (C) 2005 m5603x Linux Driver Project <m5602@x3ng.com.br>
 *
 * Portions of code to USB interface and ALi driver software,
 * Copyright (c) 2006 Willem Duinker
 * v4l2 interface modeled after the V4L2 driver
 * for SN9C10x PC Camera Controllers
 */

#define pr_fmt(fmt) KBUILD_MODNAME ": " fmt

#include "m5602_ov9650.h"
#include "m5602_ov7660.h"
#include "m5602_mt9m111.h"
#include "m5602_po1030.h"
#include "m5602_s5k83a.h"
#include "m5602_s5k4aa.h"

/* Kernel module parameters */
int force_sensor;
static bool dump_bridge;
bool dump_sensor;

static const struct usb_device_id m5602_table[] = {
	{USB_DEVICE(0x0402, 0x5602)},
	{}
};

MODULE_DEVICE_TABLE(usb, m5602_table);

/* A skeleton used for sending messages to the sensor */
static const unsigned char sensor_urb_skeleton[] = {
	0x23, M5602_XB_GPIO_EN_H, 0x81, 0x06,
	0x23, M5602_XB_MISC_CTRL, 0x81, 0x80,
	0x13, M5602_XB_I2C_DEV_ADDR, 0x81, 0x00,
	0x13, M5602_XB_I2C_REG_ADDR, 0x81, 0x00,
	0x13, M5602_XB_I2C_DATA, 0x81, 0x00,
	0x13, M5602_XB_I2C_CTRL, 0x81, 0x11
};

/* A skeleton used for sending messages to the m5602 bridge */
static const unsigned char bridge_urb_skeleton[] = {
	0x13, 0x00, 0x81, 0x00
};

/* Reads a byte from the m5602 */
int m5602_read_bridge(struct sd *sd, const u8 address, u8 *i2c_data)
{
	int err;
	struct gspca_dev *gspca_dev = (struct gspca_dev *) sd;
	struct usb_device *udev = sd->gspca_dev.dev;
	__u8 *buf = sd->gspca_dev.usb_buf;

	err = usb_control_msg(udev, usb_rcvctrlpipe(udev, 0),
			      0x04, 0xc0, 0x14,
			      0x8100 + address, buf,
			      1, M5602_URB_MSG_TIMEOUT);
	*i2c_data = buf[0];

	gspca_dbg(gspca_dev, D_CONF, "Reading bridge register 0x%x containing 0x%x\n",
		  address, *i2c_data);

	/* usb_control_msg(...) returns the number of bytes sent upon success,
	mask that and return zero instead*/
	return (err < 0) ? err : 0;
}

/* Writes a byte to the m5602 */
int m5602_write_bridge(struct sd *sd, const u8 address, const u8 i2c_data)
{
	int err;
	struct gspca_dev *gspca_dev = (struct gspca_dev *) sd;
	struct usb_device *udev = sd->gspca_dev.dev;
	__u8 *buf = sd->gspca_dev.usb_buf;

	gspca_dbg(gspca_dev, D_CONF, "Writing bridge register 0x%x with 0x%x\n",
		  address, i2c_data);

	memcpy(buf, bridge_urb_skeleton,
	       sizeof(bridge_urb_skeleton));
	buf[1] = address;
	buf[3] = i2c_data;

	err = usb_control_msg(udev, usb_sndctrlpipe(udev, 0),
				0x04, 0x40, 0x19,
				0x0000, buf,
				4, M5602_URB_MSG_TIMEOUT);

	/* usb_control_msg(...) returns the number of bytes sent upon success,
	   mask that and return zero instead */
	return (err < 0) ? err : 0;
}

static int m5602_wait_for_i2c(struct sd *sd)
{
	int err;
	u8 data;

	do {
		err = m5602_read_bridge(sd, M5602_XB_I2C_STATUS, &data);
	} while ((data & I2C_BUSY) && !err);
	return err;
}

int m5602_read_sensor(struct sd *sd, const u8 address,
		       u8 *i2c_data, const u8 len)
{
	int err, i;
	struct gspca_dev *gspca_dev = (struct gspca_dev *) sd;

	if (!len || len > sd->sensor->i2c_regW)
		return -EINVAL;

	err = m5602_wait_for_i2c(sd);
	if (err < 0)
		return err;

	err = m5602_write_bridge(sd, M5602_XB_I2C_DEV_ADDR,
				 sd->sensor->i2c_slave_id);
	if (err < 0)
		return err;

	err = m5602_write_bridge(sd, M5602_XB_I2C_REG_ADDR, address);
	if (err < 0)
		return err;

	/* Sensors with registers that are of only
	   one byte width are differently read */

	/* FIXME: This works with the ov9650, but has issues with the po1030 */
	if (sd->sensor->i2c_regW == 1) {
		err = m5602_write_bridge(sd, M5602_XB_I2C_CTRL, 1);
		if (err < 0)
			return err;

		err = m5602_write_bridge(sd, M5602_XB_I2C_CTRL, 0x08);
	} else {
		err = m5602_write_bridge(sd, M5602_XB_I2C_CTRL, 0x18 + len);
	}

	for (i = 0; (i < len) && !err; i++) {
		err = m5602_wait_for_i2c(sd);
		if (err < 0)
			return err;

		err = m5602_read_bridge(sd, M5602_XB_I2C_DATA, &(i2c_data[i]));

		gspca_dbg(gspca_dev, D_CONF, "Reading sensor register 0x%x containing 0x%x\n",
			  address, *i2c_data);
	}
	return err;
}

int m5602_write_sensor(struct sd *sd, const u8 address,
			u8 *i2c_data, const u8 len)
{
	int err, i;
	u8 *p;
	struct gspca_dev *gspca_dev = (struct gspca_dev *) sd;
	struct usb_device *udev = sd->gspca_dev.dev;
	__u8 *buf = sd->gspca_dev.usb_buf;

	/* No sensor with a data width larger than 16 bits has yet been seen */
	if (len > sd->sensor->i2c_regW || !len)
		return -EINVAL;

	memcpy(buf, sensor_urb_skeleton,
	       sizeof(sensor_urb_skeleton));

	buf[11] = sd->sensor->i2c_slave_id;
	buf[15] = address;

	/* Special case larger sensor writes */
	p = buf + 16;

	/* Copy a four byte write sequence for each byte to be written to */
	for (i = 0; i < len; i++) {
		memcpy(p, sensor_urb_skeleton + 16, 4);
		p[3] = i2c_data[i];
		p += 4;
		gspca_dbg(gspca_dev, D_CONF, "Writing sensor register 0x%x with 0x%x\n",
			  address, i2c_data[i]);
	}

	/* Copy the tailer */
	memcpy(p, sensor_urb_skeleton + 20, 4);

	/* Set the total length */
	p[3] = 0x10 + len;

	err = usb_control_msg(udev, usb_sndctrlpipe(udev, 0),
			      0x04, 0x40, 0x19,
			      0x0000, buf,
			      20 + len * 4, M5602_URB_MSG_TIMEOUT);

	return (err < 0) ? err : 0;
}

/* Dump all the registers of the m5602 bridge,
   unfortunately this breaks the camera until it's power cycled */
static void m5602_dump_bridge(struct sd *sd)
{
	int i;
	for (i = 0; i < 0x80; i++) {
		unsigned char val = 0;
		m5602_read_bridge(sd, i, &val);
		pr_info("ALi m5602 address 0x%x contains 0x%x\n", i, val);
	}
	pr_info("Warning: The ALi m5602 webcam probably won't work until it's power cycled\n");
}

static int m5602_probe_sensor(struct sd *sd)
{
	/* Try the po1030 */
	sd->sensor = &po1030;
	if (!sd->sensor->probe(sd))
		return 0;

	/* Try the mt9m111 sensor */
	sd->sensor = &mt9m111;
	if (!sd->sensor->probe(sd))
		return 0;

	/* Try the s5k4aa */
	sd->sensor = &s5k4aa;
	if (!sd->sensor->probe(sd))
		return 0;

	/* Try the ov9650 */
	sd->sensor = &ov9650;
	if (!sd->sensor->probe(sd))
		return 0;

	/* Try the ov7660 */
	sd->sensor = &ov7660;
	if (!sd->sensor->probe(sd))
		return 0;

	/* Try the s5k83a */
	sd->sensor = &s5k83a;
	if (!sd->sensor->probe(sd))
		return 0;

	/* More sensor probe function goes here */
	pr_info("Failed to find a sensor\n");
	sd->sensor = NULL;
	return -ENODEV;
}

static int m5602_configure(struct gspca_dev *gspca_dev,
			   const struct usb_device_id *id);

static int m5602_init(struct gspca_dev *gspca_dev)
{
	struct sd *sd = (struct sd *) gspca_dev;
	int err;

	gspca_dbg(gspca_dev, D_CONF, "Initializing ALi m5602 webcam\n");
	/* Run the init sequence */
	err = sd->sensor->init(sd);

	return err;
}

static int m5602_init_controls(struct gspca_dev *gspca_dev)
{
	struct sd *sd = (struct sd *) gspca_dev;

	if (!sd->sensor->init_controls)
		return 0;

	return sd->sensor->init_controls(sd);
}

static int m5602_start_transfer(struct gspca_dev *gspca_dev)
{
	struct sd *sd = (struct sd *) gspca_dev;
	__u8 *buf = sd->gspca_dev.usb_buf;
	int err;

	/* Send start command to the camera */
	const u8 buffer[4] = {0x13, 0xf9, 0x0f, 0x01};

	if (sd->sensor->start)
		sd->sensor->start(sd);

	memcpy(buf, buffer, sizeof(buffer));
	err = usb_control_msg(gspca_dev->dev,
			      usb_sndctrlpipe(gspca_dev->dev, 0),
			      0x04, 0x40, 0x19, 0x0000, buf,
			      sizeof(buffer), M5602_URB_MSG_TIMEOUT);

	gspca_dbg(gspca_dev, D_STREAM, "Transfer started\n");
	return (err < 0) ? err : 0;
}

static void m5602_urb_complete(struct gspca_dev *gspca_dev,
				u8 *data, int len)
{
	struct sd *sd = (struct sd *) gspca_dev;

	if (len < 6) {
		gspca_dbg(gspca_dev, D_PACK, "Packet is less than 6 bytes\n");
		return;
	}

	/* Frame delimiter: ff xx xx xx ff ff */
	if (data[0] == 0xff && data[4] == 0xff && data[5] == 0xff &&
	    data[2] != sd->frame_id) {
		gspca_dbg(gspca_dev, D_FRAM, "Frame delimiter detected\n");
		sd->frame_id = data[2];

		/* Remove the extra fluff appended on each header */
		data += 6;
		len -= 6;

		/* Complete the last frame (if any) */
		gspca_frame_add(gspca_dev, LAST_PACKET,
				NULL, 0);
		sd->frame_count++;

		/* Create a new frame */
		gspca_frame_add(gspca_dev, FIRST_PACKET, data, len);

		gspca_dbg(gspca_dev, D_FRAM, "Starting new frame %d\n",
			  sd->frame_count);

	} else {
		int cur_frame_len;

		cur_frame_len = gspca_dev->image_len;
		/* Remove urb header */
		data += 4;
		len -= 4;

		if (cur_frame_len + len <= gspca_dev->pixfmt.sizeimage) {
			gspca_dbg(gspca_dev, D_FRAM, "Continuing frame %d copying %d bytes\n",
				  sd->frame_count, len);

			gspca_frame_add(gspca_dev, INTER_PACKET,
					data, len);
		} else {
			/* Add the remaining data up to frame size */
			gspca_frame_add(gspca_dev, INTER_PACKET, data,
				gspca_dev->pixfmt.sizeimage - cur_frame_len);
		}
	}
}

static void m5602_stop_transfer(struct gspca_dev *gspca_dev)
{
	struct sd *sd = (struct sd *) gspca_dev;

	/* Run the sensor specific end transfer sequence */
	if (sd->sensor->stop)
		sd->sensor->stop(sd);
}

/* sub-driver description */
static const struct sd_desc sd_desc = {
	.name		= MODULE_NAME,
	.config		= m5602_configure,
	.init		= m5602_init,
	.init_controls	= m5602_init_controls,
	.start		= m5602_start_transfer,
	.stopN		= m5602_stop_transfer,
	.pkt_scan	= m5602_urb_complete
};

/* this function is called at probe time */
static int m5602_configure(struct gspca_dev *gspca_dev,
			   const struct usb_device_id *id)
{
	struct sd *sd = (struct sd *) gspca_dev;
	struct cam *cam;
	int err;

	cam = &gspca_dev->cam;

	if (dump_bridge)
		m5602_dump_bridge(sd);

	/* Probe sensor */
	err = m5602_probe_sensor(sd);
	if (err)
		goto fail;

	return 0;

fail:
	gspca_err(gspca_dev, "ALi m5602 webcam failed\n");
	cam->cam_mode = NULL;
	cam->nmodes = 0;

	return err;
}

static int m5602_probe(struct usb_interface *intf,
		       const struct usb_device_id *id)
{
	return gspca_dev_probe(intf, id, &sd_desc, sizeof(struct sd),
			       THIS_MODULE);
}

static void m5602_disconnect(struct usb_interface *intf)
{
	struct gspca_dev *gspca_dev = usb_get_intfdata(intf);
	struct sd *sd = (struct sd *) gspca_dev;

	if (sd->sensor->disconnect)
		sd->sensor->disconnect(sd);

	gspca_disconnect(intf);
}

static struct usb_driver sd_driver = {
	.name = MODULE_NAME,
	.id_table = m5602_table,
	.probe = m5602_probe,
#ifdef CONFIG_PM
	.suspend = gspca_suspend,
	.resume = gspca_resume,
	.reset_resume = gspca_resume,
#endif
	.disconnect = m5602_disconnect
};

module_usb_driver(sd_driver);

MODULE_AUTHOR(DRIVER_AUTHOR);
MODULE_DESCRIPTION(DRIVER_DESC);
MODULE_LICENSE("GPL");
module_param(force_sensor, int, S_IRUGO | S_IWUSR);
MODULE_PARM_DESC(force_sensor,
		"forces detection of a sensor, 1 = OV9650, 2 = S5K83A, 3 = S5K4AA, 4 = MT9M111, 5 = PO1030, 6 = OV7660");

module_param(dump_bridge, bool, S_IRUGO | S_IWUSR);
MODULE_PARM_DESC(dump_bridge, "Dumps all usb bridge registers at startup");

module_param(dump_sensor, bool, S_IRUGO | S_IWUSR);
MODULE_PARM_DESC(dump_sensor, "Dumps all usb sensor registers at startup providing a sensor is found");
