// SPDX-License-Identifier: GPL-2.0-or-later
/*
 * SQ905 subdriver
 *
 * Copyright (C) 2008, 2009 Adam Baker and Theodore Kilgore
 */

/*
 * History and Acknowledgments
 *
 * The original Linux driver for SQ905 based cameras was written by
 * Marcell Lengyel and further developed by many other contributors
 * and is available from http://sourceforge.net/projects/sqcam/
 *
 * This driver takes advantage of the reverse engineering work done for
 * that driver and for libgphoto2 but shares no code with them.
 *
 * This driver has used as a base the finepix driver and other gspca
 * based drivers and may still contain code fragments taken from those
 * drivers.
 */

#define pr_fmt(fmt) KBUILD_MODNAME ": " fmt

#define MODULE_NAME "sq905"

#include <linux/workqueue.h>
#include <linux/slab.h>
#include "gspca.h"

MODULE_AUTHOR("Adam Baker <linux@baker-net.org.uk>, Theodore Kilgore <kilgota@auburn.edu>");
MODULE_DESCRIPTION("GSPCA/SQ905 USB Camera Driver");
MODULE_LICENSE("GPL");

/* Default timeouts, in ms */
#define SQ905_CMD_TIMEOUT 500
#define SQ905_DATA_TIMEOUT 1000

/* Maximum transfer size to use. */
#define SQ905_MAX_TRANSFER 0x8000
#define FRAME_HEADER_LEN 64

/* The known modes, or registers. These go in the "value" slot. */

/* 00 is "none" obviously */

#define SQ905_BULK_READ	0x03	/* precedes any bulk read */
#define SQ905_COMMAND	0x06	/* precedes the command codes below */
#define SQ905_PING	0x07	/* when reading an "idling" command */
#define SQ905_READ_DONE 0xc0    /* ack bulk read completed */

/* Any non-zero value in the bottom 2 bits of the 2nd byte of
 * the ID appears to indicate the camera can do 640*480. If the
 * LSB of that byte is set the image is just upside down, otherwise
 * it is rotated 180 degrees. */
#define SQ905_HIRES_MASK	0x00000300
#define SQ905_ORIENTATION_MASK	0x00000100

/* Some command codes. These go in the "index" slot. */

#define SQ905_ID      0xf0	/* asks for model string */
#define SQ905_CONFIG  0x20	/* gets photo alloc. table, not used here */
#define SQ905_DATA    0x30	/* accesses photo data, not used here */
#define SQ905_CLEAR   0xa0	/* clear everything */
#define SQ905_CAPTURE_LOW  0x60	/* Starts capture at 160x120 */
#define SQ905_CAPTURE_MED  0x61	/* Starts capture at 320x240 */
#define SQ905_CAPTURE_HIGH 0x62	/* Starts capture at 640x480 (some cams only) */
/* note that the capture command also controls the output dimensions */

/* Structure to hold all of our device specific stuff */
struct sd {
	struct gspca_dev gspca_dev;	/* !! must be the first item */

	/*
	 * Driver stuff
	 */
	struct work_struct work_struct;
	struct workqueue_struct *work_thread;
};

static struct v4l2_pix_format sq905_mode[] = {
	{ 160, 120, V4L2_PIX_FMT_SBGGR8, V4L2_FIELD_NONE,
		.bytesperline = 160,
		.sizeimage = 160 * 120,
		.colorspace = V4L2_COLORSPACE_SRGB,
		.priv = 0},
	{ 320, 240, V4L2_PIX_FMT_SBGGR8, V4L2_FIELD_NONE,
		.bytesperline = 320,
		.sizeimage = 320 * 240,
		.colorspace = V4L2_COLORSPACE_SRGB,
		.priv = 0},
	{ 640, 480, V4L2_PIX_FMT_SBGGR8, V4L2_FIELD_NONE,
		.bytesperline = 640,
		.sizeimage = 640 * 480,
		.colorspace = V4L2_COLORSPACE_SRGB,
		.priv = 0}
};

