Donate to e Foundation | Murena handsets with /e/OS | Own a part of Murena! Learn more

Commit 59f0ad80 authored by Sergio Aguirre's avatar Sergio Aguirre Committed by Mauro Carvalho Chehab
Browse files

[media] v4l: omap4iss: Add support for OMAP4 camera interface - Core



This adds a very simplistic driver to utilize the CSI2A interface inside
the ISS subsystem in OMAP4, and dump the data to memory.
Check Documentation/video4linux/omap4_camera.txt for details.
This commit adds the driver core, registers definitions and
documentation.

Signed-off-by: default avatarSergio Aguirre <sergio.a.aguirre@gmail.com>
Signed-off-by: default avatarLaurent Pinchart <laurent.pinchart@ideasonboard.com>
Acked-by: default avatarHans Verkuil <hans.verkuil@cisco.com>
Signed-off-by: default avatarMauro Carvalho Chehab <mchehab@redhat.com>
parent 64695905
Loading
Loading
Loading
Loading
+60 −0
Original line number Diff line number Diff line
                              OMAP4 ISS Driver
                              ================

Introduction
------------

The OMAP44XX family of chips contains the Imaging SubSystem (a.k.a. ISS),
Which contains several components that can be categorized in 3 big groups:

- Interfaces (2 Interfaces: CSI2-A & CSI2-B/CCP2)
- ISP (Image Signal Processor)
- SIMCOP (Still Image Coprocessor)

For more information, please look in [1] for latest version of:
	"OMAP4430 Multimedia Device Silicon Revision 2.x"

As of Revision AB, the ISS is described in detail in section 8.

This driver is supporting _only_ the CSI2-A/B interfaces for now.

