创造着

  博客园  :: 首页  :: 新随笔  :: 联系 :: 订阅 订阅  :: 管理

OV7670摄像头初始化通过SCCI接口,由 I2C_Controller.v 底层SCCI 驱动模块和上层初始化参数配置构成 I2C_CCD_Config.v 。

模块应用硬件平台:

http://item.taobao.com/item.htm?id=6933324904

// --------------------------------------------------------------------
// Copyright (c) 2005 by  amfpga.taobao.com .
// --------------------------------------------------------------------
// --------------------------------------------------------------------
//          
//                     Terasic Technologies Inc
//                     356 Fu-Shin E. Rd Sec. 1. JhuBei City,
//                     HsinChu County, Taiwan
//                     302
//
//                     web: http://amfpga.taobao.com

//                     email: owein@163.com
//
// --------------------------------------------------------------------
//
// Major Functions:I2C_Controller.v

//
// --------------------------------------------------------------------
//
// Revision History :
// --------------------------------------------------------------------
//   Ver  :| Author            :| Mod. Date :| Changes Made:
//   V1.0 :| Joe Yang          :| 05/07/10  :|      Initial Revision
// --------------------------------------------------------------------
module I2C_Controller (
 CLOCK,
 I2C_SCLK,//I2C CLOCK
  I2C_SDAT,//I2C DATA
 I2C_DATA,//DATA:[SLAVE_ADDR,SUB_ADDR,DATA]
 GO,      //GO transfor
 END,     //END transfor
 W_R,     //W_R
 ACK,      //ACK
 RESET,
 //TEST
 SD_COUNTER,
 SDO
);
 input  CLOCK;
 input  [23:0]I2C_DATA; 
 input  GO;
 input  RESET; 
 input  W_R;
  inout  I2C_SDAT; 
 output I2C_SCLK;
 output END; 
 output ACK;

//TEST
 output [5:0] SD_COUNTER;
 output SDO;


reg SDO;
reg SCLK;
reg END;
reg [23:0]SD;
reg [5:0]SD_COUNTER;

wire I2C_SCLK=SCLK | ( ((SD_COUNTER >= 4) & (SD_COUNTER <=30))? ~CLOCK :0 );
wire I2C_SDAT=SDO?1'bz:0 ;

reg ACK1,ACK2,ACK3;
wire ACK=ACK1 | ACK2 |ACK3;