/*
 * Send a command to the camera.
 */
static int sq905_command(struct gspca_dev *gspca_dev, u16 index)
{
	int ret;

	gspca_dev->usb_buf[0] = '\0';
	ret = usb_control_msg(gspca_dev->dev,
			      usb_sndctrlpipe(gspca_dev->dev, 0),
			      USB_REQ_SYNCH_FRAME,                /* request */
			      USB_DIR_OUT | USB_TYPE_VENDOR | USB_RECIP_DEVICE,
			      SQ905_COMMAND, index, gspca_dev->usb_buf, 1,
			      SQ905_CMD_TIMEOUT);
	if (ret < 0) {
		pr_err("%s: usb_control_msg failed (%d)\n", __func__, ret);
		return ret;
	}

	ret = usb_control_msg(gspca_dev->dev,
			      usb_rcvctrlpipe(gspca_dev->dev, 0),
			      USB_REQ_SYNCH_FRAME,                /* request */
			      USB_DIR_IN | USB_TYPE_VENDOR | USB_RECIP_DEVICE,
			      SQ905_PING, 0, gspca_dev->usb_buf, 1,
			      SQ905_CMD_TIMEOUT);
	if (ret < 0) {
		pr_err("%s: usb_control_msg failed 2 (%d)\n", __func__, ret);
		return ret;
	}

	return 0;
}

/*
 * Acknowledge the end of a frame - see warning on sq905_command.
 */
static int sq905_ack_frame(struct gspca_dev *gspca_dev)
{
	int ret;

	gspca_dev->usb_buf[0] = '\0';
	ret = usb_control_msg(gspca_dev->dev,
			      usb_sndctrlpipe(gspca_dev->dev, 0),
			      USB_REQ_SYNCH_FRAME,                /* request */
			      USB_DIR_OUT | USB_TYPE_VENDOR | USB_RECIP_DEVICE,
			      SQ905_READ_DONE, 0, gspca_dev->usb_buf, 1,
			      SQ905_CMD_TIMEOUT);
	if (ret < 0) {
		pr_err("%s: usb_control_msg failed (%d)\n", __func__, ret);
		return ret;
	}

	return 0;
}

/*
 *  request and read a block of data - see warning on sq905_command.
 */
static int
sq905_read_data(struct gspca_dev *gspca_dev, u8 *data, int size, int need_lock)
{
	int ret;
	int act_len = 0;

	gspca_dev->usb_buf[0] = '\0';
	if (need_lock)
		mutex_lock(&gspca_dev->usb_lock);
	ret = usb_control_msg(gspca_dev->dev,
			      usb_sndctrlpipe(gspca_dev->dev, 0),
			      USB_REQ_SYNCH_FRAME,                /* request */
			      USB_DIR_OUT | USB_TYPE_VENDOR | USB_RECIP_DEVICE,
			      SQ905_BULK_READ, size, gspca_dev->usb_buf,
			      1, SQ905_CMD_TIMEOUT);
	if (need_lock)
		mutex_unlock(&gspca_dev->usb_lock);
	if (ret < 0) {
		pr_err("%s: usb_control_msg failed (%d)\n", __func__, ret);
		return ret;
	}
	ret = usb_bulk_msg(gspca_dev->dev,
			   usb_rcvbulkpipe(gspca_dev->dev, 0x81),
			   data, size, &act_len, SQ905_DATA_TIMEOUT);

	/* successful, it returns 0, otherwise  negative */
	if (ret < 0 || act_len != size) {
		pr_err("bulk read fail (%d) len %d/%d\n", ret, act_len, size);
		return -EIO;
	}
	return 0;
}

/*
 * This function is called as a workqueue function and runs whenever the camera
 * is streaming data. Because it is a workqueue function it is allowed to sleep
 * so we can use synchronous USB calls. To avoid possible collisions with other
 * threads attempting to use gspca_dev->usb_buf we take the usb_lock when
 * performing USB operations using it. In practice we don't really need this
 * as the camera doesn't provide any controls.
 */
