Академический Документы
Профессиональный Документы
Культура Документы
The AXI OV7670 Decoder provides an AXI interface decoder for the output of the
OmniVision OV7670 VGA video camera. The decoder provides a bridge between the
camera input and video processing cores with AXI4-Stream Video Protocol interfaces. It
also provides a software based camera configuration core.
This IP is largely based on the codes provided in class and on the Xilinx LogiCORE IP
Video In to AXI4-Stream.
It is of great importance to fully read this document before trying to use the IP. It is highly
recommend to read the datasheets for the Xilinx IPs mentioned in this document.
This IP was designed to operate with the Digilent Nexys4 DDR FPGA board and Vivado
2014.1
DISCLAIMER
1
AXI OV7670 Decoder
Chapter 1: Overview
CHAPTER 1: OVERVIEW
Functional Description
The AXI OV7670 Decoder provides an AXI4-Stream Video Protocol for the input of the
OV7670 camera and a software based camera configuration.
The top-level block diagram of the AXI OV7670 Decoder is shown in Figure 1.
I2C_AV_CONFIG
AXI4-Lite Interface
The AXI4-Lite Interface implements a 32-bit AXI4-Lite slave interface for changing
between the RGB colour formats available with the camera, writing the camera
configuration and soft reset of the camera configuration. A Memory Write Logic is needed
to translate the information at the input registers to the internal memory.
2
AXI OV7670 Decoder
Chapter 1: Overview
AXI4-Stream Interface
The AXI4-Stream Interface implements a 32-bit AXI4-Stream Video Protocol master
interface. It consists of parallel video data (tdata), handshaking signals (tvalid and tready)
and two flags (tlast and tuser). The flag tlast corresponds to the video protocol signal end
of line (EOL) and the flag tuser corresponds to the video protocol start of frame (SOF).
The Xilinx IP Video In to AXI4-Stream generates this interface. The output is a 32-bit pixel
RGB888, with 8 bits 0 added at the 8 MSBs.
I2C_AV_Config
This block implements the I2C standard for the camera configuration. It is based on the
code provided in class. A BRAM memory is used instead of a Look-up Table, allowing for
modifications via software.
Video In (pre-decoder)
This block provides a bridge between the camera data and timing signals to the expected
input of the Video In to AXI4-Stream IP. It is based on the code provided in class.
3
AXI OV7670 Decoder
Chapter 2: Product Specification
Performance
The core was implemented in an Artix-7 xc7a100tcsg324-1 with a 100 MHz clock
frequency.
Resource Utilization
Table 1 - Device Resources Utilization (Post-Implementation)
Device Resources
Flip-Flops LUTs Memory LUTs BRAM
417 349 97 1
Port Descriptions
The AXI OV7670 Decoder I/O signals are listed and described in Table 2.
4
AXI OV7670 Decoder
Chapter 2: Product Specification
Register Space
The AXI OV7670 Decoder registers are shown in Table 3.
31 24 23 16 15 8 7 0
5
AXI OV7670 Decoder
Chapter 2: Product Specification
31 1 0
31 3 2 0
6
AXI OV7670 Decoder
Chapter 3: Designing with the Core
Operation
The camera inputs and outputs should be connected to this core. One camera input still
needs to be connected externally. This input (OV7670_XCLK) connects to the system
clock. The Stream interface should be connected to the next component of the dataflow,
usually an AXI4-Stream Interconnect or the Video DMA. The AXI4-Lite interface should
be connected as a Slave to the microprocessor.
Programming Sequence
Before using the video data, the camera must be configured. The code provided in
Appendix A is an example of the camera configuration code. The camera datasheet must
be consulted for more information. After the initial configuration, any memory position can
be changed but the I2C Controller must be reset. The second slave register provides the
microprocessor with such reset option. The decoder type at the third slave register must
match with the video data configured on the camera.
Clocking
The AXI OV7670 Decoder has three clock domains:
s_axi_aclk Associates with the AXI4-Lite slave interface.
m_axis_aclk Associates with the AXI4-Stream master interface.
pclk Camera pixel clock.
The two AXI clocks can be the same. The clock domain crossing is handled by the Video
In to AXI-Stream IP.
Resets
Similarly to the clocks, the AXI OV7670 Decoder has two active-Low resets, one for each
AXI interface. The camera configuration reset can be used when it is wanted to run the
I2C configuration again. It can be achieved by software using slv_reg1 or by hardware
using the input reset. Both are active High.
7
AXI OV7670 Decoder
Chapter 4: Example Design
The example design is a Video In / Video Out design. This IP is used as a bridge between
the camera output and the AXI4-Stream Interface. It is connected to a Video DMA via an
AXI4-Stream Interconnect. The VDMA moves the video data to the memory. The image
is displayed using the TFT Controller IP.
Figure 5 is a high-level view of the video data flow of this design.
AXI Interconnect
AXI4-Stream
8
AXI OV7670 Decoder
Appendix
The following code is used to test the IP. The function config_OV7670 has the camera
configuration. It can be used as default code and new configurations can be added after
the comment // Mirror (this line is inverting the camera output).
#include <stdio.h>
#include "platform.h"
#include "xparameters.h"
void config_OV7670() {
decoder[1] = 0;
decoder[0] = 0x000000;
decoder[0] = 0x010000;
decoder[0] = 0x023a04;
decoder[0] = 0x033dc8;
decoder[0] = 0x041e31;
decoder[0] = 0x056b00;
decoder[0] = 0x0632b6;
decoder[0] = 0x071713;
decoder[0] = 0x081801;
decoder[0] = 0x091902;
decoder[0] = 0x0A1a7a;
decoder[0] = 0x0B030a;
decoder[0] = 0x0C0c00;
decoder[0] = 0x0D3e00;
decoder[0] = 0x0E7000;
decoder[0] = 0x0F7100;
decoder[0] = 0x107211;
decoder[0] = 0x117300;
decoder[0] = 0x12a202;
decoder[0] = 0x131180;
decoder[0] = 0x147a20;
decoder[0] = 0x157b1c;
decoder[0] = 0x167c28;
decoder[0] = 0x177d3c;
decoder[0] = 0x187e55;
decoder[0] = 0x197f68;
decoder[0] = 0x1A8076;
decoder[0] = 0x1B8180;
decoder[0] = 0x1C8288;
decoder[0] = 0x1D838f;
decoder[0] = 0x1E8496;
decoder[0] = 0x1F85a3;
decoder[0] = 0x2086af;
decoder[0] = 0x2187c4;
decoder[0] = 0x2288d7;
decoder[0] = 0x2389e8;
decoder[0] = 0x2413e0;
decoder[0] = 0x250000;
decoder[0] = 0x261000;
decoder[0] = 0x270d00;
decoder[0] = 0x281428;
decoder[0] = 0x29a505;
decoder[0] = 0x2Aab07;
decoder[0] = 0x2B2475;
decoder[0] = 0x2C2563;
decoder[0] = 0x2D26a5;
decoder[0] = 0x2E9f78;
decoder[0] = 0x2Fa068;
decoder[0] = 0x30a103;
decoder[0] = 0x31a6df;
decoder[0] = 0x32a7df;
decoder[0] = 0x33a8f0;
decoder[0] = 0x34a990;
decoder[0] = 0x35aa94;
decoder[0] = 0x3613ef;
9
AXI OV7670 Decoder
Appendix
decoder[0] = 0x370e61;
decoder[0] = 0x380f4b;
decoder[0] = 0x391602;
decoder[0] = 0x3A2102;
decoder[0] = 0x3B2291;
decoder[0] = 0x3C2907;
decoder[0] = 0x3D330b;
decoder[0] = 0x3E350b;
decoder[0] = 0x3F371d;
decoder[0] = 0x403871;
decoder[0] = 0x41392a;
decoder[0] = 0x423c78;
decoder[0] = 0x434d40;
decoder[0] = 0x444e20;
decoder[0] = 0x456900;
decoder[0] = 0x467419;
decoder[0] = 0x478d4f;
decoder[0] = 0x488e00;
decoder[0] = 0x498f00;
decoder[0] = 0x4A9000;
decoder[0] = 0x4B9100;
decoder[0] = 0x4C9200;
decoder[0] = 0x4D9600;
decoder[0] = 0x4E9a80;
decoder[0] = 0x4Fb084;
decoder[0] = 0x50b10c;
decoder[0] = 0x51b20e;
decoder[0] = 0x52b382;
decoder[0] = 0x53b80a;
decoder[0] = 0x544314;
decoder[0] = 0x5544f0;
decoder[0] = 0x564534;
decoder[0] = 0x574658;
decoder[0] = 0x584728;
decoder[0] = 0x59483a;
decoder[0] = 0x5A5988;
decoder[0] = 0x5B5a88;
decoder[0] = 0x5C5b44;
decoder[0] = 0x5D5c67;
decoder[0] = 0x5E5d49;
decoder[0] = 0x5F5e0e;
decoder[0] = 0x606404;
decoder[0] = 0x616520;
decoder[0] = 0x626605;
decoder[0] = 0x639404;
decoder[0] = 0x649508;
decoder[0] = 0x659508;
decoder[0] = 0x666d55;
decoder[0] = 0x676e11;
decoder[0] = 0x686f9f;
decoder[0] = 0x696a40;
decoder[0] = 0x6A0140;
decoder[0] = 0x6B0240;
decoder[0] = 0x6C13e7;
decoder[0] = 0x6D1500;
decoder[0] = 0x6E4f80;
decoder[0] = 0x6F5080;
decoder[0] = 0x705100;
decoder[0] = 0x715222;
decoder[0] = 0x72535e;
decoder[0] = 0x735480;
decoder[0] = 0x74589e;
decoder[0] = 0x754108;
decoder[0] = 0x763f00;
decoder[0] = 0x777505;
decoder[0] = 0x7876e1;
decoder[0] = 0x794c00;
decoder[0] = 0x7A7701;
decoder[0] = 0x7B4b09;
decoder[0] = 0x7Cc9F0;
decoder[0] = 0x7D4138;
decoder[0] = 0x7E5640;
decoder[0] = 0x7F3411;
decoder[0] = 0x803b02;
decoder[0] = 0x81a489;
decoder[0] = 0x829600;
decoder[0] = 0x839730;
decoder[0] = 0x849820;
decoder[0] = 0x859930;
decoder[0] = 0x869a84;
decoder[0] = 0x879b29;
10
AXI OV7670 Decoder
Appendix
decoder[0] = 0x889c03;
decoder[0] = 0x899d4c;
decoder[0] = 0x8A9e3f;
decoder[0] = 0x8B7804;
decoder[0] = 0x8C7901;
decoder[0] = 0x8Dc8f0;
decoder[0] = 0x8E790f;
decoder[0] = 0x8Fc800;
decoder[0] = 0x907910;
decoder[0] = 0x91c87e;
decoder[0] = 0x92790a;
decoder[0] = 0x93c880;
decoder[0] = 0x94790b;
decoder[0] = 0x95c801;
decoder[0] = 0x96790c;
decoder[0] = 0x97c80f;
decoder[0] = 0x98790d;
decoder[0] = 0x99c820;
decoder[0] = 0x9A7909;
decoder[0] = 0x9Bc880;
decoder[0] = 0x9C7902;
decoder[0] = 0x9Dc8c0;
decoder[0] = 0x9E7903;
decoder[0] = 0x9Fc840;
decoder[0] = 0xA07905;
decoder[0] = 0xA1c830;
decoder[0] = 0xA27926;
decoder[0] = 0xA30903;
decoder[0] = 0xA43b42;
decoder[0] = 0xA58c02;
decoder[0] = 0xA640d0;
decoder[0] = 0xA71204;
11
AXI OV7670 Decoder
Appendix
decoder[0] = 0xD80000;
decoder[0] = 0xD90000;
decoder[0] = 0xDA0000;
decoder[0] = 0xDB0000;
decoder[0] = 0xDC0000;
decoder[0] = 0xDD0000;
decoder[0] = 0xDE0000;
decoder[0] = 0xDF0000;
decoder[0] = 0xE00000;
decoder[0] = 0xE10000;
decoder[0] = 0xE20000;
decoder[0] = 0xE30000;
decoder[0] = 0xE40000;
decoder[0] = 0xE50000;
decoder[0] = 0xE60000;
decoder[0] = 0xE70000;
decoder[0] = 0xE80000;
decoder[0] = 0xE90000;
decoder[0] = 0xEA0000;
decoder[0] = 0xEB0000;
decoder[0] = 0xEC0000;
decoder[0] = 0xED0000;
decoder[0] = 0xEE0000;
decoder[0] = 0xEF0000;
decoder[0] = 0xF00000;
decoder[0] = 0xF10000;
decoder[0] = 0xF20000;
decoder[0] = 0xF30000;
decoder[0] = 0xF40000;
decoder[0] = 0xF50000;
decoder[0] = 0xF60000;
decoder[0] = 0xF70000;
decoder[0] = 0xF80000;
decoder[0] = 0xF90000;
decoder[0] = 0xFA0000;
decoder[0] = 0xFB0000;
decoder[0] = 0xFC0000;
decoder[0] = 0xFD0000;
decoder[0] = 0xFE0000;
decoder[0] = 0xFF0000;
int main ()
{
init_platform();
config_OV7670();
vdma[12] = 0x0000000B; // enable vdma
vdma[43] = 0x80000000; // write base address
vdma[42] = 4*1024; // stride (bytes)
vdma[41] = 4*640; // image size (bytes)
vdma[40] = 512; // number of lines
*AR = 0x80000000;//output;
//decoder[0] = 0xA98C00; // no RGB444. Other formats only work if RGB444 is disabled.
//decoder[0] = 0xAA40F0; // RGB555
//decoder[0] = 0xAB40D0; // RGB565
decoder[2] = 0; // 0 = RGB444, 1 = RGB555, 2 = RGB565
return 0;
}
12
AXI OV7670 Decoder
Appendix
During the implementation of this IP, four critical warnings will show up. Those are
[Common 17-55], [Vivado 12-259], [Vivado 12-1387], [Memdata 28-122]. During
the bitstream generation the last warning and the error [Memdata 28-96] will also
appear. All those can be ignored. The first three are related to hierarchical
constraints and the other are related to the fact that the internal memory has no
bmm file linked to it. Fixing these warning is one of the to do activities for this IP.
Video decoding is accomplished by simply shifting bits. Depending on the
application, this is not a good strategy. Bytes for YUV and YCbCr colour spaces
are not described in the preliminary camera datasheet. Fixing and expanding the
decoding capabilities of this IP is another to do activity.
There is no API other than the default API generated by SDK. No time for that
either.
13
AXI OV7670 Decoder