//--I2C COUNTER
always @(negedge RESET or posedge CLOCK ) begin
if (!RESET) SD_COUNTER=6'b111111;
else begin
if (GO==0)
 SD_COUNTER=0;
 else
 if (SD_COUNTER < 6'b111111) SD_COUNTER=SD_COUNTER+1; 
end
end
//----

always @(negedge RESET or  posedge CLOCK ) begin
if (!RESET) begin SCLK=1;SDO=1; ACK1=0;ACK2=0;ACK3=0; END=1; end
else
case (SD_COUNTER)
 6'd0  : begin ACK1=0 ;ACK2=0 ;ACK3=0 ; END=0; SDO=1; SCLK=1;end
 //start
 6'd1  : begin SD=I2C_DATA;SDO=0;end
 6'd2  : SCLK=0;
 //SLAVE ADDR
 6'd3  : SDO=SD[23];
 6'd4  : SDO=SD[22];
 6'd5  : SDO=SD[21];
 6'd6  : SDO=SD[20];
 6'd7  : SDO=SD[19];
 6'd8  : SDO=SD[18];
 6'd9  : SDO=SD[17];
 6'd10 : SDO=SD[16]; 
 6'd11 : SDO=1'b1;//ACK

 //SUB ADDR
 6'd12  : begin SDO=SD[15]; ACK1=I2C_SDAT; end
 6'd13  : SDO=SD[14];
 6'd14  : SDO=SD[13];
 6'd15  : SDO=SD[12];
 6'd16  : SDO=SD[11];
 6'd17  : SDO=SD[10];
 6'd18  : SDO=SD[9];
 6'd19  : SDO=SD[8];
 6'd20  : SDO=1'b1;//ACK

 //DATA
 6'd21  : begin SDO=SD[7]; ACK2=I2C_SDAT; end
 6'd22  : SDO=SD[6];
 6'd23  : SDO=SD[5];
 6'd24  : SDO=SD[4];
 6'd25  : SDO=SD[3];
 6'd26  : SDO=SD[2];
 6'd27  : SDO=SD[1];
 6'd28  : SDO=SD[0];
 6'd29  : SDO=1'b1;//ACK

 
 //stop
    6'd30 : begin SDO=1'b0; SCLK=1'b0; ACK3=I2C_SDAT; end 
    6'd31 : SCLK=1'b1;
    6'd32 : begin SDO=1'b1; END=1; end

endcase
end

 

endmodule

 ////////////////////////////////////////////////////////////////////////////////////////////////////////

//////////   I2C_CCD_Config.v

////////////////////////////////////////////////////////////////////////////////////////////////////////

module I2C_CCD_Config ( // Host Side
      iCLK,
      iRST_N,
      //iExposure,
      // I2C Side
      I2C_SCLK,
      I2C_SDAT,
      cmos_finish );
// Host Side
input   iCLK;
input   iRST_N;
//input [15:0] iExposure;
// I2C Side
output  I2C_SCLK;
inout  I2C_SDAT;

output cmos_finish;
// Internal Registers/Wires
reg [15:0] mI2C_CLK_DIV;
reg [23:0] mI2C_DATA;
reg   mI2C_CTRL_CLK;
reg   mI2C_GO;
wire  mI2C_END;
wire  mI2C_ACK;
reg [15:0] LUT_DATA;
reg [15:0] LUT_INDEX;
reg [3:0] mSetup_ST;

// Clock Setting
parameter CLK_Freq = 100000000; // 100 MHz
parameter I2C_Freq = 20000;  // 200 KHz
// LUT Data Number
parameter LUT_SIZE = 165;

///////////////////// I2C Control Clock ////////////////////////
always@(posedge iCLK or negedge iRST_N)
begin
 if(!iRST_N)
 begin
  mI2C_CTRL_CLK <= 0;
  mI2C_CLK_DIV <= 0;
 end
 else
 begin
  if( mI2C_CLK_DIV < (CLK_Freq/I2C_Freq) )
  mI2C_CLK_DIV <= mI2C_CLK_DIV+1;
  else
  begin
   mI2C_CLK_DIV <= 0;
   mI2C_CTRL_CLK <= ~mI2C_CTRL_CLK;
  end
 end
end
////////////////////////////////////////////////////////////////////
I2C_Controller  ua ( .CLOCK(mI2C_CTRL_CLK),  // Controller Work Clock
      .I2C_SCLK(I2C_SCLK),  // I2C CLOCK
            .I2C_SDAT(I2C_SDAT),  // I2C DATA
      .I2C_DATA(mI2C_DATA),  // DATA:[SLAVE_ADDR,SUB_ADDR,DATA]
      .GO(mI2C_GO),         // GO transfor
      .END(mI2C_END),    // END transfor
      .ACK(mI2C_ACK),    // ACK
      .RESET(iRST_N) );
////////////////////////////////////////////////////////////////////
/*the slave device 8-bit address. The SADDR pin is used
to select between two different addresses in case of
conflict with another device. If SADDR is LOW, the
slave address is 0x90; if SADDR is HIGH, the slave
address is 0xBA.*/
////////////////////// Config Control ////////////////////////////
reg cmos_finish;
always@(posedge mI2C_CTRL_CLK or negedge iRST_N)
begin
 if(!iRST_N)
 begin
  LUT_INDEX <= 0;
  mSetup_ST <= 0;
  mI2C_GO  <= 0;
  cmos_finish <= 1'b0;
 end
 else
 begin
  if(LUT_INDEX<LUT_SIZE)
  begin
   case(mSetup_ST)
   0: begin
     mI2C_DATA <= {8'h42,LUT_DATA};
     mI2C_GO  <= 1;
     mSetup_ST <= 1;
    end
   1: begin
     if(mI2C_END)
     begin
      if(!mI2C_ACK)
      mSetup_ST <= 2;
      else
      mSetup_ST <= 0;       
      mI2C_GO  <= 0;
     end
    end
   2: begin
     LUT_INDEX <= LUT_INDEX+1;
     mSetup_ST <= 0;
    end
   endcase
  end
  else
   cmos_finish <= 1'b1;
 end
end
////////////////////////////////////////////////////////////////////
///////////////////// Config Data LUT   ////////////////////////// 
always
begin
 case(LUT_INDEX)
 0 : LUT_DATA <= 16'h3a04;
 1 : LUT_DATA <= 16'h40d0;
 2 : LUT_DATA <= 16'h1214; // Mirror Row and Columns
 3 : LUT_DATA <= 16'h3280;
 4 : LUT_DATA <= 16'h1716;
 5 : LUT_DATA <= 16'h1804; // Green 1 Gain
 6 : LUT_DATA <= 16'h1902;
 7 : LUT_DATA <= 16'h1a7b; // Blue Gain
 8 : LUT_DATA <= 16'h0306;
 9 : LUT_DATA <= 16'h0c38; // Red Gain
 10 : LUT_DATA <= 16'h3e00;
 11 : LUT_DATA <= 16'h7000; // Green 2 Gain
 12 : LUT_DATA <= 16'h7100;
 13 : LUT_DATA <= 16'h7211; // H_Blanking
 14 : LUT_DATA <= 16'h7300;
 15 : LUT_DATA <= 16'ha202; // V_Blanking
 16 : LUT_DATA <= 16'h1101;
 17 : LUT_DATA <= 16'h7a20;
 18 : LUT_DATA <= 16'h7b1c;
 19 : LUT_DATA <= 16'h7c28;
 20 : LUT_DATA <= 16'h7d3c;
 21 : LUT_DATA <= 16'h7e55;
 22 : LUT_DATA <= 16'h7f68;
 23 : LUT_DATA <= 16'h8076;
 24 : LUT_DATA <= 16'h8180;
 25 : LUT_DATA <= 16'h8288;
 26 : LUT_DATA <= 16'h838f;
 27 : LUT_DATA <= 16'h8496;
 28 : LUT_DATA <= 16'h85a3;
 29 : LUT_DATA <= 16'h86af;
 30 : LUT_DATA <= 16'h87c4;
 31 : LUT_DATA <= 16'h88d7;
 32 : LUT_DATA <= 16'h89e8;
 33 : LUT_DATA <= 16'h138f;
 34 : LUT_DATA <= 16'h0000;
 35 : LUT_DATA <= 16'h1000;
 36 : LUT_DATA <= 16'h0d00;
 37 : LUT_DATA <= 16'h1410;
 38 : LUT_DATA <= 16'ha505;
 39 : LUT_DATA <= 16'hab07;
 40 : LUT_DATA <= 16'h2475;
 41 : LUT_DATA <= 16'h2563;
 42 : LUT_DATA <= 16'h26a5;
 43 : LUT_DATA <= 16'h9f78;
 44 : LUT_DATA <= 16'ha068;
 45 : LUT_DATA <= 16'ha103;
 46 : LUT_DATA <= 16'ha6df;
 47 : LUT_DATA <= 16'ha7df;
 48 : LUT_DATA <= 16'ha8f0;
 49 : LUT_DATA <= 16'ha990;
 50 : LUT_DATA <= 16'haa94;
 51 : LUT_DATA <= 16'h13e5;
 52 : LUT_DATA <= 16'h0e61;
 53 : LUT_DATA <= 16'h0f4b;
 54 : LUT_DATA <= 16'h1602;
 55 : LUT_DATA <= 16'h1e07;
 56 : LUT_DATA <= 16'h2102;
 57 : LUT_DATA <= 16'h2291;
 58 : LUT_DATA <= 16'h2907; 
 59 : LUT_DATA <= 16'h330b;
 60 : LUT_DATA <= 16'h350b;
 61 : LUT_DATA <= 16'h371d;
 62 : LUT_DATA <= 16'h3871;
 63 : LUT_DATA <= 16'h392a;
 64 : LUT_DATA <= 16'h3c00;
 65 : LUT_DATA <= 16'h4d40;
 66 : LUT_DATA <= 16'h4e20;
 67 : LUT_DATA <= 16'h690c;
 68 : LUT_DATA <= 16'h6b40;
 69 : LUT_DATA <= 16'h7419;
 70 : LUT_DATA <= 16'h8d4f;
 71 : LUT_DATA <= 16'h8e00;
 72 : LUT_DATA <= 16'h8f00;
 73 : LUT_DATA <= 16'h9000;
 74 : LUT_DATA <= 16'h9100;
 75 : LUT_DATA <= 16'h9200;
 76 : LUT_DATA <= 16'h9600;
 77 : LUT_DATA <= 16'h9a80;
 78 : LUT_DATA <= 16'hb084;
 79 : LUT_DATA <= 16'hb10c;
 80 : LUT_DATA <= 16'hb20e;
 81 : LUT_DATA <= 16'hb382;
 82 : LUT_DATA <= 16'hb80a;
 83 : LUT_DATA <= 16'h4314;
 84 : LUT_DATA <= 16'h44f0;
 85 : LUT_DATA <= 16'h4534;
 86 : LUT_DATA <= 16'h4658;
 87 : LUT_DATA <= 16'h4728;
 88 : LUT_DATA <= 16'h483a;
 89 : LUT_DATA <= 16'h5988;
 90 : LUT_DATA <= 16'h5a88;
 91 : LUT_DATA <= 16'h5b44;
 92 : LUT_DATA <= 16'h5c67;
 93 : LUT_DATA <= 16'h5e0e;
 94 : LUT_DATA <= 16'h6404;
 95 : LUT_DATA <= 16'h6520;
 96 : LUT_DATA <= 16'h6605;
 97 : LUT_DATA <= 16'h9404;
 98 : LUT_DATA <= 16'h9508;
 99 : LUT_DATA <= 16'h6c0a;
 100 : LUT_DATA <= 16'h6d55;
 101 : LUT_DATA <= 16'h6e11;
 102 : LUT_DATA <= 16'h6f9f;
 103 : LUT_DATA <= 16'h6a40;
 104 : LUT_DATA <= 16'h0140;
 105 : LUT_DATA <= 16'h0240;
 106 : LUT_DATA <= 16'h13e7;
 107 : LUT_DATA <= 16'h1500; 
 108 : LUT_DATA <= 16'h4f80;
 109 : LUT_DATA <= 16'h5080;
 110 : LUT_DATA <= 16'h5100;
 111 : LUT_DATA <= 16'h5222;
 112 : LUT_DATA <= 16'h535e;
 113 : LUT_DATA <= 16'h5480;
 114 : LUT_DATA <= 16'h589e;
 115 : LUT_DATA <= 16'h4108;
 116 : LUT_DATA <= 16'h3f00;
 117 : LUT_DATA <= 16'h7505;
 118 : LUT_DATA <= 16'h76c5;
 119 : LUT_DATA <= 16'h4c00;
 120 : LUT_DATA <= 16'h7701;
 121 : LUT_DATA <= 16'h3dc2;
 122 : LUT_DATA <= 16'h4b09;
 123 : LUT_DATA <= 16'hc960;
 124 : LUT_DATA <= 16'h4138;
 125 : LUT_DATA <= 16'h5640;
 126 : LUT_DATA <= 16'h3411;//
 127 : LUT_DATA <= 16'h3b02;
 128 : LUT_DATA <= 16'ha489;
 129 : LUT_DATA <= 16'h9600;
 130 : LUT_DATA <= 16'h9730;
 131 : LUT_DATA <= 16'h9820;
 132 : LUT_DATA <= 16'h9930;
 133 : LUT_DATA <= 16'h9a84;
 134 : LUT_DATA <= 16'h9b29;
 135 : LUT_DATA <= 16'h9c03;
 136 : LUT_DATA <= 16'h9d4c;
 137 : LUT_DATA <= 16'h9e3f;
 138 : LUT_DATA <= 16'h7804;
 139 : LUT_DATA <= 16'h7910;
 140 : LUT_DATA <= 16'hc87e; 
 141 : LUT_DATA <= 16'h790a;
 142 : LUT_DATA <= 16'hc880;
 143 : LUT_DATA <= 16'h790b;
 144 : LUT_DATA <= 16'hc801;
 145 : LUT_DATA <= 16'h790b;
 146 : LUT_DATA <= 16'hc801;
 147 : LUT_DATA <= 16'h790c;
 148 : LUT_DATA <= 16'hc820;
 149 : LUT_DATA <= 16'h7909;
 150 : LUT_DATA <= 16'hc820;
 151 : LUT_DATA <= 16'h7909;
 152 : LUT_DATA <= 16'hc820;
 153 : LUT_DATA <= 16'h7909;
 154 : LUT_DATA <= 16'hc880;
 155 : LUT_DATA <= 16'h7902;
 156 : LUT_DATA <= 16'hc8c0;
 157 : LUT_DATA <= 16'h7903;
 158 : LUT_DATA <= 16'hc840;
 159 : LUT_DATA <= 16'h7905;
 160 : LUT_DATA <= 16'hc830;
 161 : LUT_DATA <= 16'h7926;
 162 : LUT_DATA <= 16'h0903;
 163 : LUT_DATA <= 16'h5500;
 164 : LUT_DATA <= 16'h5640; 
 165 : LUT_DATA <= 16'h3b42;

 default:LUT_DATA <= 16'h0000;
 endcase
end
////////////////////////////////////////////////////////////////////
endmodule

posted on 2010-12-05 20:07  创造着  阅读(2926)  评论(0编辑  收藏  举报