static void sq905_dostream(struct work_struct *work)
{
	struct sd *dev = container_of(work, struct sd, work_struct);
	struct gspca_dev *gspca_dev = &dev->gspca_dev;
	int bytes_left; /* bytes remaining in current frame. */
	int data_len;   /* size to use for the next read. */
	int header_read; /* true if we have already read the frame header. */
	int packet_type;
	int frame_sz;
	int ret;
	u8 *data;
	u8 *buffer;

	buffer = kmalloc(SQ905_MAX_TRANSFER, GFP_KERNEL);
	if (!buffer) {
		pr_err("Couldn't allocate USB buffer\n");
		goto quit_stream;
	}

	frame_sz = gspca_dev->cam.cam_mode[gspca_dev->curr_mode].sizeimage
			+ FRAME_HEADER_LEN;

	while (gspca_dev->present && gspca_dev->streaming) {
#ifdef CONFIG_PM
		if (gspca_dev->frozen)
			break;
#endif
		/* request some data and then read it until we have
		 * a complete frame. */
		bytes_left = frame_sz;
		header_read = 0;

		/* Note we do not check for gspca_dev->streaming here, as
		   we must finish reading an entire frame, otherwise the
		   next time we stream we start reading in the middle of a
		   frame. */
		while (bytes_left > 0 && gspca_dev->present) {
			data_len = bytes_left > SQ905_MAX_TRANSFER ?
				SQ905_MAX_TRANSFER : bytes_left;
			ret = sq905_read_data(gspca_dev, buffer, data_len, 1);
			if (ret < 0)
				goto quit_stream;
			gspca_dbg(gspca_dev, D_PACK,
				  "Got %d bytes out of %d for frame\n",
				  data_len, bytes_left);
			bytes_left -= data_len;
			data = buffer;
			if (!header_read) {
				packet_type = FIRST_PACKET;
				/* The first 64 bytes of each frame are
				 * a header full of FF 00 bytes */
				data += FRAME_HEADER_LEN;
				data_len -= FRAME_HEADER_LEN;
				header_read = 1;
			} else if (bytes_left == 0) {
				packet_type = LAST_PACKET;
			} else {
				packet_type = INTER_PACKET;
			}
			gspca_frame_add(gspca_dev, packet_type,
					data, data_len);
			/* If entire frame fits in one packet we still
			   need to add a LAST_PACKET */
			if (packet_type == FIRST_PACKET &&
			    bytes_left == 0)
				gspca_frame_add(gspca_dev, LAST_PACKET,
						NULL, 0);
		}
		if (gspca_dev->present) {
			/* acknowledge the frame */
			mutex_lock(&gspca_dev->usb_lock);
			ret = sq905_ack_frame(gspca_dev);
			mutex_unlock(&gspca_dev->usb_lock);
			if (ret < 0)
				goto quit_stream;
		}
	}
quit_stream:
	if (gspca_dev->present) {
		mutex_lock(&gspca_dev->usb_lock);
		sq905_command(gspca_dev, SQ905_CLEAR);
		mutex_unlock(&gspca_dev->usb_lock);
	}
	kfree(buffer);
}

/* This function is called at probe time just before sd_init */
static int sd_config(struct gspca_dev *gspca_dev,
		const struct usb_device_id *id)
{
	struct cam *cam = &gspca_dev->cam;
	struct sd *dev = (struct sd *) gspca_dev;

	/* We don't use the buffer gspca allocates so make it small. */
	cam->bulk = 1;
	cam->bulk_size = 64;

	INIT_WORK(&dev->work_struct, sq905_dostream);

	return 0;
}

/* called on streamoff with alt==0 and on disconnect */
/* the usb_lock is held at entry - restore on exit */
static void sd_stop0(struct gspca_dev *gspca_dev)
{
	struct sd *dev = (struct sd *) gspca_dev;

	/* wait for the work queue to terminate */
	mutex_unlock(&gspca_dev->usb_lock);
	/* This waits for sq905_dostream to finish */
	destroy_workqueue(dev->work_thread);
	dev->work_thread = NULL;
	mutex_lock(&gspca_dev->usb_lock);
}