It makes use of the Media Controller framework [2], and inherited most of the
code from OMAP3 ISP driver (found under drivers/media/platform/omap3isp/*),
except that it doesn't need an IOMMU now for ISS buffers memory mapping.

Supports usage of MMAP buffers only (for now).

Tested platforms
----------------

- OMAP4430SDP, w/ ES2.1 GP & SEVM4430-CAM-V1-0 (Contains IMX060 & OV5640, in
  which only the last one is supported, outputting YUV422 frames).

- TI Blaze MDP, w/ OMAP4430 ES2.2 EMU (Contains 1 IMX060 & 2 OV5650 sensors, in
  which only the OV5650 are supported, outputting RAW10 frames).

- PandaBoard, Rev. A2, w/ OMAP4430 ES2.1 GP & OV adapter board, tested with
  following sensors:
  * OV5640
  * OV5650

- Tested on mainline kernel:

	http://git.kernel.org/?p=linux/kernel/git/torvalds/linux-2.6.git;a=summary

  Tag: v3.3 (commit c16fa4f2ad19908a47c63d8fa436a1178438c7e7)

File list
---------
drivers/staging/media/omap4iss/
include/media/omap4iss.h

References
----------

[1] http://focus.ti.com/general/docs/wtbu/wtbudocumentcenter.tsp?navigationId=12037&templateId=6123#62
[2] http://lwn.net/Articles/420485/
[3] http://www.spinics.net/lists/linux-media/msg44370.html
--
Author: Sergio Aguirre <sergio.a.aguirre@gmail.com>
Copyright (C) 2012, Texas Instruments
+1477 −0

File added.

Preview size limit exceeded, changes collapsed.

+153 −0
Original line number Diff line number Diff line
/*
 * TI OMAP4 ISS V4L2 Driver
 *
 * Copyright (C) 2012 Texas Instruments.
 *
 * Author: Sergio Aguirre <sergio.a.aguirre@gmail.com>
 *
 * This program is free software; you can redistribute it and/or modify
 * it under the terms of the GNU General Public License as published by
 * the Free Software Foundation; either version 2 of the License, or
 * (at your option) any later version.
 */

#ifndef _OMAP4_ISS_H_
#define _OMAP4_ISS_H_

#include <media/v4l2-device.h>
#include <linux/device.h>
#include <linux/io.h>
#include <linux/platform_device.h>
#include <linux/wait.h>

#include <media/omap4iss.h>

#include "iss_regs.h"
#include "iss_csiphy.h"
#include "iss_csi2.h"
#include "iss_ipipeif.h"
#include "iss_ipipe.h"
#include "iss_resizer.h"

#define to_iss_device(ptr_module)				\
	container_of(ptr_module, struct iss_device, ptr_module)
#define to_device(ptr_module)						\
	(to_iss_device(ptr_module)->dev)

enum iss_mem_resources {
	OMAP4_ISS_MEM_TOP,
	OMAP4_ISS_MEM_CSI2_A_REGS1,
	OMAP4_ISS_MEM_CAMERARX_CORE1,
	OMAP4_ISS_MEM_CSI2_B_REGS1,
	OMAP4_ISS_MEM_CAMERARX_CORE2,
	OMAP4_ISS_MEM_BTE,
	OMAP4_ISS_MEM_ISP_SYS1,
	OMAP4_ISS_MEM_ISP_RESIZER,
	OMAP4_ISS_MEM_ISP_IPIPE,
	OMAP4_ISS_MEM_ISP_ISIF,
	OMAP4_ISS_MEM_ISP_IPIPEIF,
	OMAP4_ISS_MEM_LAST,
};

enum iss_subclk_resource {
	OMAP4_ISS_SUBCLK_SIMCOP		= (1 << 0),
	OMAP4_ISS_SUBCLK_ISP		= (1 << 1),
	OMAP4_ISS_SUBCLK_CSI2_A		= (1 << 2),
	OMAP4_ISS_SUBCLK_CSI2_B		= (1 << 3),
	OMAP4_ISS_SUBCLK_CCP2		= (1 << 4),
};

enum iss_isp_subclk_resource {
	OMAP4_ISS_ISP_SUBCLK_BL		= (1 << 0),
	OMAP4_ISS_ISP_SUBCLK_ISIF	= (1 << 1),
	OMAP4_ISS_ISP_SUBCLK_H3A	= (1 << 2),
	OMAP4_ISS_ISP_SUBCLK_RSZ	= (1 << 3),
	OMAP4_ISS_ISP_SUBCLK_IPIPE	= (1 << 4),
	OMAP4_ISS_ISP_SUBCLK_IPIPEIF	= (1 << 5),
};

/*
 * struct iss_reg - Structure for ISS register values.
 * @reg: 32-bit Register address.
 * @val: 32-bit Register value.
 */
struct iss_reg {
	enum iss_mem_resources mmio_range;
	u32 reg;
	u32 val;
};

struct iss_device {
	struct v4l2_device v4l2_dev;
	struct media_device media_dev;
	struct device *dev;
	u32 revision;

	/* platform HW resources */
	struct iss_platform_data *pdata;
	unsigned int irq_num;

	struct resource *res[OMAP4_ISS_MEM_LAST];
	void __iomem *regs[OMAP4_ISS_MEM_LAST];

	u64 raw_dmamask;

	struct mutex iss_mutex;	/* For handling ref_count field */
	int has_context;
	int ref_count;

	struct clk *iss_fck;
	struct clk *iss_ctrlclk;

	/* ISS modules */
	struct iss_csi2_device csi2a;
	struct iss_csi2_device csi2b;
	struct iss_csiphy csiphy1;
	struct iss_csiphy csiphy2;
	struct iss_ipipeif_device ipipeif;
	struct iss_ipipe_device ipipe;
	struct iss_resizer_device resizer;

	unsigned int subclk_resources;
	unsigned int isp_subclk_resources;
};

#define v4l2_dev_to_iss_device(dev) \
	container_of(dev, struct iss_device, v4l2_dev)

int omap4iss_get_external_info(struct iss_pipeline *pipe,
			       struct media_link *link);

int omap4iss_module_sync_idle(struct media_entity *me, wait_queue_head_t *wait,
			      atomic_t *stopping);

int omap4iss_module_sync_is_stopping(wait_queue_head_t *wait,
				     atomic_t *stopping);

int omap4iss_pipeline_set_stream(struct iss_pipeline *pipe,
				 enum iss_pipeline_stream_state state);

void omap4iss_configure_bridge(struct iss_device *iss,
			       enum ipipeif_input_entity input);

struct iss_device *omap4iss_get(struct iss_device *iss);
void omap4iss_put(struct iss_device *iss);
int omap4iss_subclk_enable(struct iss_device *iss,
			   enum iss_subclk_resource res);
int omap4iss_subclk_disable(struct iss_device *iss,
			    enum iss_subclk_resource res);
int omap4iss_isp_subclk_enable(struct iss_device *iss,
				enum iss_isp_subclk_resource res);
int omap4iss_isp_subclk_disable(struct iss_device *iss,
				enum iss_isp_subclk_resource res);

void omap4iss_isp_enable_interrupts(struct iss_device *iss);
void omap4iss_isp_disable_interrupts(struct iss_device *iss);

int omap4iss_pipeline_pm_use(struct media_entity *entity, int use);

int omap4iss_register_entities(struct platform_device *pdev,
			       struct v4l2_device *v4l2_dev);
void omap4iss_unregister_entities(struct platform_device *pdev);

#endif /* _OMAP4_ISS_H_ */
+883 −0

File added.

Preview size limit exceeded, changes collapsed.

+65 −0
Original line number Diff line number Diff line
#ifndef ARCH_ARM_PLAT_OMAP4_ISS_H
#define ARCH_ARM_PLAT_OMAP4_ISS_H

#include <linux/i2c.h>

struct iss_device;

enum iss_interface_type {
	ISS_INTERFACE_CSI2A_PHY1,
	ISS_INTERFACE_CSI2B_PHY2,
};

/**
 * struct iss_csiphy_lane: CSI2 lane position and polarity
 * @pos: position of the lane
 * @pol: polarity of the lane
 */
struct iss_csiphy_lane {
	u8 pos;
	u8 pol;
};

#define ISS_CSIPHY1_NUM_DATA_LANES	4
#define ISS_CSIPHY2_NUM_DATA_LANES	1

/**
 * struct iss_csiphy_lanes_cfg - CSI2 lane configuration
 * @data: Configuration of one or two data lanes
 * @clk: Clock lane configuration
 */
struct iss_csiphy_lanes_cfg {
	struct iss_csiphy_lane data[ISS_CSIPHY1_NUM_DATA_LANES];
	struct iss_csiphy_lane clk;
};

/**
 * struct iss_csi2_platform_data - CSI2 interface platform data
 * @crc: Enable the cyclic redundancy check
 * @vpclk_div: Video port output clock control
 */
struct iss_csi2_platform_data {
	unsigned crc:1;
	unsigned vpclk_div:2;
	struct iss_csiphy_lanes_cfg lanecfg;
};

struct iss_subdev_i2c_board_info {
	struct i2c_board_info *board_info;
	int i2c_adapter_id;
};

struct iss_v4l2_subdevs_group {
	struct iss_subdev_i2c_board_info *subdevs;
	enum iss_interface_type interface;
	union {
		struct iss_csi2_platform_data csi2;
	} bus; /* gcc < 4.6.0 chokes on anonymous union initializers */
};

struct iss_platform_data {
	struct iss_v4l2_subdevs_group *subdevs;
	void (*set_constraints)(struct iss_device *iss, bool enable);
};

#endif