mirror of
git://projects.qi-hardware.com/openwrt-xburst.git
synced 2024-12-01 07:43:09 +02:00
a95f9f92e2
git-svn-id: svn://svn.openwrt.org/openwrt/trunk@13619 3c298f89-4303-0410-b956-a3cf2f4a3e73
1691 lines
55 KiB
Diff
Executable File
1691 lines
55 KiB
Diff
Executable File
From 0bd2a8e00d4a1814d0a9d8206d52717e3f538b68 Mon Sep 17 00:00:00 2001
|
|
From: Andy Green <andy@opennoko.com>
|
|
Date: Fri, 25 Jul 2008 23:06:10 +0100
|
|
Subject: [PATCH] uplevel-samsung-camera-unit.patch
|
|
|
|
Update this old code to clk API, I2C changes, official GPIO API
|
|
various struct changes, explicit readl() writel(), DMA API changes.
|
|
Still not ready for actual use (eg, I2C) but a LOT closer.
|
|
|
|
Compiles on 2.6.24 without errors or warnings now.
|
|
|
|
Use CONFIG_S3C2440_CAMERA=y in .config
|
|
|
|
Signed-off-by: Andy Green <andy@openmoko.com>
|
|
---
|
|
arch/arm/mach-s3c2440/Kconfig | 5 +-
|
|
arch/arm/mach-s3c2440/Makefile | 9 +-
|
|
arch/arm/mach-s3c2440/camera/Makefile | 1 -
|
|
arch/arm/mach-s3c2440/camera/cam_reg.h | 92 +++--
|
|
arch/arm/mach-s3c2440/camera/camif.c | 633 +++++++++++++++------------
|
|
arch/arm/mach-s3c2440/camera/camif_fsm.c | 5 +
|
|
arch/arm/mach-s3c2440/camera/imgsensor.c | 43 +-
|
|
arch/arm/mach-s3c2440/camera/qt-driver.c | 5 +-
|
|
arch/arm/mach-s3c2440/camera/video-driver.c | 87 +++--
|
|
arch/arm/mach-s3c2440/camera/videodev.c | 24 +-
|
|
arch/arm/mach-s3c2440/camera/videodev.h | 16 +-
|
|
11 files changed, 516 insertions(+), 404 deletions(-)
|
|
|
|
diff --git a/arch/arm/mach-s3c2440/Kconfig b/arch/arm/mach-s3c2440/Kconfig
|
|
index e042965..20dd2c5 100644
|
|
--- a/arch/arm/mach-s3c2440/Kconfig
|
|
+++ b/arch/arm/mach-s3c2440/Kconfig
|
|
@@ -30,9 +30,6 @@ config S3C2440_C_FIQ
|
|
Support for S3C2440 FIQ support in C -- see
|
|
./arch/arm/macs3c2440/fiq_c_isr.c
|
|
|
|
-source "arch/arm/mach-s3c2440/camera/Kconfig"
|
|
-
|
|
-
|
|
menu "S3C2440 Machines"
|
|
|
|
config MACH_ANUBIS
|
|
@@ -96,3 +93,5 @@ config NEO1973_GTA02_2440
|
|
of the FIC/Openmoko Neo1973 GTA02 GSM Phone.
|
|
|
|
endmenu
|
|
+
|
|
+#source "arch/arm/mach-s3c2440/camera/Kconfig"
|
|
diff --git a/arch/arm/mach-s3c2440/Makefile b/arch/arm/mach-s3c2440/Makefile
|
|
index e9c6334..964e50b 100644
|
|
--- a/arch/arm/mach-s3c2440/Makefile
|
|
+++ b/arch/arm/mach-s3c2440/Makefile
|
|
@@ -1,4 +1,10 @@
|
|
-obj-y += camera/
|
|
+# arch/arm/mach-s3c2440/Makefile
|
|
+#
|
|
+# Copyright 2007 Simtec Electronics
|
|
+#
|
|
+# Licensed under GPLv2
|
|
+
|
|
+obj-y :=
|
|
obj-m :=
|
|
obj-n :=
|
|
obj- :=
|
|
@@ -17,5 +23,6 @@ obj-$(CONFIG_MACH_RX3715) += mach-rx3715.o
|
|
obj-$(CONFIG_ARCH_S3C2440) += mach-smdk2440.o
|
|
obj-$(CONFIG_MACH_NEXCODER_2440) += mach-nexcoder.o
|
|
obj-$(CONFIG_MACH_AT2440EVB) += mach-at2440evb.o
|
|
+obj-$(CONFIG_MACH_HXD8) += mach-hxd8.o
|
|
obj-$(CONFIG_MACH_NEO1973_GTA02) += mach-gta02.o
|
|
|
|
diff --git a/arch/arm/mach-s3c2440/camera/Makefile b/arch/arm/mach-s3c2440/camera/Makefile
|
|
index a46d3be..9cd6d79 100644
|
|
--- a/arch/arm/mach-s3c2440/camera/Makefile
|
|
+++ b/arch/arm/mach-s3c2440/camera/Makefile
|
|
@@ -1,7 +1,6 @@
|
|
obj-$(CONFIG_S3C2440_CAMERA) += \
|
|
videodev.o \
|
|
imgsensor.o \
|
|
- videodrv.o \
|
|
video-driver.o \
|
|
camif.o \
|
|
camif_fsm.o \
|
|
diff --git a/arch/arm/mach-s3c2440/camera/cam_reg.h b/arch/arm/mach-s3c2440/camera/cam_reg.h
|
|
index 7247a4e..93d59b8 100644
|
|
--- a/arch/arm/mach-s3c2440/camera/cam_reg.h
|
|
+++ b/arch/arm/mach-s3c2440/camera/cam_reg.h
|
|
@@ -7,6 +7,7 @@
|
|
#ifndef __FIMC20_CAMERA_H__
|
|
#define __FIMC20_CAMERA_H__
|
|
|
|
+extern u32 * camregs;
|
|
|
|
#ifdef CONFIG_ARCH_S3C24A0
|
|
#define CAM_BASE_ADD 0x48000000
|
|
@@ -14,10 +15,23 @@
|
|
#define CAM_BASE_ADD 0x4F000000
|
|
#endif
|
|
|
|
+#if ! defined(FExtr)
|
|
+#define UData(Data) ((unsigned long) (Data))
|
|
+#define FExtr(Data, Field) \
|
|
+ ((UData (Data) >> FShft (Field)) & FAlnMsk (Field))
|
|
+#define FInsrt(Value, Field) \
|
|
+ (UData (Value) << FShft (Field))
|
|
+#define FSize(Field) ((Field) >> 16)
|
|
+#define FShft(Field) ((Field) & 0x0000FFFF)
|
|
+#define FMsk(Field) (((UData (1) << FSize (Field)) - 1) << FShft (Field))
|
|
+#define FAlnMsk(Field) ((UData (1) << FSize (Field)) - 1)
|
|
+#define F1stBit(Field) (UData (1) << FShft (Field))
|
|
+#define Fld(Size, Shft) (((Size) << 16) + (Shft))
|
|
+#endif
|
|
|
|
/*
|
|
* CAMERA IP
|
|
- * P-port is used as RGB Capturing device which including scale and crop
|
|
+ * P-port is used as RGB Capturing device which including scale and crop
|
|
* those who want to see(preview ) the image on display needs RGB image.
|
|
*
|
|
* C-port is used as YCbCr(4:2:0, 4:2:2) Capturing device which including the scale and crop
|
|
@@ -25,45 +39,45 @@
|
|
YCBCB format not RGB
|
|
*/
|
|
|
|
-#define CISRCFMT __REG(CAM_BASE_ADD+0x00) // RW Input Source Format
|
|
-#define CIWDOFST __REG(CAM_BASE_ADD+0x04) // Window offset register
|
|
-#define CIGCTRL __REG(CAM_BASE_ADD+0x08) // Global control register
|
|
-#define CICOYSA0 __REG(CAM_BASE_ADD+0x18) // Y 1 st frame start address
|
|
-#define CICOYSA1 __REG(CAM_BASE_ADD+0x1C) // Y 2 nd frame start address
|
|
-#define CICOYSA2 __REG(CAM_BASE_ADD+0x20) // Y 3 rd frame start address
|
|
-#define CICOYSA3 __REG(CAM_BASE_ADD+0x24) // Y 4 th frame start address
|
|
-#define CICOCBSA0 __REG(CAM_BASE_ADD+0x28) // Cb 1 st frame start address
|
|
-#define CICOCBSA1 __REG(CAM_BASE_ADD+0x2C) // Cb 2 nd frame start address
|
|
-#define CICOCBSA2 __REG(CAM_BASE_ADD+0x30) // Cb 3 rd frame start address
|
|
-#define CICOCBSA3 __REG(CAM_BASE_ADD+0x34) // Cb 4 th frame start address
|
|
-#define CICOCRSA0 __REG(CAM_BASE_ADD+0x38) // Cr 1 st frame start address
|
|
-#define CICOCRSA1 __REG(CAM_BASE_ADD+0x3C) // Cr 2 nd frame start address
|
|
-#define CICOCRSA2 __REG(CAM_BASE_ADD+0x40) // Cr 3 rd frame start address
|
|
-#define CICOCRSA3 __REG(CAM_BASE_ADD+0x44) // Cr 4 th frame start address
|
|
-#define CICOTRGFMT __REG(CAM_BASE_ADD+0x48) // Target image format of codec
|
|
-#define CICOCTRL __REG(CAM_BASE_ADD+0x4C) // Codec DMA control related
|
|
-#define CICOSCPRERATIO __REG(CAM_BASE_ADD+0x50) // Codec pre-scaler ratio control
|
|
-#define CICOSCPREDST __REG(CAM_BASE_ADD+0x54) // Codec pre-scaler destination
|
|
-#define CICOSCCTRL __REG(CAM_BASE_ADD+0x58) // Codec main-scaler control
|
|
-#define CICOTAREA __REG(CAM_BASE_ADD+0x5C) // Codec pre-scaler destination
|
|
-#define CICOSTATUS __REG(CAM_BASE_ADD+0x64) // Codec path status
|
|
-#define CIPRCLRSA0 __REG(CAM_BASE_ADD+0x6C) // RGB 1 st frame start address
|
|
-#define CIPRCLRSA1 __REG(CAM_BASE_ADD+0x70) // RGB 2 nd frame start address
|
|
-#define CIPRCLRSA2 __REG(CAM_BASE_ADD+0x74) // RGB 3 rd frame start address
|
|
-#define CIPRCLRSA3 __REG(CAM_BASE_ADD+0x78) // RGB 4 th frame start address
|
|
-#define CIPRTRGFMT __REG(CAM_BASE_ADD+0x7C) // Target image format of preview
|
|
-#define CIPRCTRL __REG(CAM_BASE_ADD+0x80) // Preview DMA control related
|
|
-#define CIPRSCPRERATIO __REG(CAM_BASE_ADD+0x84) // Preview pre-scaler ratio control
|
|
-#define CIPRSCPREDST __REG(CAM_BASE_ADD+0x88) // Preview pre-scaler destination
|
|
-#define CIPRSCCTRL __REG(CAM_BASE_ADD+0x8C) // Preview main-scaler control
|
|
-#define CIPRTAREA __REG(CAM_BASE_ADD+0x90) // Preview pre-scaler destination
|
|
-#define CIPRSTATUS __REG(CAM_BASE_ADD+0x98) // Preview path status
|
|
-#define CIIMGCPT __REG(CAM_BASE_ADD+0xA0) // Image capture enable command
|
|
-
|
|
-#define CICOYSA(__x) __REG(CAM_BASE_ADD+0x18 + (__x)*4 )
|
|
-#define CICOCBSA(__x) __REG(CAM_BASE_ADD+0x28 + (__x)*4 )
|
|
-#define CICOCRSA(__x) __REG(CAM_BASE_ADD+0x38 + (__x)*4 )
|
|
-#define CIPRCLRSA(__x) __REG(CAM_BASE_ADD+0x6C + (__x)*4 )
|
|
+#define S3C2440_CAM_REG_CISRCFMT (0x00) // RW Input Source Format
|
|
+#define S3C2440_CAM_REG_CIWDOFST (0x04) // Window offset register
|
|
+#define S3C2440_CAM_REG_CIGCTRL (0x08) // Global control register
|
|
+#define S3C2440_CAM_REG_CICOYSA0 (0x18) // Y 1 st frame start ads
|
|
+#define S3C2440_CAM_REG_CICOYSA1 (0x1C) // Y 2 nd frame start ads
|
|
+#define S3C2440_CAM_REG_CICOYSA2 (0x20) // Y 3 rd frame start ads
|
|
+#define S3C2440_CAM_REG_CICOYSA3 (0x24) // Y 4 th frame start ads
|
|
+#define S3C2440_CAM_REG_CICOCBSA0 (0x28) // Cb 1 st frame start ads
|
|
+#define S3C2440_CAM_REG_CICOCBSA1 (0x2C) // Cb 2 nd frame start ads
|
|
+#define S3C2440_CAM_REG_CICOCBSA2 (0x30) // Cb 3 rd frame start ads
|
|
+#define S3C2440_CAM_REG_CICOCBSA3 (0x34) // Cb 4 th frame start ads
|
|
+#define S3C2440_CAM_REG_CICOCRSA0 (0x38) // Cr 1 st frame start ads
|
|
+#define S3C2440_CAM_REG_CICOCRSA1 (0x3C) // Cr 2 nd frame start ads
|
|
+#define S3C2440_CAM_REG_CICOCRSA2 (0x40) // Cr 3 rd frame start ads
|
|
+#define S3C2440_CAM_REG_CICOCRSA3 (0x44) // Cr 4 th frame start ads
|
|
+#define S3C2440_CAM_REG_CICOTRGFMT (0x48) // Target img format of codec
|
|
+#define S3C2440_CAM_REG_CICOCTRL (0x4C) // Codec DMA control related
|
|
+#define S3C2440_CAM_REG_CICOSCPRERATIO (0x50) // Codec pre-scaler ratio
|
|
+#define S3C2440_CAM_REG_CICOSCPREDST (0x54) // Codec pre-scaler dest
|
|
+#define S3C2440_CAM_REG_CICOSCCTRL (0x58) // Codec main-scaler control
|
|
+#define S3C2440_CAM_REG_CICOTAREA (0x5C) // Codec pre-scaler dest
|
|
+#define S3C2440_CAM_REG_CICOSTATUS (0x64) // Codec path status
|
|
+#define S3C2440_CAM_REG_CIPRCLRSA0 (0x6C) // RGB 1 st frame start ads
|
|
+#define S3C2440_CAM_REG_CIPRCLRSA1 (0x70) // RGB 2 nd frame start ads
|
|
+#define S3C2440_CAM_REG_CIPRCLRSA2 (0x74) // RGB 3 rd frame start ads
|
|
+#define S3C2440_CAM_REG_CIPRCLRSA3 (0x78) // RGB 4 th frame start ads
|
|
+#define S3C2440_CAM_REG_CIPRTRGFMT (0x7C) // Target img fmt of preview
|
|
+#define S3C2440_CAM_REG_CIPRCTRL (0x80) // Preview DMA ctl related
|
|
+#define S3C2440_CAM_REG_CIPRSCPRERATIO (0x84) // Preview pre-scaler ratio
|
|
+#define S3C2440_CAM_REG_CIPRSCPREDST (0x88) // Preview pre-scaler dest
|
|
+#define S3C2440_CAM_REG_CIPRSCCTRL (0x8C) // Preview main-scaler ctl
|
|
+#define S3C2440_CAM_REG_CIPRTAREA (0x90) // Preview pre-scaler dest
|
|
+#define S3C2440_CAM_REG_CIPRSTATUS (0x98) // Preview path status
|
|
+#define S3C2440_CAM_REG_CIIMGCPT (0xA0) // Image capture enable cmd
|
|
+
|
|
+#define S3C2440_CAM_REG_CICOYSA(__x) (0x18 + (__x)*4 )
|
|
+#define S3C2440_CAM_REG_CICOCBSA(__x) (0x28 + (__x)*4 )
|
|
+#define S3C2440_CAM_REG_CICOCRSA(__x) (0x38 + (__x)*4 )
|
|
+#define S3C2440_CAM_REG_CIPRCLRSA(__x) (0x6C + (__x)*4 )
|
|
|
|
/* CISRCFMT BitField */
|
|
#define SRCFMT_ITU601 BIT31
|
|
diff --git a/arch/arm/mach-s3c2440/camera/camif.c b/arch/arm/mach-s3c2440/camera/camif.c
|
|
index 36d4ccc..2e97e21 100644
|
|
--- a/arch/arm/mach-s3c2440/camera/camif.c
|
|
+++ b/arch/arm/mach-s3c2440/camera/camif.c
|
|
@@ -7,14 +7,11 @@
|
|
* for more details.
|
|
*/
|
|
|
|
-#include <linux/config.h>
|
|
#include <linux/module.h>
|
|
#include <linux/kernel.h>
|
|
#include <linux/init.h>
|
|
#include <linux/sched.h>
|
|
#include <linux/irq.h>
|
|
-#include <linux/tqueue.h>
|
|
-#include <linux/locks.h>
|
|
#include <linux/completion.h>
|
|
#include <linux/delay.h>
|
|
#include <linux/slab.h>
|
|
@@ -26,28 +23,29 @@
|
|
#include <asm/semaphore.h>
|
|
#include <asm/hardware.h>
|
|
#include <asm/uaccess.h>
|
|
+#include <linux/device.h>
|
|
+#include <linux/dma-mapping.h>
|
|
+#include <linux/clk.h>
|
|
|
|
#ifdef CONFIG_ARCH_S3C24A0A
|
|
#include <asm/arch/S3C24A0.h>
|
|
#include <asm/arch/clocks.h>
|
|
#else
|
|
-#include <asm/arch/S3C2440.h>
|
|
-#include <asm/arch/clocks.h>
|
|
+#include <asm/arch/regs-gpio.h>
|
|
+#include <asm/arch/regs-gpioj.h>
|
|
+#include <asm/arch/regs-irq.h>
|
|
#endif
|
|
|
|
#include "cam_reg.h"
|
|
//#define SW_DEBUG
|
|
+#define CONFIG_VIDEO_V4L1_COMPAT
|
|
+#include <linux/videodev.h>
|
|
#include "camif.h"
|
|
-#include "videodev.h"
|
|
#include "miscdevice.h"
|
|
|
|
-
|
|
static int camif_dma_burst(camif_cfg_t *);
|
|
static int camif_scaler(camif_cfg_t *);
|
|
|
|
-static const char *camif_version =
|
|
- "$Id: camif.c,v 1.10 2004/06/04 04:24:14 swlee Exp $";
|
|
-
|
|
/* For SXGA Image */
|
|
#define RESERVE_MEM 15*1024*1024
|
|
#define YUV_MEM 10*1024*1024
|
|
@@ -66,11 +64,13 @@ static int camif_malloc(camif_cfg_t *cfg)
|
|
t_size = t_size *cfg->pp_num;
|
|
|
|
#ifndef SAMSUNG_SXGA_CAM
|
|
- cfg->pp_virt_buf = consistent_alloc(GFP_KERNEL, t_size, &cfg->pp_phys_buf);
|
|
+ cfg->pp_virt_buf = dma_alloc_coherent(cfg->v->dev,
|
|
+ t_size, &cfg->pp_phys_buf,
|
|
+ GFP_KERNEL);
|
|
#else
|
|
printk(KERN_INFO "Reserving High RAM Addresses \n");
|
|
cfg->pp_phys_buf = PHYS_OFFSET + (MEM_SIZE - RESERVE_MEM);
|
|
- cfg->pp_virt_buf = ioremap_nocache(cfg->pp_phys_buf,YUV_MEM);
|
|
+ cfg->pp_virt_buf = ioremap_nocache(cfg->pp_phys_buf, YUV_MEM);
|
|
#endif
|
|
|
|
if ( !cfg->pp_virt_buf ) {
|
|
@@ -90,7 +90,9 @@ static int camif_malloc(camif_cfg_t *cfg)
|
|
}
|
|
t_size = t_size * cfg->pp_num;
|
|
#ifndef SAMSUNG_SXGA_CAM
|
|
- cfg->pp_virt_buf = consistent_alloc(GFP_KERNEL, t_size, &cfg->pp_phys_buf);
|
|
+ cfg->pp_virt_buf = dma_alloc_coherent(cfg->v->dev,
|
|
+ t_size, &cfg->pp_phys_buf,
|
|
+ GFP_KERNEL);
|
|
#else
|
|
printk(KERN_INFO "Reserving High RAM Addresses \n");
|
|
cfg->pp_phys_buf = PHYS_OFFSET + (MEM_SIZE - RESERVE_MEM ) + YUV_MEM;
|
|
@@ -112,7 +114,8 @@ static int camif_demalloc(camif_cfg_t *cfg)
|
|
{
|
|
#ifndef SAMSUNG_SXGA_CAM
|
|
if ( cfg->pp_virt_buf ) {
|
|
- consistent_free(cfg->pp_virt_buf,cfg->pp_totalsize,cfg->pp_phys_buf);
|
|
+ dma_free_coherent(cfg->v->dev, cfg->pp_totalsize,
|
|
+ cfg->pp_virt_buf, cfg->pp_phys_buf);
|
|
cfg->pp_virt_buf = 0;
|
|
}
|
|
#else
|
|
@@ -131,13 +134,14 @@ int camif_g_frame_num(camif_cfg_t *cfg)
|
|
int index = 0;
|
|
|
|
if (cfg->dma_type & CAMIF_CODEC ) {
|
|
- index = FRAME_CNT(CICOSTATUS);
|
|
+ index = FRAME_CNT(readl(camregs + S3C2440_CAM_REG_CICOSTATUS));
|
|
DPRINTK("CAMIF_CODEC frame %d \n", index);
|
|
}
|
|
else {
|
|
assert(cfg->dma_type & CAMIF_PREVIEW );
|
|
- index = FRAME_CNT(CIPRSTATUS);
|
|
- DPRINTK("CAMIF_PREVIEW frame %d 0x%08X \n", index, CIPRSTATUS);
|
|
+ index = FRAME_CNT(readl(camregs + S3C2440_CAM_REG_CIPRSTATUS));
|
|
+ DPRINTK("CAMIF_PREVIEW frame %d 0x%08X \n", index,
|
|
+ readl(camregs + S3C2440_CAM_REG_CIPRSTATUS));
|
|
}
|
|
cfg->now_frame_num = (index + 2) % 4; /* When 4 PingPong */
|
|
return index; /* meaningless */
|
|
@@ -148,60 +152,59 @@ static int camif_pp_codec(camif_cfg_t *cfg)
|
|
u32 i, c_size; /* Cb,Cr size */
|
|
u32 one_p_size;
|
|
u32 daon = cfg->target_x * cfg->target_y;
|
|
- if (cfg->fmt & CAMIF_OUT_YCBCR420) {
|
|
- c_size = daon /4;
|
|
- }
|
|
+ if (cfg->fmt & CAMIF_OUT_YCBCR420)
|
|
+ c_size = daon / 4;
|
|
else {
|
|
assert(cfg->fmt & CAMIF_OUT_YCBCR422);
|
|
- c_size = daon /2;
|
|
+ c_size = daon / 2;
|
|
}
|
|
switch ( cfg->pp_num ) {
|
|
- case 1 :
|
|
- for ( i =0 ; i < 4; i=i+1) {
|
|
- cfg->img_buf[i].virt_y = cfg->pp_virt_buf;
|
|
- cfg->img_buf[i].phys_y = cfg->pp_phys_buf;
|
|
- cfg->img_buf[i].virt_cb = cfg->pp_virt_buf + daon;
|
|
- cfg->img_buf[i].phys_cb = cfg->pp_phys_buf + daon;
|
|
- cfg->img_buf[i].virt_cr = cfg->pp_virt_buf + daon + c_size;
|
|
- cfg->img_buf[i].phys_cr = cfg->pp_phys_buf + daon + c_size;
|
|
- CICOYSA(i) = cfg->img_buf[i].phys_y;
|
|
- CICOCBSA(i) = cfg->img_buf[i].phys_cb;
|
|
- CICOCRSA(i) = cfg->img_buf[i].phys_cr;
|
|
- }
|
|
- break;
|
|
- case 2:
|
|
+ case 1 :
|
|
+ for (i =0 ; i < 4; i++) {
|
|
+ cfg->img_buf[i].virt_y = cfg->pp_virt_buf;
|
|
+ cfg->img_buf[i].phys_y = cfg->pp_phys_buf;
|
|
+ cfg->img_buf[i].virt_cb = cfg->pp_virt_buf + daon;
|
|
+ cfg->img_buf[i].phys_cb = cfg->pp_phys_buf + daon;
|
|
+ cfg->img_buf[i].virt_cr = cfg->pp_virt_buf + daon + c_size;
|
|
+ cfg->img_buf[i].phys_cr = cfg->pp_phys_buf + daon + c_size;
|
|
+ writel(cfg->img_buf[i].phys_y, camregs + S3C2440_CAM_REG_CICOYSA(i));
|
|
+ writel(cfg->img_buf[i].phys_cb, camregs + S3C2440_CAM_REG_CICOCBSA(i));
|
|
+ writel(cfg->img_buf[i].phys_cr, camregs + S3C2440_CAM_REG_CICOCRSA(i));
|
|
+ }
|
|
+ break;
|
|
+ case 2:
|
|
#define TRY (( i%2 ) ? 1 :0)
|
|
- one_p_size = daon + 2*c_size;
|
|
- for (i = 0; i < 4 ; i++) {
|
|
- cfg->img_buf[i].virt_y = cfg->pp_virt_buf + TRY * one_p_size;
|
|
- cfg->img_buf[i].phys_y = cfg->pp_phys_buf + TRY * one_p_size;
|
|
- cfg->img_buf[i].virt_cb = cfg->pp_virt_buf + daon + TRY * one_p_size;
|
|
- cfg->img_buf[i].phys_cb = cfg->pp_phys_buf + daon + TRY * one_p_size;
|
|
- cfg->img_buf[i].virt_cr = cfg->pp_virt_buf + daon + c_size + TRY * one_p_size;
|
|
- cfg->img_buf[i].phys_cr = cfg->pp_phys_buf + daon + c_size + TRY * one_p_size;
|
|
- CICOYSA(i) = cfg->img_buf[i].phys_y;
|
|
- CICOCBSA(i) = cfg->img_buf[i].phys_cb;
|
|
- CICOCRSA(i) = cfg->img_buf[i].phys_cr;
|
|
- }
|
|
- break;
|
|
- case 4:
|
|
- one_p_size = daon + 2*c_size;
|
|
- for (i = 0; i < 4 ; i++) {
|
|
- cfg->img_buf[i].virt_y = cfg->pp_virt_buf + i * one_p_size;
|
|
- cfg->img_buf[i].phys_y = cfg->pp_phys_buf + i * one_p_size;
|
|
- cfg->img_buf[i].virt_cb = cfg->pp_virt_buf + daon + i * one_p_size;
|
|
- cfg->img_buf[i].phys_cb = cfg->pp_phys_buf + daon + i * one_p_size;
|
|
- cfg->img_buf[i].virt_cr = cfg->pp_virt_buf + daon + c_size + i * one_p_size;
|
|
- cfg->img_buf[i].phys_cr = cfg->pp_phys_buf + daon + c_size + i * one_p_size;
|
|
- CICOYSA(i) = cfg->img_buf[i].phys_y;
|
|
- CICOCBSA(i) = cfg->img_buf[i].phys_cb;
|
|
- CICOCRSA(i) = cfg->img_buf[i].phys_cr;
|
|
- }
|
|
- break;
|
|
- default:
|
|
- printk("Invalid PingPong Number %d \n",cfg->pp_num);
|
|
- panic("halt\n");
|
|
- }
|
|
+ one_p_size = daon + 2*c_size;
|
|
+ for (i = 0; i < 4 ; i++) {
|
|
+ cfg->img_buf[i].virt_y = cfg->pp_virt_buf + TRY * one_p_size;
|
|
+ cfg->img_buf[i].phys_y = cfg->pp_phys_buf + TRY * one_p_size;
|
|
+ cfg->img_buf[i].virt_cb = cfg->pp_virt_buf + daon + TRY * one_p_size;
|
|
+ cfg->img_buf[i].phys_cb = cfg->pp_phys_buf + daon + TRY * one_p_size;
|
|
+ cfg->img_buf[i].virt_cr = cfg->pp_virt_buf + daon + c_size + TRY * one_p_size;
|
|
+ cfg->img_buf[i].phys_cr = cfg->pp_phys_buf + daon + c_size + TRY * one_p_size;
|
|
+ writel(cfg->img_buf[i].phys_y, camregs + S3C2440_CAM_REG_CICOYSA(i));
|
|
+ writel(cfg->img_buf[i].phys_cb, camregs + S3C2440_CAM_REG_CICOCBSA(i));
|
|
+ writel(cfg->img_buf[i].phys_cr, camregs + S3C2440_CAM_REG_CICOCRSA(i));
|
|
+ }
|
|
+ break;
|
|
+ case 4:
|
|
+ one_p_size = daon + 2*c_size;
|
|
+ for (i = 0; i < 4 ; i++) {
|
|
+ cfg->img_buf[i].virt_y = cfg->pp_virt_buf + i * one_p_size;
|
|
+ cfg->img_buf[i].phys_y = cfg->pp_phys_buf + i * one_p_size;
|
|
+ cfg->img_buf[i].virt_cb = cfg->pp_virt_buf + daon + i * one_p_size;
|
|
+ cfg->img_buf[i].phys_cb = cfg->pp_phys_buf + daon + i * one_p_size;
|
|
+ cfg->img_buf[i].virt_cr = cfg->pp_virt_buf + daon + c_size + i * one_p_size;
|
|
+ cfg->img_buf[i].phys_cr = cfg->pp_phys_buf + daon + c_size + i * one_p_size;
|
|
+ writel(cfg->img_buf[i].phys_y, camregs + S3C2440_CAM_REG_CICOYSA(i));
|
|
+ writel(cfg->img_buf[i].phys_cb, camregs + S3C2440_CAM_REG_CICOCBSA(i));
|
|
+ writel(cfg->img_buf[i].phys_cr, camregs + S3C2440_CAM_REG_CICOCRSA(i));
|
|
+ }
|
|
+ break;
|
|
+ default:
|
|
+ printk("Invalid PingPong Number %d \n",cfg->pp_num);
|
|
+ panic("halt\n");
|
|
+}
|
|
return 0;
|
|
}
|
|
|
|
@@ -222,21 +225,21 @@ static int camif_pp_preview(camif_cfg_t *cfg)
|
|
for ( i = 0; i < 4 ; i++ ) {
|
|
cfg->img_buf[i].virt_rgb = cfg->pp_virt_buf ;
|
|
cfg->img_buf[i].phys_rgb = cfg->pp_phys_buf ;
|
|
- CIPRCLRSA(i) = cfg->img_buf[i].phys_rgb;
|
|
+ writel(cfg->img_buf[i].phys_rgb, camregs + S3C2440_CAM_REG_CICOCRSA(i));
|
|
}
|
|
break;
|
|
case 2:
|
|
for ( i = 0; i < 4 ; i++) {
|
|
cfg->img_buf[i].virt_rgb = cfg->pp_virt_buf + TRY * daon;
|
|
cfg->img_buf[i].phys_rgb = cfg->pp_phys_buf + TRY * daon;
|
|
- CIPRCLRSA(i) = cfg->img_buf[i].phys_rgb;
|
|
+ writel(cfg->img_buf[i].phys_rgb, camregs + S3C2440_CAM_REG_CICOCRSA(i));
|
|
}
|
|
break;
|
|
case 4:
|
|
for ( i = 0; i < 4 ; i++) {
|
|
cfg->img_buf[i].virt_rgb = cfg->pp_virt_buf + i * daon;
|
|
cfg->img_buf[i].phys_rgb = cfg->pp_phys_buf + i * daon;
|
|
- CIPRCLRSA(i) = cfg->img_buf[i].phys_rgb;
|
|
+ writel(cfg->img_buf[i].phys_rgb, camregs + S3C2440_CAM_REG_CICOCRSA(i));
|
|
}
|
|
break;
|
|
default:
|
|
@@ -308,7 +311,7 @@ static int camif_source_fmt(camif_gc_t *gc)
|
|
cmd |= SOURCE_HSIZE(gc->source_x)| SOURCE_VSIZE(gc->source_y);
|
|
/* Order422 */
|
|
cmd |= gc->order422;
|
|
- CISRCFMT = cmd;
|
|
+ writel(cmd, camregs + S3C2440_CAM_REG_CISRCFMT);
|
|
|
|
return 0 ;
|
|
}
|
|
@@ -331,33 +334,24 @@ static int camif_target_fmt(camif_cfg_t *cfg)
|
|
assert(cfg->fmt & CAMIF_OUT_YCBCR422);
|
|
cmd |= OUT_YCBCR422|IN_YCBCR422;
|
|
}
|
|
- CICOTRGFMT = cmd | cfg->flip;
|
|
- }
|
|
- else {
|
|
+ writel(cmd | cfg->flip, camregs + S3C2440_CAM_REG_CICOTRGFMT);
|
|
+
|
|
+ } else {
|
|
assert(cfg->dma_type & CAMIF_PREVIEW);
|
|
- CIPRTRGFMT =
|
|
- TARGET_HSIZE(cfg->target_x)|TARGET_VSIZE(cfg->target_y)|cfg->flip;
|
|
+ writel(TARGET_HSIZE(cfg->target_x)|TARGET_VSIZE(cfg->target_y)|cfg->flip,
|
|
+ camregs + S3C2440_CAM_REG_CIPRTRGFMT);
|
|
}
|
|
return 0;
|
|
}
|
|
|
|
void camif_change_flip(camif_cfg_t *cfg)
|
|
{
|
|
- u32 cmd = 0;
|
|
+ u32 cmd = readl(camregs + S3C2440_CAM_REG_CICOTRGFMT);
|
|
|
|
- if (cfg->dma_type & CAMIF_CODEC ) {
|
|
- /* YCBCR setting */
|
|
- cmd = CICOTRGFMT;
|
|
- cmd &= ~(BIT14|BIT15); /* Clear FLIP Mode */
|
|
- cmd |= cfg->flip;
|
|
- CICOTRGFMT = cmd;
|
|
- }
|
|
- else {
|
|
- cmd = CIPRTRGFMT;
|
|
- cmd &= ~(BIT14|BIT15);
|
|
- cmd |= cfg->flip;
|
|
- CICOTRGFMT = cmd;
|
|
- }
|
|
+ cmd &= ~(BIT14|BIT15);
|
|
+ cmd |= cfg->flip;
|
|
+
|
|
+ writel(cmd, camregs + S3C2440_CAM_REG_CICOTRGFMT);
|
|
}
|
|
|
|
|
|
@@ -373,70 +367,81 @@ int camif_capture_start(camif_cfg_t *cfg)
|
|
u32 n_cmd = 0; /* Next Command */
|
|
|
|
switch(cfg->exec) {
|
|
- case CAMIF_BOTH_DMA_ON:
|
|
- camif_reset(CAMIF_RESET,0); /* Flush Camera Core Buffer */
|
|
- CIPRSCCTRL |= SCALERSTART;
|
|
- CICOSCCTRL |= SCALERSTART;
|
|
- n_cmd = CAMIF_CAP_PREVIEW_ON|CAMIF_CAP_CODEC_ON;
|
|
- break;
|
|
- case CAMIF_DMA_ON:
|
|
- camif_reset(CAMIF_RESET,0); /* Flush Camera Core Buffer */
|
|
- if (cfg->dma_type&CAMIF_CODEC) {
|
|
- CICOSCCTRL |= SCALERSTART;
|
|
- n_cmd = CAMIF_CAP_CODEC_ON;
|
|
- }else {
|
|
- CIPRSCCTRL |= SCALERSTART;
|
|
- n_cmd = CAMIF_CAP_PREVIEW_ON;
|
|
- }
|
|
+ case CAMIF_BOTH_DMA_ON:
|
|
+ camif_reset(CAMIF_RESET, 0); /* Flush Camera Core Buffer */
|
|
+ writel(readl(camregs + S3C2440_CAM_REG_CIPRSCCTRL) |
|
|
+ SCALERSTART, camregs + S3C2440_CAM_REG_CIPRSCCTRL);
|
|
+ writel(readl(camregs + S3C2440_CAM_REG_CICOSCCTRL) |
|
|
+ SCALERSTART, camregs + S3C2440_CAM_REG_CICOSCCTRL);
|
|
+ n_cmd = CAMIF_CAP_PREVIEW_ON | CAMIF_CAP_CODEC_ON;
|
|
+ break;
|
|
+ case CAMIF_DMA_ON:
|
|
+ camif_reset(CAMIF_RESET, 0); /* Flush Camera Core Buffer */
|
|
+ if (cfg->dma_type&CAMIF_CODEC) {
|
|
+ writel(readl(camregs + S3C2440_CAM_REG_CICOSCCTRL) |
|
|
+ SCALERSTART, camregs + S3C2440_CAM_REG_CICOSCCTRL);
|
|
+ n_cmd = CAMIF_CAP_CODEC_ON;
|
|
+ } else {
|
|
+ writel(readl(camregs + S3C2440_CAM_REG_CIPRSCCTRL) |
|
|
+ SCALERSTART, camregs + S3C2440_CAM_REG_CIPRSCCTRL);
|
|
+ n_cmd = CAMIF_CAP_PREVIEW_ON;
|
|
+ }
|
|
|
|
- /* wait until Sync Time expires */
|
|
- /* First settting, to wait VSYNC fall */
|
|
- /* By VESA spec,in 640x480 @60Hz
|
|
- MAX Delay Time is around 64us which "while" has.*/
|
|
- while(VSYNC & CICOSTATUS);
|
|
- break;
|
|
- default:
|
|
- break;
|
|
- }
|
|
- CIIMGCPT = n_cmd|CAMIF_CAP_ON;
|
|
+ /* wait until Sync Time expires */
|
|
+ /* First settting, to wait VSYNC fall */
|
|
+ /* By VESA spec,in 640x480 @60Hz
|
|
+ MAX Delay Time is around 64us which "while" has.*/
|
|
+ while(VSYNC & readl(camregs + S3C2440_CAM_REG_CICOSTATUS));
|
|
+ break;
|
|
+ default:
|
|
+ break;
|
|
+}
|
|
+ writel(n_cmd | CAMIF_CAP_ON, camregs + S3C2440_CAM_REG_CIIMGCPT);
|
|
return 0;
|
|
}
|
|
|
|
|
|
int camif_capture_stop(camif_cfg_t *cfg)
|
|
{
|
|
- u32 n_cmd = CIIMGCPT; /* Next Command */
|
|
+ u32 n_cmd = readl(camregs + S3C2440_CAM_REG_CIIMGCPT); /* Next Command */
|
|
|
|
switch(cfg->exec) {
|
|
- case CAMIF_BOTH_DMA_OFF:
|
|
- CIPRSCCTRL &= ~SCALERSTART;
|
|
- CICOSCCTRL &= ~SCALERSTART;
|
|
- n_cmd = 0;
|
|
- break;
|
|
- case CAMIF_DMA_OFF_L_IRQ: /* fall thru */
|
|
- case CAMIF_DMA_OFF:
|
|
- if (cfg->dma_type&CAMIF_CODEC) {
|
|
- CICOSCCTRL &= ~SCALERSTART;
|
|
- n_cmd &= ~CAMIF_CAP_CODEC_ON;
|
|
- if (!(n_cmd & CAMIF_CAP_PREVIEW_ON))
|
|
- n_cmd = 0;
|
|
- }else {
|
|
- CIPRSCCTRL &= ~SCALERSTART;
|
|
- n_cmd &= ~CAMIF_CAP_PREVIEW_ON;
|
|
- if (!(n_cmd & CAMIF_CAP_CODEC_ON))
|
|
- n_cmd = 0;
|
|
- }
|
|
- break;
|
|
- default:
|
|
- panic("Unexpected \n");
|
|
- }
|
|
- CIIMGCPT = n_cmd;
|
|
- if(cfg->exec == CAMIF_DMA_OFF_L_IRQ) { /* Last IRQ */
|
|
- if (cfg->dma_type & CAMIF_CODEC)
|
|
- CICOCTRL |= LAST_IRQ_EN;
|
|
- else
|
|
- CIPRCTRL |= LAST_IRQ_EN;
|
|
- }
|
|
+ case CAMIF_BOTH_DMA_OFF:
|
|
+ writel(readl(camregs + S3C2440_CAM_REG_CIPRSCCTRL) &
|
|
+ ~SCALERSTART, camregs + S3C2440_CAM_REG_CIPRSCCTRL);
|
|
+ writel(readl(camregs + S3C2440_CAM_REG_CICOSCCTRL) &
|
|
+ ~SCALERSTART, camregs + S3C2440_CAM_REG_CICOSCCTRL);
|
|
+ n_cmd = 0;
|
|
+ break;
|
|
+ case CAMIF_DMA_OFF_L_IRQ: /* fall thru */
|
|
+ case CAMIF_DMA_OFF:
|
|
+ if (cfg->dma_type&CAMIF_CODEC) {
|
|
+ writel(readl(camregs + S3C2440_CAM_REG_CICOSCCTRL) &
|
|
+ ~SCALERSTART, camregs + S3C2440_CAM_REG_CICOSCCTRL);
|
|
+ n_cmd &= ~CAMIF_CAP_CODEC_ON;
|
|
+ if (!(n_cmd & CAMIF_CAP_PREVIEW_ON))
|
|
+ n_cmd = 0;
|
|
+ } else {
|
|
+ writel(readl(camregs + S3C2440_CAM_REG_CIPRSCCTRL) &
|
|
+ ~SCALERSTART, camregs + S3C2440_CAM_REG_CIPRSCCTRL);
|
|
+ n_cmd &= ~CAMIF_CAP_PREVIEW_ON;
|
|
+ if (!(n_cmd & CAMIF_CAP_CODEC_ON))
|
|
+ n_cmd = 0;
|
|
+ }
|
|
+ break;
|
|
+ default:
|
|
+ panic("Unexpected \n");
|
|
+ }
|
|
+ writel(n_cmd, camregs + S3C2440_CAM_REG_CIIMGCPT);
|
|
+
|
|
+ if (cfg->exec == CAMIF_DMA_OFF_L_IRQ) { /* Last IRQ */
|
|
+ if (cfg->dma_type & CAMIF_CODEC)
|
|
+ writel(readl(camregs + S3C2440_CAM_REG_CICOCTRL) |
|
|
+ LAST_IRQ_EN, camregs + S3C2440_CAM_REG_CICOCTRL);
|
|
+ else
|
|
+ writel(readl(camregs + S3C2440_CAM_REG_CIPRCTRL) |
|
|
+ LAST_IRQ_EN, camregs + S3C2440_CAM_REG_CIPRCTRL);
|
|
+ }
|
|
#if 0
|
|
else { /* to make internal state machine of CAMERA stop */
|
|
camif_reset(CAMIF_RESET, 0);
|
|
@@ -449,16 +454,13 @@ int camif_capture_stop(camif_cfg_t *cfg)
|
|
/* LastIRQEn is autoclear */
|
|
void camif_last_irq_en(camif_cfg_t *cfg)
|
|
{
|
|
- if(cfg->exec == CAMIF_BOTH_DMA_ON) {
|
|
- CIPRCTRL |= LAST_IRQ_EN;
|
|
- CICOCTRL |= LAST_IRQ_EN;
|
|
- }
|
|
- else {
|
|
- if (cfg->dma_type & CAMIF_CODEC)
|
|
- CICOCTRL |= LAST_IRQ_EN;
|
|
- else
|
|
- CIPRCTRL |= LAST_IRQ_EN;
|
|
- }
|
|
+ if ((cfg->exec == CAMIF_BOTH_DMA_ON) || (cfg->dma_type & CAMIF_CODEC))
|
|
+ writel(readl(camregs + S3C2440_CAM_REG_CICOCTRL) |
|
|
+ LAST_IRQ_EN, camregs + S3C2440_CAM_REG_CICOCTRL);
|
|
+
|
|
+ if ((cfg->exec == CAMIF_BOTH_DMA_ON) || !(cfg->dma_type & CAMIF_CODEC))
|
|
+ writel(readl(camregs + S3C2440_CAM_REG_CIPRCTRL) |
|
|
+ LAST_IRQ_EN, camregs + S3C2440_CAM_REG_CIPRCTRL);
|
|
}
|
|
|
|
static int
|
|
@@ -502,23 +504,33 @@ int camif_g_fifo_status(camif_cfg_t *cfg)
|
|
u32 reg;
|
|
|
|
if (cfg->dma_type & CAMIF_CODEC) {
|
|
- u32 flag = CO_OVERFLOW_Y|CO_OVERFLOW_CB|CO_OVERFLOW_CR;
|
|
- reg = CICOSTATUS;
|
|
+ u32 flag = CO_OVERFLOW_Y | CO_OVERFLOW_CB | CO_OVERFLOW_CR;
|
|
+ reg = readl(camregs + S3C2440_CAM_REG_CICOSTATUS);
|
|
if (reg & flag) {
|
|
printk("CODEC: FIFO error(0x%08x) and corrected\n",reg);
|
|
/* FIFO Error Count ++ */
|
|
- CIWDOFST |= CO_FIFO_Y|CO_FIFO_CB|CO_FIFO_CR;
|
|
- CIWDOFST &= ~(CO_FIFO_Y|CO_FIFO_CB|CO_FIFO_CR);
|
|
+ writel(readl(camregs + S3C2440_CAM_REG_CIWDOFST) |
|
|
+ CO_FIFO_Y | CO_FIFO_CB | CO_FIFO_CR,
|
|
+ camregs + S3C2440_CAM_REG_CIWDOFST);
|
|
+
|
|
+ writel(readl(camregs + S3C2440_CAM_REG_CIWDOFST) &
|
|
+ ~(CO_FIFO_Y | CO_FIFO_CB | CO_FIFO_CR),
|
|
+ camregs + S3C2440_CAM_REG_CIWDOFST);
|
|
return 1; /* Error */
|
|
}
|
|
}
|
|
if (cfg->dma_type & CAMIF_PREVIEW) {
|
|
- u32 flag = PR_OVERFLOW_CB|PR_OVERFLOW_CR;
|
|
- reg = CIPRSTATUS;
|
|
+ u32 flag = PR_OVERFLOW_CB | PR_OVERFLOW_CR;
|
|
+ reg = readl(camregs + S3C2440_CAM_REG_CIPRSTATUS);
|
|
if (reg & flag) {
|
|
printk("PREVIEW:FIFO error(0x%08x) and corrected\n",reg);
|
|
- CIWDOFST |= PR_FIFO_CB|PR_FIFO_CR;
|
|
- CIWDOFST &= ~(CO_FIFO_Y|CO_FIFO_CB|CO_FIFO_CR);
|
|
+ writel(readl(camregs + S3C2440_CAM_REG_CIWDOFST) |
|
|
+ CO_FIFO_CB | CO_FIFO_CR,
|
|
+ camregs + S3C2440_CAM_REG_CIWDOFST);
|
|
+
|
|
+ writel(readl(camregs + S3C2440_CAM_REG_CIWDOFST) &
|
|
+ ~(CO_FIFO_Y | CO_FIFO_CB | CO_FIFO_CR),
|
|
+ camregs + S3C2440_CAM_REG_CIWDOFST);
|
|
/* FIFO Error Count ++ */
|
|
return 1; /* Error */
|
|
}
|
|
@@ -537,13 +549,16 @@ int camif_win_offset(camif_gc_t *gc )
|
|
u32 v = gc->win_ver_ofst;
|
|
|
|
/*Clear Overflow */
|
|
- CIWDOFST = CO_FIFO_Y|CO_FIFO_CB|CO_FIFO_CR|PR_FIFO_CB|PR_FIFO_CB;
|
|
- CIWDOFST = 0; /* ? Dummy */
|
|
+ writel(CO_FIFO_Y | CO_FIFO_CB | CO_FIFO_CR | PR_FIFO_CB | PR_FIFO_CB,
|
|
+ camregs + S3C2440_CAM_REG_CIWDOFST);
|
|
+ writel(0, camregs + S3C2440_CAM_REG_CIWDOFST);
|
|
+
|
|
if (!h && !v) {
|
|
- CIWDOFST = 0;
|
|
+ writel(0, camregs + S3C2440_CAM_REG_CIWDOFST);
|
|
return 0;
|
|
}
|
|
- CIWDOFST = WINOFEN | WINHOROFST(h) | WINVEROFST(v);
|
|
+
|
|
+ writel(WINOFEN | WINHOROFST(h) | WINVEROFST(v), camregs + S3C2440_CAM_REG_CIWDOFST);
|
|
return 0;
|
|
}
|
|
|
|
@@ -554,7 +569,7 @@ int camif_win_offset(camif_gc_t *gc )
|
|
*/
|
|
static void camif_polarity(camif_gc_t *gc)
|
|
{
|
|
- u32 cmd = CIGCTRL;
|
|
+ u32 cmd = readl(camregs + S3C2440_CAM_REG_CIGCTRL);;
|
|
|
|
cmd = cmd & ~(BIT26|BIT25|BIT24); /* clear polarity */
|
|
if (gc->polarity_pclk)
|
|
@@ -563,7 +578,8 @@ static void camif_polarity(camif_gc_t *gc)
|
|
cmd |= GC_INVPOLVSYNC;
|
|
if (gc->polarity_href)
|
|
cmd |= GC_INVPOLHREF;
|
|
- CIGCTRL |= cmd;
|
|
+ writel(readl(camregs + S3C2440_CAM_REG_CIGCTRL) |
|
|
+ cmd, camregs + S3C2440_CAM_REG_CIGCTRL);
|
|
}
|
|
|
|
|
|
@@ -599,12 +615,13 @@ int camif_dynamic_close(camif_cfg_t *cfg)
|
|
static int camif_target_area(camif_cfg_t *cfg)
|
|
{
|
|
u32 rect = cfg->target_x * cfg->target_y;
|
|
- if (cfg->dma_type & CAMIF_CODEC ) {
|
|
- CICOTAREA = rect;
|
|
- }
|
|
- if (cfg->dma_type & CAMIF_PREVIEW) {
|
|
- CIPRTAREA = rect;
|
|
- }
|
|
+
|
|
+ if (cfg->dma_type & CAMIF_CODEC)
|
|
+ writel(rect, camregs + S3C2440_CAM_REG_CICOTAREA);
|
|
+
|
|
+ if (cfg->dma_type & CAMIF_PREVIEW)
|
|
+ writel(rect, camregs + S3C2440_CAM_REG_CIPRTAREA);
|
|
+
|
|
return 0;
|
|
}
|
|
|
|
@@ -613,40 +630,44 @@ static int inline camif_hw_reg(camif_cfg_t *cfg)
|
|
u32 cmd = 0;
|
|
|
|
if (cfg->dma_type & CAMIF_CODEC) {
|
|
- CICOSCPRERATIO = PRE_SHIFT(cfg->sc.shfactor)
|
|
- |PRE_HRATIO(cfg->sc.prehratio)|PRE_VRATIO(cfg->sc.prevratio);
|
|
- CICOSCPREDST =
|
|
- PRE_DST_WIDTH(cfg->sc.predst_x)|PRE_DST_HEIGHT(cfg->sc.predst_y);
|
|
+ writel(PRE_SHIFT(cfg->sc.shfactor) |
|
|
+ PRE_HRATIO(cfg->sc.prehratio) |
|
|
+ PRE_VRATIO(cfg->sc.prevratio),
|
|
+ camregs + S3C2440_CAM_REG_CICOSCPRERATIO);
|
|
+ writel(PRE_DST_WIDTH(cfg->sc.predst_x) |
|
|
+ PRE_DST_HEIGHT(cfg->sc.predst_y),
|
|
+ camregs + S3C2440_CAM_REG_CICOSCPREDST);
|
|
|
|
/* Differ from Preview */
|
|
if (cfg->sc.scalerbypass)
|
|
cmd |= SCALERBYPASS;
|
|
if (cfg->sc.scaleup_h & cfg->sc.scaleup_v)
|
|
cmd |= BIT30|BIT29;
|
|
- CICOSCCTRL = cmd | MAIN_HRATIO(cfg->sc.mainhratio)
|
|
- |MAIN_VRATIO(cfg->sc.mainvratio);
|
|
+ writel(cmd | MAIN_HRATIO(cfg->sc.mainhratio) |
|
|
+ MAIN_VRATIO(cfg->sc.mainvratio),
|
|
+ camregs + S3C2440_CAM_REG_CICOSCCTRL);
|
|
return 0;
|
|
}
|
|
- else if (cfg->dma_type & CAMIF_PREVIEW) {
|
|
- CIPRSCPRERATIO = PRE_SHIFT(cfg->sc.shfactor)
|
|
- |PRE_HRATIO(cfg->sc.prehratio)|PRE_VRATIO(cfg->sc.prevratio);
|
|
- CIPRSCPREDST =
|
|
- PRE_DST_WIDTH(cfg->sc.predst_x)|PRE_DST_HEIGHT(cfg->sc.predst_y);
|
|
+ if (cfg->dma_type & CAMIF_PREVIEW) {
|
|
+ writel(PRE_SHIFT(cfg->sc.shfactor) |
|
|
+ PRE_HRATIO(cfg->sc.prehratio) |
|
|
+ PRE_VRATIO(cfg->sc.prevratio),
|
|
+ camregs + S3C2440_CAM_REG_CIPRSCPRERATIO);
|
|
+ writel(PRE_DST_WIDTH(cfg->sc.predst_x) |
|
|
+ PRE_DST_HEIGHT(cfg->sc.predst_y),
|
|
+ camregs + S3C2440_CAM_REG_CIPRSCPREDST);
|
|
/* Differ from Codec */
|
|
- if (cfg->fmt & CAMIF_RGB24) {
|
|
+ if (cfg->fmt & CAMIF_RGB24)
|
|
cmd |= RGB_FMT24;
|
|
- }
|
|
- else {
|
|
- /* RGB16 */;
|
|
- }
|
|
if (cfg->sc.scaleup_h & cfg->sc.scaleup_v)
|
|
- cmd |= BIT29|BIT28;
|
|
- CIPRSCCTRL = cmd |MAIN_HRATIO(cfg->sc.mainhratio)|S_METHOD
|
|
- |MAIN_VRATIO(cfg->sc.mainvratio);
|
|
- }else {
|
|
- panic("CAMERA:DMA_TYPE Wrong \n");
|
|
+ cmd |= BIT29 | BIT28;
|
|
+ writel(cmd | MAIN_HRATIO(cfg->sc.mainhratio) | S_METHOD |
|
|
+ MAIN_VRATIO(cfg->sc.mainvratio),
|
|
+ camregs + S3C2440_CAM_REG_CIPRSCCTRL);
|
|
+ return 0;
|
|
}
|
|
|
|
+ panic("CAMERA:DMA_TYPE Wrong \n");
|
|
return 0;
|
|
}
|
|
|
|
@@ -654,46 +675,50 @@ static int inline camif_hw_reg(camif_cfg_t *cfg)
|
|
/* Configure Pre-scaler control & main scaler control register */
|
|
static int camif_scaler(camif_cfg_t *cfg)
|
|
{
|
|
- int tx = cfg->target_x,ty=cfg->target_y;
|
|
+ int tx = cfg->target_x, ty = cfg->target_y;
|
|
int sx, sy;
|
|
|
|
- if (tx <= 0 || ty<= 0) panic("CAMERA: Invalid target size \n");
|
|
+ if (tx <= 0 || ty <= 0)
|
|
+ panic("CAMERA: Invalid target size \n");
|
|
+
|
|
+ sx = cfg->gc->source_x - 2 * cfg->gc->win_hor_ofst;
|
|
+ sy = cfg->gc->source_y - 2 * cfg->gc->win_ver_ofst;
|
|
+ if (sx <= 0 || sy <= 0)
|
|
+ panic("CAMERA: Invalid source size \n");
|
|
|
|
- sx = cfg->gc->source_x - 2*cfg->gc->win_hor_ofst;
|
|
- sy = cfg->gc->source_y - 2*cfg->gc->win_ver_ofst;
|
|
- if (sx <= 0 || sy<= 0) panic("CAMERA: Invalid source size \n");
|
|
cfg->sc.modified_src_x = sx;
|
|
cfg->sc.modified_src_y = sy;
|
|
|
|
/* Pre-scaler control register 1 */
|
|
- camif_scaler_internal(sx,tx,&cfg->sc.prehratio,&cfg->sc.hfactor);
|
|
- camif_scaler_internal(sy,ty,&cfg->sc.prevratio,&cfg->sc.vfactor);
|
|
+ camif_scaler_internal(sx, tx, &cfg->sc.prehratio, &cfg->sc.hfactor);
|
|
+ camif_scaler_internal(sy, ty, &cfg->sc.prevratio, &cfg->sc.vfactor);
|
|
|
|
- if (cfg->dma_type & CAMIF_PREVIEW) {
|
|
- if ( (sx /cfg->sc.prehratio) <= 640 ) {}
|
|
- else {
|
|
- printk(KERN_INFO "CAMERA: Internal Preview line buffer is 640 pixels\n");
|
|
+ if (cfg->dma_type & CAMIF_PREVIEW)
|
|
+ if ((sx / cfg->sc.prehratio) > 640) {
|
|
+ printk(KERN_INFO "CAMERA: Internal Preview line "
|
|
+ "buffer is 640 pixels\n");
|
|
return 1; /* Error */
|
|
}
|
|
- }
|
|
|
|
- cfg->sc.shfactor = 10-(cfg->sc.hfactor+cfg->sc.vfactor);
|
|
+ cfg->sc.shfactor = 10 - (cfg->sc.hfactor + cfg->sc.vfactor);
|
|
/* Pre-scaler control register 2 */
|
|
cfg->sc.predst_x = sx / cfg->sc.prehratio;
|
|
cfg->sc.predst_y = sy / cfg->sc.prevratio;
|
|
|
|
/* Main-scaler control register */
|
|
- cfg->sc.mainhratio = (sx << 8)/(tx << cfg->sc.hfactor);
|
|
- cfg->sc.mainvratio = (sy << 8)/(ty << cfg->sc.vfactor);
|
|
- DPRINTK(" sx %d, sy %d tx %d ty %d \n",sx,sy,tx,ty);
|
|
- DPRINTK(" hfactor %d vfactor %d \n",cfg->sc.hfactor,cfg->sc.vfactor);
|
|
+ cfg->sc.mainhratio = (sx << 8) / (tx << cfg->sc.hfactor);
|
|
+ cfg->sc.mainvratio = (sy << 8) / (ty << cfg->sc.vfactor);
|
|
+ DPRINTK(" sx %d, sy %d tx %d ty %d \n", sx, sy, tx, ty);
|
|
+ DPRINTK(" hfactor %d vfactor %d \n",cfg->sc.hfactor, cfg->sc.vfactor);
|
|
|
|
cfg->sc.scaleup_h = (sx <= tx) ? 1: 0;
|
|
cfg->sc.scaleup_v = (sy <= ty) ? 1: 0;
|
|
- if ( cfg->sc.scaleup_h != cfg->sc.scaleup_v)
|
|
+ if (cfg->sc.scaleup_h != cfg->sc.scaleup_v)
|
|
printk(KERN_ERR "scaleup_h must be same to scaleup_v \n");
|
|
+
|
|
camif_hw_reg(cfg);
|
|
camif_target_area(cfg);
|
|
+
|
|
return 0;
|
|
}
|
|
|
|
@@ -706,38 +731,38 @@ static void camif_g_bsize(u32 hsize, u32 *mburst, u32 *rburst)
|
|
{
|
|
u32 tmp;
|
|
|
|
- tmp = (hsize/4) % 16;
|
|
+ tmp = (hsize / 4) % 16;
|
|
switch(tmp) {
|
|
+ case 0:
|
|
+ *mburst=16;
|
|
+ *rburst=16;
|
|
+ break;
|
|
+ case 4:
|
|
+ *mburst=16;
|
|
+ *rburst=4;
|
|
+ break;
|
|
+ case 8:
|
|
+ *mburst=16;
|
|
+ *rburst=8;
|
|
+ break;
|
|
+ default:
|
|
+ tmp=(hsize / 4) % 8;
|
|
+ switch(tmp) {
|
|
case 0:
|
|
- *mburst=16;
|
|
- *rburst=16;
|
|
+ *mburst = 8;
|
|
+ *rburst = 8;
|
|
break;
|
|
case 4:
|
|
- *mburst=16;
|
|
- *rburst=4;
|
|
- break;
|
|
- case 8:
|
|
- *mburst=16;
|
|
- *rburst=8;
|
|
- break;
|
|
+ *mburst = 8;
|
|
+ *rburst = 4;
|
|
default:
|
|
- tmp=(hsize/4)%8;
|
|
- switch(tmp) {
|
|
- case 0:
|
|
- *mburst=8;
|
|
- *rburst=8;
|
|
- break;
|
|
- case 4:
|
|
- *mburst=8;
|
|
- *rburst=4;
|
|
- default:
|
|
- *mburst=4;
|
|
- tmp=(hsize/4)%4;
|
|
- *rburst= (tmp) ? tmp: 4;
|
|
- break;
|
|
- }
|
|
+ *mburst = 4;
|
|
+ tmp = (hsize / 4) % 4;
|
|
+ *rburst= (tmp) ? tmp: 4;
|
|
break;
|
|
}
|
|
+ break;
|
|
+ }
|
|
}
|
|
|
|
/* SXGA 1028x1024*/
|
|
@@ -759,24 +784,30 @@ static int camif_dma_burst(camif_cfg_t *cfg)
|
|
u32 yburst_m, yburst_r;
|
|
u32 cburst_m, cburst_r;
|
|
/* CODEC DMA WIDHT is multiple of 16 */
|
|
- if (width %16 != 0 ) return BURST_ERR; /* DMA Burst Length Error */
|
|
- camif_g_bsize(width,&yburst_m,&yburst_r);
|
|
- camif_g_bsize(width/2,&cburst_m,&cburst_r);
|
|
- CICOCTRL =YBURST_M(yburst_m)|CBURST_M(cburst_m)
|
|
- |YBURST_R(yburst_r)|CBURST_R(cburst_r);
|
|
+ if (width % 16)
|
|
+ return BURST_ERR; /* DMA Burst Length Error */
|
|
+ camif_g_bsize(width, &yburst_m, &yburst_r);
|
|
+ camif_g_bsize(width / 2, &cburst_m, &cburst_r);
|
|
+
|
|
+ writel(YBURST_M(yburst_m) | CBURST_M(cburst_m) |
|
|
+ YBURST_R(yburst_r) | CBURST_R(cburst_r),
|
|
+ camregs + S3C2440_CAM_REG_CICOCTRL);
|
|
}
|
|
|
|
if (cfg->dma_type & CAMIF_PREVIEW) {
|
|
u32 rgburst_m, rgburst_r;
|
|
if(cfg->fmt == CAMIF_RGB24) {
|
|
- if (width %2 != 0 ) return BURST_ERR; /* DMA Burst Length Error */
|
|
+ if (width % 2)
|
|
+ return BURST_ERR; /* DMA Burst Length Error */
|
|
camif_g_bsize(width*4,&rgburst_m,&rgburst_r);
|
|
- }
|
|
- else { /* CAMIF_RGB16 */
|
|
- if ((width/2) %2 != 0 ) return BURST_ERR; /* DMA Burst Length Error */
|
|
+ } else { /* CAMIF_RGB16 */
|
|
+ if ((width / 2) %2)
|
|
+ return BURST_ERR; /* DMA Burst Length Error */
|
|
camif_g_bsize(width*2,&rgburst_m,&rgburst_r);
|
|
}
|
|
- CIPRCTRL = RGBURST_M(rgburst_m) | RGBURST_R(rgburst_r);
|
|
+
|
|
+ writel(RGBURST_M(rgburst_m) | RGBURST_R(rgburst_r),
|
|
+ camregs + S3C2440_CAM_REG_CIPRCTRL);
|
|
}
|
|
return 0;
|
|
}
|
|
@@ -786,19 +817,20 @@ static int camif_gpio_init(void)
|
|
#ifdef CONFIG_ARCH_S3C24A0A
|
|
/* S3C24A0A has the dedicated signal pins for Camera */
|
|
#else
|
|
- set_gpio_ctrl(GPIO_CAMDATA0);
|
|
- set_gpio_ctrl(GPIO_CAMDATA1);
|
|
- set_gpio_ctrl(GPIO_CAMDATA2);
|
|
- set_gpio_ctrl(GPIO_CAMDATA3);
|
|
- set_gpio_ctrl(GPIO_CAMDATA4);
|
|
- set_gpio_ctrl(GPIO_CAMDATA5);
|
|
- set_gpio_ctrl(GPIO_CAMDATA6);
|
|
- set_gpio_ctrl(GPIO_CAMDATA7);
|
|
- set_gpio_ctrl(GPIO_CAMPCLKIN);
|
|
- set_gpio_ctrl(GPIO_CAMVSYNC);
|
|
- set_gpio_ctrl(GPIO_CAMHREF);
|
|
- set_gpio_ctrl(GPIO_CAMPCLKOUT);
|
|
- set_gpio_ctrl(GPIO_CAMRESET);
|
|
+ s3c2410_gpio_cfgpin(S3C2440_GPJ0, S3C2440_GPJ0_CAMDATA0);
|
|
+ s3c2410_gpio_cfgpin(S3C2440_GPJ1, S3C2440_GPJ1_CAMDATA1);
|
|
+ s3c2410_gpio_cfgpin(S3C2440_GPJ2, S3C2440_GPJ2_CAMDATA2);
|
|
+ s3c2410_gpio_cfgpin(S3C2440_GPJ3, S3C2440_GPJ3_CAMDATA3);
|
|
+ s3c2410_gpio_cfgpin(S3C2440_GPJ4, S3C2440_GPJ4_CAMDATA4);
|
|
+ s3c2410_gpio_cfgpin(S3C2440_GPJ5, S3C2440_GPJ5_CAMDATA5);
|
|
+ s3c2410_gpio_cfgpin(S3C2440_GPJ6, S3C2440_GPJ6_CAMDATA6);
|
|
+ s3c2410_gpio_cfgpin(S3C2440_GPJ7, S3C2440_GPJ7_CAMDATA7);
|
|
+
|
|
+ s3c2410_gpio_cfgpin(S3C2440_GPJ8, S3C2440_GPJ8_CAMPCLK);
|
|
+ s3c2410_gpio_cfgpin(S3C2440_GPJ9, S3C2440_GPJ9_CAMVSYNC);
|
|
+ s3c2410_gpio_cfgpin(S3C2440_GPJ10, S3C2440_GPJ10_CAMHREF);
|
|
+ s3c2410_gpio_cfgpin(S3C2440_GPJ11, S3C2440_GPJ11_CAMCLKOUT);
|
|
+ s3c2410_gpio_cfgpin(S3C2440_GPJ12, S3C2440_GPJ12_CAMRESET);
|
|
#endif
|
|
return 0;
|
|
}
|
|
@@ -827,21 +859,33 @@ int camif_clock_init(camif_gc_t *gc)
|
|
camclk_div = (upll+ROUND_ADD) / camclk - 1;
|
|
CLKDIVN = (CLKDIVN & 0xFF) | CLKDIVN_CAM(camclk_div);
|
|
printk(KERN_INFO"CAMERA:upll %d MACRO 0x%08X CLKDIVN 0x%08X \n",
|
|
- upll, CLKDIVN_CAM(camclk_div),CLKDIVN);
|
|
- CIIMGCPT = 0; /* Dummy ? */
|
|
+ upll, CLKDIVN_CAM(camclk_div), CLKDIVN);
|
|
+ writel(0, camregs + S3C2440_CAM_REG_CIIMGCPT); /* Dummy ? */
|
|
+
|
|
return 0;
|
|
}
|
|
#else
|
|
int camif_clock_init(camif_gc_t *gc)
|
|
{
|
|
- unsigned int upll, camclk_div, camclk;
|
|
- if (!gc) camclk = 24000000;
|
|
- else {
|
|
+ unsigned int camclk;
|
|
+ struct clk *clk_camif = clk_get(NULL, "camif");
|
|
+ struct clk *clk_camif_upll = clk_get(NULL, "camif-upll");
|
|
+
|
|
+ if (!gc)
|
|
+ camclk = 24000000;
|
|
+ else {
|
|
camclk = gc->camclk;
|
|
if (camclk > 48000000)
|
|
printk(KERN_ERR "Wrong Camera Clock\n");
|
|
}
|
|
|
|
+ clk_set_rate(clk_camif, camclk);
|
|
+
|
|
+ clk_enable(clk_camif);
|
|
+ clk_enable(clk_camif_upll);
|
|
+
|
|
+
|
|
+#if 0
|
|
CLKCON |= CLKCON_CAMIF;
|
|
upll = elfin_get_bus_clk(GET_UPLL);
|
|
printk(KERN_INFO "CAMERA:Default UPLL %08d and Assing 96Mhz to UPLL\n",upll);
|
|
@@ -854,7 +898,9 @@ int camif_clock_init(camif_gc_t *gc)
|
|
camclk_div = (upll+ROUND_ADD) /(camclk * 2) -1;
|
|
CAMDIVN = CAMCLK_SET_DIV|(camclk_div&0xf);
|
|
printk(KERN_INFO "CAMERA:upll %08d cam_clk %08d CAMDIVN 0x%08x \n",upll,camclk, CAMDIVN);
|
|
- CIIMGCPT = 0; /* Dummy ? */
|
|
+#endif
|
|
+ writel(0, camregs + S3C2440_CAM_REG_CIIMGCPT); /* Dummy ? */
|
|
+
|
|
return 0;
|
|
}
|
|
#endif
|
|
@@ -867,23 +913,39 @@ void camif_reset(int is, int delay)
|
|
{
|
|
switch (is) {
|
|
case CAMIF_RESET:
|
|
- CIGCTRL |= GC_SWRST;
|
|
+ writel(readl(camregs + S3C2440_CAM_REG_CIGCTRL) |
|
|
+ GC_SWRST,
|
|
+ camregs + S3C2440_CAM_REG_CIGCTRL);
|
|
mdelay(1);
|
|
- CIGCTRL &= ~GC_SWRST;
|
|
+ writel(readl(camregs + S3C2440_CAM_REG_CIGCTRL) &
|
|
+ ~GC_SWRST,
|
|
+ camregs + S3C2440_CAM_REG_CIGCTRL);
|
|
break;
|
|
case CAMIF_EX_RESET_AH: /*Active High */
|
|
- CIGCTRL &= ~GC_CAMRST;
|
|
+ writel(readl(camregs + S3C2440_CAM_REG_CIGCTRL) &
|
|
+ ~GC_CAMRST,
|
|
+ camregs + S3C2440_CAM_REG_CIGCTRL);
|
|
udelay(200);
|
|
- CIGCTRL |= GC_CAMRST;
|
|
+ writel(readl(camregs + S3C2440_CAM_REG_CIGCTRL) |
|
|
+ GC_CAMRST,
|
|
+ camregs + S3C2440_CAM_REG_CIGCTRL);
|
|
udelay(delay);
|
|
- CIGCTRL &= ~GC_CAMRST;
|
|
+ writel(readl(camregs + S3C2440_CAM_REG_CIGCTRL) &
|
|
+ ~GC_CAMRST,
|
|
+ camregs + S3C2440_CAM_REG_CIGCTRL);
|
|
break;
|
|
case CAMIF_EX_RESET_AL: /*Active Low */
|
|
- CIGCTRL |= GC_CAMRST;
|
|
+ writel(readl(camregs + S3C2440_CAM_REG_CIGCTRL) |
|
|
+ GC_CAMRST,
|
|
+ camregs + S3C2440_CAM_REG_CIGCTRL);
|
|
udelay(200);
|
|
- CIGCTRL &= ~GC_CAMRST;
|
|
+ writel(readl(camregs + S3C2440_CAM_REG_CIGCTRL) &
|
|
+ ~GC_CAMRST,
|
|
+ camregs + S3C2440_CAM_REG_CIGCTRL);
|
|
udelay(delay);
|
|
- CIGCTRL |= GC_CAMRST;
|
|
+ writel(readl(camregs + S3C2440_CAM_REG_CIGCTRL) |
|
|
+ GC_CAMRST,
|
|
+ camregs + S3C2440_CAM_REG_CIGCTRL);
|
|
break;
|
|
default:
|
|
break;
|
|
@@ -908,10 +970,10 @@ static void camif_bus_priority(int flag)
|
|
PRIORITY1 = PRIORITY_I_FIX;
|
|
|
|
#else
|
|
- old_priority = PRIORITY;
|
|
- PRIORITY &= ~(3<<7);
|
|
- PRIORITY |= (1<<7); /* Arbiter 1, REQ2 first */
|
|
- PRIORITY &= ~(1<<1); /* Disable Priority Rotate */
|
|
+ old_priority = readl(S3C2410_PRIORITY);
|
|
+ writel(readl(S3C2410_PRIORITY) & ~(3<<7), S3C2410_PRIORITY);
|
|
+ writel(readl(S3C2410_PRIORITY) | (1<<7), S3C2410_PRIORITY); /* Arbiter 1, REQ2 first */
|
|
+ writel(readl(S3C2410_PRIORITY) & ~(1<<1), S3C2410_PRIORITY); /* Disable Priority Rotate */
|
|
#endif
|
|
}
|
|
else {
|
|
@@ -919,19 +981,26 @@ static void camif_bus_priority(int flag)
|
|
PRIORITY0 = old_priority;
|
|
PRIORITY1 = old_priority;
|
|
#else
|
|
- PRIORITY = old_priority;
|
|
+ writel(old_priority, S3C2410_PRIORITY);
|
|
#endif
|
|
}
|
|
}
|
|
|
|
static void inline camif_clock_off(void)
|
|
{
|
|
- CIIMGCPT = 0;
|
|
#if defined (CONFIG_ARCH_S3C24A0A)
|
|
+ writel(0, camregs + S3C2440_CAM_REG_CIIMGCPT);
|
|
+
|
|
CLKCON &= ~CLKCON_CAM_UPLL;
|
|
CLKCON &= ~CLKCON_CAM_HCLK;
|
|
#else
|
|
- CLKCON &= ~CLKCON_CAMIF;
|
|
+ struct clk *clk_camif = clk_get(NULL, "camif");
|
|
+ struct clk *clk_camif_upll = clk_get(NULL, "camif-upll");
|
|
+
|
|
+ writel(0, camregs + S3C2440_CAM_REG_CIIMGCPT);
|
|
+
|
|
+ clk_disable(clk_camif);
|
|
+ clk_disable(clk_camif_upll);
|
|
#endif
|
|
}
|
|
|
|
diff --git a/arch/arm/mach-s3c2440/camera/camif_fsm.c b/arch/arm/mach-s3c2440/camera/camif_fsm.c
|
|
index 3e2b71a..b534aca 100644
|
|
--- a/arch/arm/mach-s3c2440/camera/camif_fsm.c
|
|
+++ b/arch/arm/mach-s3c2440/camera/camif_fsm.c
|
|
@@ -31,7 +31,12 @@
|
|
#include <asm/semaphore.h>
|
|
#include <linux/miscdevice.h>
|
|
|
|
+#define CONFIG_VIDEO_V4L1_COMPAT
|
|
+#include <linux/videodev.h>
|
|
+#include "camif.h"
|
|
+
|
|
//#define SW_DEBUG
|
|
+static void camif_start_p_with_c(camif_cfg_t *cfg);
|
|
|
|
#include "camif.h"
|
|
const char *fsm_version =
|
|
diff --git a/arch/arm/mach-s3c2440/camera/imgsensor.c b/arch/arm/mach-s3c2440/camera/imgsensor.c
|
|
index 44b7bee..2099b69 100644
|
|
--- a/arch/arm/mach-s3c2440/camera/imgsensor.c
|
|
+++ b/arch/arm/mach-s3c2440/camera/imgsensor.c
|
|
@@ -11,7 +11,7 @@
|
|
* Driver for FIMC20 Camera Decoder
|
|
*/
|
|
|
|
-#include <linux/config.h>
|
|
+
|
|
#include <linux/module.h>
|
|
#include <linux/kernel.h>
|
|
#include <linux/init.h>
|
|
@@ -24,10 +24,12 @@
|
|
|
|
#ifdef CONFIG_ARCH_S3C24A0A
|
|
#else
|
|
-#include <asm/arch/S3C2440.h>
|
|
+//#include <asm/arch/S3C2440.h>
|
|
#endif
|
|
|
|
#define SW_DEBUG
|
|
+#define CONFIG_VIDEO_V4L1_COMPAT
|
|
+#include <linux/videodev.h>
|
|
#include "camif.h"
|
|
#include "sensor.h"
|
|
|
|
@@ -37,10 +39,6 @@
|
|
#include "sxga.h"
|
|
#endif
|
|
|
|
-static const char *sensor_version =
|
|
- "$Id: imgsensor.c,v 1.11 2004/06/10 12:45:40 swlee Exp $";
|
|
-
|
|
-
|
|
static struct i2c_driver s5x532_driver;
|
|
static camif_gc_t data = {
|
|
itu_fmt: CAMIF_ITU601,
|
|
@@ -69,22 +67,18 @@ static camif_gc_t data = {
|
|
|
|
#define CAM_ID 0x5a
|
|
|
|
-static unsigned short ignore[] = { I2C_CLIENT_END };
|
|
+static unsigned short ignore = I2C_CLIENT_END;
|
|
static unsigned short normal_addr[] = { (CAM_ID>>1), I2C_CLIENT_END };
|
|
static struct i2c_client_address_data addr_data = {
|
|
normal_i2c: normal_addr,
|
|
- normal_i2c_range: ignore,
|
|
- probe: ignore,
|
|
- probe_range: ignore,
|
|
- ignore: ignore,
|
|
- ignore_range: ignore,
|
|
- force: ignore,
|
|
+ probe: &ignore,
|
|
+ ignore: &ignore,
|
|
};
|
|
|
|
s5x532_t s5x532_regs_mirror[S5X532_REGS];
|
|
|
|
unsigned char
|
|
-s5x532_read(struct i2c_client *client,unsigned char subaddr)
|
|
+s5x532_read(struct i2c_client *client, unsigned char subaddr)
|
|
{
|
|
int ret;
|
|
unsigned char buf[1];
|
|
@@ -151,7 +145,7 @@ void inline s5x532_init(struct i2c_client *sam_client)
|
|
}
|
|
|
|
static int
|
|
-s5x532_attach(struct i2c_adapter *adap, int addr, unsigned short flags,int kind)
|
|
+s5x532_attach(struct i2c_adapter *adap, int addr, int kind)
|
|
{
|
|
struct i2c_client *c;
|
|
|
|
@@ -159,13 +153,13 @@ s5x532_attach(struct i2c_adapter *adap, int addr, unsigned short flags,int kind)
|
|
if (!c) return -ENOMEM;
|
|
|
|
strcpy(c->name, "S5X532");
|
|
- c->id = s5x532_driver.id;
|
|
- c->flags = I2C_CLIENT_ALLOW_USE;
|
|
+// c->id = s5x532_driver.id;
|
|
+ c->flags = 0 /* I2C_CLIENT_ALLOW_USE */;
|
|
c->addr = addr;
|
|
c->adapter = adap;
|
|
c->driver = &s5x532_driver;
|
|
- c->data = &data;
|
|
- data.sensor = c;
|
|
+ data.sensor = c;
|
|
+ i2c_set_clientdata(c, &data);
|
|
|
|
camif_register_decoder(c);
|
|
return i2c_attach_client(c);
|
|
@@ -192,10 +186,10 @@ s5x532_command(struct i2c_client *client, unsigned int cmd, void *arg)
|
|
printk(KERN_INFO "CAMERA: S5X532 Sensor initialized\n");
|
|
break;
|
|
case USER_ADD:
|
|
- MOD_INC_USE_COUNT;
|
|
+ /* MOD_INC_USE_COUNT; uh.. 2.6 deals with this, old-timer */
|
|
break;
|
|
case USER_EXIT:
|
|
- MOD_DEC_USE_COUNT;
|
|
+ /* MOD_DEC_USE_COUNT; */
|
|
break;
|
|
/* Todo
|
|
case SENSOR_BRIGHTNESS:
|
|
@@ -210,9 +204,8 @@ s5x532_command(struct i2c_client *client, unsigned int cmd, void *arg)
|
|
}
|
|
|
|
static struct i2c_driver s5x532_driver = {
|
|
- name: "S5X532",
|
|
- id: I2C_ALGO_S3C,
|
|
- flags: I2C_DF_NOTIFY,
|
|
+ driver: { name: "S5X532" },
|
|
+ id: 0, /* optional in i2c-id.h I2C_ALGO_S3C, */
|
|
attach_adapter: s5x532_probe,
|
|
detach_client: s5x532_detach,
|
|
command: s5x532_command
|
|
@@ -220,11 +213,13 @@ static struct i2c_driver s5x532_driver = {
|
|
|
|
static void iic_gpio_port(void)
|
|
{
|
|
+/* FIXME: no gpio config for i2c !!!
|
|
#ifdef CONFIG_ARCH_S3C24A0A
|
|
#else
|
|
GPECON &= ~(0xf <<28);
|
|
GPECON |= 0xa <<28;
|
|
#endif
|
|
+*/
|
|
}
|
|
|
|
static __init int camif_sensor_init(void)
|
|
diff --git a/arch/arm/mach-s3c2440/camera/qt-driver.c b/arch/arm/mach-s3c2440/camera/qt-driver.c
|
|
index 0c5dd40..cbf8565 100644
|
|
--- a/arch/arm/mach-s3c2440/camera/qt-driver.c
|
|
+++ b/arch/arm/mach-s3c2440/camera/qt-driver.c
|
|
@@ -31,12 +31,15 @@
|
|
|
|
//#define SW_DEBUG
|
|
|
|
+#define CONFIG_VIDEO_V4L1_COMPAT
|
|
+#include <linux/videodev.h>
|
|
#include "camif.h"
|
|
-#include "videodev.h"
|
|
#include "miscdevice.h"
|
|
#include "cam_reg.h"
|
|
#include "sensor.h"
|
|
#include "userapp.h"
|
|
+
|
|
+extern camif_cfg_t * get_camif(int nr);
|
|
|
|
|
|
/************************* Sharp Zarus API **************************
|
|
diff --git a/arch/arm/mach-s3c2440/camera/video-driver.c b/arch/arm/mach-s3c2440/camera/video-driver.c
|
|
index fe9130c..9c77475 100644
|
|
--- a/arch/arm/mach-s3c2440/camera/video-driver.c
|
|
+++ b/arch/arm/mach-s3c2440/camera/video-driver.c
|
|
@@ -29,11 +29,12 @@
|
|
#include <asm/irq.h>
|
|
#include <asm/semaphore.h>
|
|
#include <linux/miscdevice.h>
|
|
+#include <asm/arch/irqs.h>
|
|
|
|
//#define SW_DEBUG
|
|
-
|
|
+#define CONFIG_VIDEO_V4L1_COMPAT
|
|
+#include <linux/videodev.h>
|
|
#include "camif.h"
|
|
-#include "videodev.h"
|
|
#include "miscdevice.h"
|
|
#include "cam_reg.h"
|
|
#include "sensor.h"
|
|
@@ -46,12 +47,14 @@
|
|
/* Codec and Preview */
|
|
#define CAMIF_NUM 2
|
|
static camif_cfg_t fimc[CAMIF_NUM];
|
|
+u32 *camregs;
|
|
|
|
static const char *driver_version =
|
|
"$Id: video-driver.c,v 1.9 2004/06/02 03:10:36 swlee Exp $";
|
|
extern const char *fimc_version;
|
|
extern const char *fsm_version;
|
|
|
|
+extern void camif_start_c_with_p (camif_cfg_t *cfg, camif_cfg_t *other);
|
|
|
|
camif_cfg_t * get_camif(int nr)
|
|
{
|
|
@@ -177,28 +180,34 @@ camif_c_read(struct file *file, char *buf, size_t count, loff_t *pos)
|
|
}
|
|
|
|
|
|
-static void camif_c_irq(int irq, void *dev_id, struct pt_regs *regs)
|
|
+static irqreturn_t camif_c_irq(int irq, void *dev_id)
|
|
{
|
|
camif_cfg_t *cfg = (camif_cfg_t *)dev_id;
|
|
+
|
|
DPRINTK("\n");
|
|
camif_g_fifo_status(cfg);
|
|
camif_g_frame_num(cfg);
|
|
- if(camif_enter_c_4fsm(cfg) == INSTANT_SKIP) return;
|
|
- wake_up_interruptible(&cfg->waitq);
|
|
+ if(camif_enter_c_4fsm(cfg) != INSTANT_SKIP)
|
|
+ wake_up_interruptible(&cfg->waitq);
|
|
+
|
|
+ return IRQ_HANDLED;
|
|
}
|
|
|
|
-static void camif_p_irq(int irq, void *dev_id, struct pt_regs * regs)
|
|
+static irqreturn_t camif_p_irq(int irq, void *dev_id)
|
|
{
|
|
camif_cfg_t *cfg = (camif_cfg_t *)dev_id;
|
|
+
|
|
DPRINTK("\n");
|
|
camif_g_fifo_status(cfg);
|
|
camif_g_frame_num(cfg);
|
|
- if(camif_enter_p_4fsm(cfg) == INSTANT_SKIP) return;
|
|
- wake_up_interruptible(&cfg->waitq);
|
|
+ if(camif_enter_p_4fsm(cfg) != INSTANT_SKIP)
|
|
+ wake_up_interruptible(&cfg->waitq);
|
|
#if 0
|
|
if( (cfg->perf.frames % 5) == 0)
|
|
DPRINTK("5\n");
|
|
#endif
|
|
+
|
|
+ return IRQ_HANDLED;
|
|
}
|
|
|
|
static void camif_release_irq(camif_cfg_t *cfg)
|
|
@@ -213,13 +222,13 @@ static int camif_irq_request(camif_cfg_t *cfg)
|
|
|
|
if (cfg->dma_type & CAMIF_CODEC) {
|
|
if ((ret = request_irq(cfg->irq, camif_c_irq,
|
|
- SA_INTERRUPT,cfg->shortname, cfg))) {
|
|
+ 0, cfg->shortname, cfg))) {
|
|
printk("request_irq(CAM_C) failed.\n");
|
|
}
|
|
}
|
|
if (cfg->dma_type & CAMIF_PREVIEW) {
|
|
if ((ret = request_irq(cfg->irq, camif_p_irq,
|
|
- SA_INTERRUPT,cfg->shortname, cfg))) {
|
|
+ 0, cfg->shortname, cfg))) {
|
|
printk("request_irq(CAM_P) failed.\n");
|
|
}
|
|
}
|
|
@@ -438,7 +447,7 @@ static struct video_device codec_template =
|
|
{
|
|
.name = "CODEC_IF",
|
|
.type = VID_TYPE_CAPTURE|VID_TYPE_CLIPPING|VID_TYPE_SCALES,
|
|
- .hardware = VID_HARDWARE_SAMSUNG_FIMC20,
|
|
+/* .hardware = VID_HARDWARE_SAMSUNG_FIMC20, */
|
|
.fops = &camif_c_fops,
|
|
// .release = camif_release
|
|
.minor = -1,
|
|
@@ -448,7 +457,7 @@ static struct video_device preview_template =
|
|
{
|
|
.name = "PREVIEW_IF",
|
|
.type = VID_TYPE_CAPTURE|VID_TYPE_CLIPPING|VID_TYPE_SCALES,
|
|
- .hardware = VID_HARDWARE_SAMSUNG_FIMC20,
|
|
+/* .hardware = VID_HARDWARE_SAMSUNG_FIMC20, */
|
|
.fops = &camif_p_fops,
|
|
.minor = -1,
|
|
};
|
|
@@ -465,8 +474,8 @@ static int preview_init(camif_cfg_t *cfg)
|
|
cfg->fmt = CAMIF_RGB16;
|
|
cfg->flip = CAMIF_FLIP_Y;
|
|
cfg->v = &preview_template;
|
|
- init_MUTEX(&cfg->v->lock);
|
|
- cfg->irq = IRQ_CAM_P;
|
|
+ mutex_init(&cfg->v->lock);
|
|
+ cfg->irq = IRQ_S3C2440_CAM_P;
|
|
|
|
strcpy(cfg->shortname,name);
|
|
init_waitqueue_head(&cfg->waitq);
|
|
@@ -486,8 +495,8 @@ static int codec_init(camif_cfg_t *cfg)
|
|
cfg->fmt = CAMIF_IN_YCBCR422|CAMIF_OUT_YCBCR420;
|
|
cfg->flip = CAMIF_FLIP_X;
|
|
cfg->v = &codec_template;
|
|
- init_MUTEX(&cfg->v->lock);
|
|
- cfg->irq = IRQ_CAM_C;
|
|
+ mutex_init(&cfg->v->lock);
|
|
+ cfg->irq = IRQ_S3C2440_CAM_C;
|
|
strcpy(cfg->shortname,name);
|
|
init_waitqueue_head(&cfg->waitq);
|
|
cfg->status = CAMIF_STOPPED;
|
|
@@ -510,25 +519,44 @@ static void print_version(void)
|
|
|
|
static int camif_m_in(void)
|
|
{
|
|
- int ret = 0;
|
|
+ int ret = -EINVAL;
|
|
camif_cfg_t * cfg;
|
|
|
|
+ printk(KERN_INFO"Starting S3C2440 Camera Driver\n");
|
|
+
|
|
+ camregs = ioremap(CAM_BASE_ADD, 0x100);
|
|
+ if (!camregs) {
|
|
+ printk(KERN_ERR"Unable to map camera regs\n");
|
|
+ ret = -ENOMEM;
|
|
+ goto bail1;
|
|
+ }
|
|
+
|
|
camif_init();
|
|
cfg = get_camif(CODEC_MINOR);
|
|
codec_init(cfg);
|
|
|
|
- if (video_register_device(cfg->v,0,CODEC_MINOR)!=0) {
|
|
- DPRINTK("Couldn't register codec driver.\n");
|
|
- return 0;
|
|
+ ret = video_register_device(cfg->v,0,CODEC_MINOR);
|
|
+ if (ret) {
|
|
+ printk(KERN_ERR"Couldn't register codec driver.\n");
|
|
+ goto bail2;
|
|
}
|
|
cfg = get_camif(PREVIEW_MINOR);
|
|
preview_init(cfg);
|
|
- if (video_register_device(cfg->v,0,PREVIEW_MINOR)!=0) {
|
|
- DPRINTK("Couldn't register preview driver.\n");
|
|
- return 0;
|
|
+ ret = video_register_device(cfg->v,0,PREVIEW_MINOR);
|
|
+ if (ret) {
|
|
+ printk(KERN_ERR"Couldn't register preview driver.\n");
|
|
+ goto bail3; /* hm seems it us unregistered the once */
|
|
}
|
|
|
|
print_version();
|
|
+ return 0;
|
|
+
|
|
+bail3:
|
|
+ video_unregister_device(cfg->v);
|
|
+bail2:
|
|
+ iounmap(camregs);
|
|
+ camregs = NULL;
|
|
+bail1:
|
|
return ret;
|
|
}
|
|
|
|
@@ -536,7 +564,9 @@ static void unconfig_device(camif_cfg_t *cfg)
|
|
{
|
|
video_unregister_device(cfg->v);
|
|
camif_hw_close(cfg);
|
|
+ iounmap(camregs);
|
|
//memset(cfg, 0, sizeof(camif_cfg_t));
|
|
+ camregs = NULL;
|
|
}
|
|
|
|
static void camif_m_out(void) /* module out */
|
|
@@ -547,20 +577,22 @@ static void camif_m_out(void) /* module out */
|
|
unconfig_device(cfg);
|
|
cfg = get_camif(PREVIEW_MINOR);
|
|
unconfig_device(cfg);
|
|
+
|
|
return;
|
|
}
|
|
|
|
void camif_register_decoder(struct i2c_client *ptr)
|
|
{
|
|
camif_cfg_t *cfg;
|
|
+ void * data = i2c_get_clientdata(ptr);
|
|
|
|
cfg =get_camif(CODEC_MINOR);
|
|
- cfg->gc = (camif_gc_t *)(ptr->data);
|
|
+ cfg->gc = (camif_gc_t *)(data);
|
|
|
|
cfg =get_camif(PREVIEW_MINOR);
|
|
- cfg->gc = (camif_gc_t *)(ptr->data);
|
|
+ cfg->gc = (camif_gc_t *)(data);
|
|
|
|
- sema_init(&cfg->gc->lock,1); /* global lock for both Codec and Preview */
|
|
+ sema_init(&cfg->gc->lock, 1); /* global lock for both Codec and Preview */
|
|
cfg->gc->status |= PNOTWORKING; /* Default Value */
|
|
camif_hw_open(cfg->gc);
|
|
}
|
|
@@ -568,8 +600,9 @@ void camif_register_decoder(struct i2c_client *ptr)
|
|
void camif_unregister_decoder(struct i2c_client *ptr)
|
|
{
|
|
camif_gc_t *gc;
|
|
+ void * data = i2c_get_clientdata(ptr);
|
|
|
|
- gc = (camif_gc_t *)(ptr->data);
|
|
+ gc = (camif_gc_t *)(data);
|
|
gc->init_sensor = 0; /* need to modify */
|
|
}
|
|
|
|
diff --git a/arch/arm/mach-s3c2440/camera/videodev.c b/arch/arm/mach-s3c2440/camera/videodev.c
|
|
index 0b3498f..6f862e4 100644
|
|
--- a/arch/arm/mach-s3c2440/camera/videodev.c
|
|
+++ b/arch/arm/mach-s3c2440/camera/videodev.c
|
|
@@ -22,7 +22,7 @@
|
|
#include <linux/init.h>
|
|
#include <linux/kmod.h>
|
|
#include <linux/slab.h>
|
|
-#include <linux/devfs_fs_kernel.h>
|
|
+/* #include <linux/devfs_fs_kernel.h> */
|
|
#include <linux/miscdevice.h>
|
|
#include <asm/uaccess.h>
|
|
#include <asm/system.h>
|
|
@@ -30,8 +30,9 @@
|
|
|
|
|
|
|
|
+#define CONFIG_VIDEO_V4L1_COMPAT
|
|
+#include <linux/videodev.h>
|
|
#include "camif.h"
|
|
-#include "videodev.h"
|
|
#include "miscdevice.h"
|
|
|
|
|
|
@@ -42,18 +43,7 @@ const char *fimc_version = "$Id: videodev.c,v 1.1.1.1 2004/04/27 03:52:50 swlee
|
|
#define VIDEO_NAME "video4linux"
|
|
|
|
|
|
-static inline unsigned iminor(struct inode *inode)
|
|
-{
|
|
- return MINOR(inode->i_rdev);
|
|
-}
|
|
-
|
|
-static inline unsigned imajor(struct inode *inode)
|
|
-{
|
|
- return MAJOR(inode->i_rdev);
|
|
-}
|
|
-
|
|
-
|
|
-#define VIDEO_NUM_DEVICES 2
|
|
+#define VIDEO_NUM_DEVICES 2
|
|
static struct video_device *video_device[VIDEO_NUM_DEVICES];
|
|
|
|
static inline struct video_device * get_vd(int nr)
|
|
@@ -104,7 +94,7 @@ static int video_open(struct inode *inode, struct file *file)
|
|
int minor = MINOR(inode->i_rdev);
|
|
int err = 0;
|
|
struct video_device *vfl;
|
|
- struct file_operations *old_fops;
|
|
+ struct file_operations const *old_fops;
|
|
|
|
down(&videodev_lock);
|
|
|
|
@@ -131,13 +121,13 @@ extern int video_exclusive_open(struct inode *inode, struct file *file)
|
|
struct video_device *vfl = get_vd(MINOR(inode->i_rdev));
|
|
int retval = 0;
|
|
|
|
- down(&vfl->lock);
|
|
+ mutex_lock(&vfl->lock);
|
|
if (vfl->users) {
|
|
retval = -EBUSY;
|
|
} else {
|
|
vfl->users++;
|
|
}
|
|
- up(&vfl->lock);
|
|
+ mutex_unlock(&vfl->lock);
|
|
return retval;
|
|
}
|
|
|
|
diff --git a/arch/arm/mach-s3c2440/camera/videodev.h b/arch/arm/mach-s3c2440/camera/videodev.h
|
|
index f12db43..1c2e35a 100644
|
|
--- a/arch/arm/mach-s3c2440/camera/videodev.h
|
|
+++ b/arch/arm/mach-s3c2440/camera/videodev.h
|
|
@@ -1,11 +1,11 @@
|
|
-#ifndef __LINUX_S3C_VIDEODEV_H
|
|
-#define __LINUX_S3C_VIDEODEV_H
|
|
+//#ifndef __LINUX_S3C_VIDEODEV_H
|
|
+//#define __LINUX_S3C_VIDEODEV_H
|
|
|
|
#include <linux/types.h>
|
|
#include <linux/version.h>
|
|
-#include "videodev2.h"
|
|
-
|
|
+#include <media/v4l2-dev.h>
|
|
|
|
+#if 0
|
|
struct video_device
|
|
{
|
|
/* device info */
|
|
@@ -96,12 +96,10 @@ extern int video_usercopy(struct inode *inode, struct file *file,
|
|
|
|
|
|
|
|
-#define VID_HARDWARE_SAMSUNG_FIMC 255
|
|
-
|
|
-
|
|
-
|
|
-#endif
|
|
+#endif
|
|
+//#endif
|
|
|
|
+#define VID_HARDWARE_SAMSUNG_FIMC 255
|
|
|
|
/*
|
|
* Local variables:
|
|
--
|
|
1.5.6.3
|
|
|