/* this function is called at probe and resume time */
static int sd_init(struct gspca_dev *gspca_dev)
{
	u32 ident;
	int ret;

	/* connect to the camera and read
	 * the model ID and process that and put it away.
	 */
	ret = sq905_command(gspca_dev, SQ905_CLEAR);
	if (ret < 0)
		return ret;
	ret = sq905_command(gspca_dev, SQ905_ID);
	if (ret < 0)
		return ret;
	ret = sq905_read_data(gspca_dev, gspca_dev->usb_buf, 4, 0);
	if (ret < 0)
		return ret;
	/* usb_buf is allocated with kmalloc so is aligned.
	 * Camera model number is the right way round if we assume this
	 * reverse engineered ID is supposed to be big endian. */
	ident = be32_to_cpup((__be32 *)gspca_dev->usb_buf);
	ret = sq905_command(gspca_dev, SQ905_CLEAR);
	if (ret < 0)
		return ret;
	gspca_dbg(gspca_dev, D_CONF, "SQ905 camera ID %08x detected\n", ident);
	gspca_dev->cam.cam_mode = sq905_mode;
	gspca_dev->cam.nmodes = ARRAY_SIZE(sq905_mode);
	if (!(ident & SQ905_HIRES_MASK))
		gspca_dev->cam.nmodes--;

	if (ident & SQ905_ORIENTATION_MASK)
		gspca_dev->cam.input_flags = V4L2_IN_ST_VFLIP;
	else
		gspca_dev->cam.input_flags = V4L2_IN_ST_VFLIP |
					     V4L2_IN_ST_HFLIP;
	return 0;
}

/* Set up for getting frames. */
static int sd_start(struct gspca_dev *gspca_dev)
{
	struct sd *dev = (struct sd *) gspca_dev;
	int ret;

	/* "Open the shutter" and set size, to start capture */
	switch (gspca_dev->curr_mode) {
	default:
/*	case 2: */
		gspca_dbg(gspca_dev, D_STREAM, "Start streaming at high resolution\n");
		ret = sq905_command(&dev->gspca_dev, SQ905_CAPTURE_HIGH);
		break;
	case 1:
		gspca_dbg(gspca_dev, D_STREAM, "Start streaming at medium resolution\n");
		ret = sq905_command(&dev->gspca_dev, SQ905_CAPTURE_MED);
		break;
	case 0:
		gspca_dbg(gspca_dev, D_STREAM, "Start streaming at low resolution\n");
		ret = sq905_command(&dev->gspca_dev, SQ905_CAPTURE_LOW);
	}

	if (ret < 0) {
		gspca_err(gspca_dev, "Start streaming command failed\n");
		return ret;
	}
	/* Start the workqueue function to do the streaming */
	dev->work_thread = create_singlethread_workqueue(MODULE_NAME);
	if (!dev->work_thread)
		return -ENOMEM;

	queue_work(dev->work_thread, &dev->work_struct);

	return 0;
}

/* Table of supported USB devices */
static const struct usb_device_id device_table[] = {
	{USB_DEVICE(0x2770, 0x9120)},
	{}
};

MODULE_DEVICE_TABLE(usb, device_table);

/* sub-driver description */
static const struct sd_desc sd_desc = {
	.name   = MODULE_NAME,
	.config = sd_config,
	.init   = sd_init,
	.start  = sd_start,
	.stop0  = sd_stop0,
};

/* -- device connect -- */
static int sd_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 struct usb_driver sd_driver = {
	.name       = MODULE_NAME,
	.id_table   = device_table,
	.probe      = sd_probe,
	.disconnect = gspca_disconnect,
#ifdef CONFIG_PM
	.suspend = gspca_suspend,
	.resume  = gspca_resume,
	.reset_resume = gspca_resume,
#endif
};

module_usb_driver(sd_driver);
