谈及运用FPGA技术处理CMOS摄像头捕捉的视频信息,并通过USB2.0接口在电脑屏幕上展示,众多技术发烧友无不眼前一亮。这确实是一项集多种技术于一体的既复杂又充满趣味的工作。
FPGA技术与摄像头的结合
FPGA在视频数据处理方面表现优异。在这个设计案例中,我们需对CMOS摄像头的视频数据进行操作。该摄像头使用LVDS接口,支持通过1至4个数据通道传输8至12位数据。在如安防监控等实际应用中,这项技术能保证图像数据质量上乘。FPGA技术高效处理采集的视频数据,为后续操作奠定基础。其高效之处在于快速的数据采集与存储。
接下来涉及数据在不同时钟域间的存储,不论是写入DDR2还是读取,都涉及对数据的妥善处理。以某个特定视频处理项目为例,确保数据在时钟域间的读写顺畅,对于视频的流畅播放至关重要。
USB2.0在数据传输中的角色
SpiWriteRegister(0x01,0x03,0x01);// soft reset SpiWriteRegister(0x01,0x00,0x00);SpiWriteRegister(0x30,0x34,0x01);SpiWriteRegister(0x30,0x35,0xc2); SpiWriteRegister(0x33,0x0b,0x4c);SpiWriteRegister(0x36,0x64,0x09);SpiWriteRegister(0x36,0x38,0x82); SpiWriteRegister(0x3d,0x08,0x00);SpiWriteRegister(0x36,0x40,0x03);SpiWriteRegister(0x36,0x28,0x07); SpiWriteRegister(0x32,0x05,0x93); //rnc SpiWriteRegister(0x36,0x20,0x42);SpiWriteRegister(0x36,0x23,0x06);SpiWriteRegister(0x36,0x27,0x02); SpiWriteRegister(0x36,0x21,0x28);SpiWriteRegister(0x36,0x3b,0x00);SpiWriteRegister(0x36,0x33,0x24); SpiWriteRegister(0x36,0x34,0xff); //fpn optimize SpiWriteRegister(0x34,0x16,0x10);SpiWriteRegister(0x3e,0x03,0x0b);SpiWriteRegister(0x3e,0x08,0x03); SpiWriteRegister(0x3e,0x09,0x20);SpiWriteRegister(0x3e,0x01,0x23); SpiWriteRegister(0x3e,0x14,0xb0);SpiWriteRegister(0x33,0x0b,0x40);SpiWriteRegister(0x3e,0x08,0x3f); SpiWriteRegister(0x36,0x3b,0x80);SpiWriteRegister(0x36,0x23,0x07);SpiWriteRegister(0x50,0x00,0x01); SpiWriteRegister(0x3e,0x01,0x00);SpiWriteRegister(0x3e,0x02,0x30);SpiWriteRegister(0x32,0x0c,0x05); SpiWriteRegister(0x32,0x0d,0x46);SpiWriteRegister(0x32,0x0e,0x02); SpiWriteRegister(0x32,0x0f,0x58);SpiWriteRegister(0x36,0x38,0x85);SpiWriteRegister(0x33,0x06,0x50); SpiWriteRegister(0x33,0x0b,0x68);SpiWriteRegister(0x33,0x08,0x10);SpiWriteRegister(0x3e,0x01,0x00); SpiWriteRegister(0x36,0x3b,0x00);SpiWriteRegister(0x36,0x63,0xf8);SpiWriteRegister(0x36,0x64,0x0a); SpiWriteRegister(0x36,0x33,0x27);SpiWriteRegister(0x30,0x3a,0x3a); SpiWriteRegister(0x30,0x3a,0x3a);SpiWriteRegister(0x30,0x3a,0x3a);SpiWriteRegister(0x30,0x3a,0x3a); SpiWriteRegister(0x36,0x3b,0x00);SpiWriteRegister(0x34,0x16,0x38);SpiWriteRegister(0x3e,0x08,0x23); SpiWriteRegister(0x3c,0x00,0x41); //FIFO RESET for mipi SpiWriteRegister(0x30,0x19,0x00); SpiWriteRegister(0x30,0x31,0x0a); // 10bit SpiWriteRegister(0x30,0x00,0x00);SpiWriteRegister(0x30,0x01,0x00);SpiWriteRegister(0x30,0x39,0x20); SpiWriteRegister(0x30,0x3a,0x31);SpiWriteRegister(0x30,0x3b,0x02);SpiWriteRegister(0x30,0x3c,0x08); SpiWriteRegister(0x4b,0x00,0xa2); //must SpiWriteRegister(0x30,0x22,0x19); //must SpiWriteRegister(0x30,0x3f,0x01); //must SpiWriteRegister(0x30,0x30,0x04); //must SpiWriteRegister(0x30,0x2b,0xa0); //must SpiWriteRegister(0x36,0x20,0x43);SpiWriteRegister(0x36,0x21,0x18);SpiWriteRegister(0x45,0x01,0xc0); SpiWriteRegister(0x45,0x02,0x16); //br recieve inv off SpiWriteRegister(0x36,0x23,0x07);SpiWriteRegister(0x50,0x00,0x01);SpiWriteRegister(0x36,0x20,0x43); SpiWriteRegister(0x33,0x00,0x30);SpiWriteRegister(0x3e,0x01,0x14);SpiWriteRegister(0x36,0x3b,0x80); SpiWriteRegister(0x36,0x64,0x0a);SpiWriteRegister(0x3e,0x08,0x23); SpiWriteRegister(0x34,0x16,0x00);SpiWriteRegister(0x36,0x33,0x20); SpiWriteRegister(0x36,0x33,0x23);SpiWriteRegister(0x32,0x11,0x0c);SpiWriteRegister(0x3e,0x0f,0x05); SpiWriteRegister(0x36,0x3b,0x08); //fpn SpiWriteRegister(0x36,0x33,0x22); //nvdd SpiWriteRegister(0x33,0x02,0x0c);//rst go low SpiWriteRegister(0x33,0x83,0x0a);// pbias en rise edge SpiWriteRegister(0x36,0x23,0x04); SpiWriteRegister(0x33,0x82,0x0f); //sa fall edge SpiWriteRegister(0x3e,0x0f,0x84); //gain SpiWriteRegister(0x3e,0x0e,0x03); //gain SpiWriteRegister(0x3e,0x08,0x27);SpiWriteRegister(0x3e,0x08,0x23);SpiWriteRegister(0x36,0x64,0x05); SpiWriteRegister(0x33,0x0b,0x68); SpiWriteRegister(0x36,0x38,0x84);SpiWriteRegister(0x5b,0x00,0x02);SpiWriteRegister(0x5b,0x01,0x03); SpiWriteRegister(0x5b,0x02,0x01);SpiWriteRegister(0x5b,0x03,0x01);SpiWriteRegister(0x36,0x3b,0x02); SpiWriteRegister(0x36,0x32,0x54);SpiWriteRegister(0x36,0x33,0x32);SpiWriteRegister(0x34,0x16,0x0e); SpiWriteRegister(0x36,0x64,0x0e);SpiWriteRegister(0x36,0x63,0x88);SpiWriteRegister(0x33,0x0b,0x50); SpiWriteRegister(0x36,0x22,0x06); //blksun SpiWriteRegister(0x36,0x30,0xb3);SpiWriteRegister(0x34,0x16,0x11);SpiWriteRegister(0x01,0x00,0x01);
USB2.0在此处扮演着至关重要的角色。我们公司的EZ-USB FX2性能卓越,是全球首个整合USB2.0技术的微处理器。它集成了众多功能,例如USB2.0收发器等。在数据传输过程中,若将FX2视为USB2.0接口进行高速通信,便可以运用Slave FIFO传输模式。以传输大量视频数据为例,此方法能有效提升传输效率。
在这种模式下,8051固件主要承担设置相关寄存器的任务。这好比一个团队中各成员各尽其责,8051固件专注于自己的领域,保障USB2.0传输在Slave FIFO模式下能够顺畅进行。
开发平台与工具
开发EZ-USB驱动程序需要特定的工具支持。比如,微软的WDW DDK和VC++就是必不可少的。DDK是可以获取到的资源。至于USB2.0的固件程序,则是在KEIL平台上进行的。KEIL这个平台对于从事相关工作的人来说很熟悉。在这个项目中,有三个关键的源文件,它们是构建整个程序的关键组成部分。
在一个研发团队里,各个开发人员各自在各自的平台上负责开发不同的模块。只有将这些模块最终拼接在一起,视频数据才能通过USB2.0接口在电脑屏幕上正确显示,系统才能正常运行。
数据的同步操作
为了确保USB PHY芯片与FPGA的同步,我们采用视频信号中的场同步信号vsync进行同步,并借助68013的INT0引脚来引发中断。以处理高清视频数据为例,数据同步至关重要,否则画面可能会出现撕裂或卡顿。在实际操作中,需要使用特定的中断函数,目的在于保证数据传输的精确性和处理的高效性。
代码编译与文件固化
完成代码设计后,需完成两项关键步骤。首先,需编译代码生成HEX文件,该文件用于调试和下载至ram。其次,要生成IIC文件,此文件用于固件固化。此外,固化IIC文件还需使用特定工具,且这些工具的使用也有特定规范。在操作过程中,若开发人员操作不当,可能导致固化失败,进而影响项目整体进度。
;for x64 platforms [Device.NTamd64] %VID_2017&PID_0328.DeviceDesc%=CyUsb, USBVID_2017&PID_0328 [Strings] CYUSB_Provider = "Cypress" CYUSB_Company = "Cypress Semiconductor Corporation" CYUSB_Description = "Cypress Generic USB Driver" CYUSB_DisplayName = "Cypress USB Generic" CYUSB_Install = "Cypress CYUSB Driver Installation Disk" VID_2017&PID_0328.DeviceDesc="Shugen_VIP Device" CYUSB.GUID="{AE18AA60-7F6A-11d4-97DD-00010229B959}" CYUSB_Unused = "."
上位机程序的开发
在实践操作中,我们可以运用VC++来编写应用软件。在开发68013主控程序时,官方提供的API函数和驱动程序显得尤为关键。例如,传输端点控制类等众多类在程序构建中扮演着各自的角色。传输端点控制类能够管理数据传输的端点连接等任务,各类之间相互配合,共同构成了一个完整的主控程序。
观察这复杂而又井然有序的技术融合,我们不禁要问:若是在某个环节引入新技术,整个流程又将产生怎样的转变?不妨点赞、留言或转发本篇文章。
void ISR_EXTR0(void) interrupt 0 //using 0 { if(frame_sign == 1){ PA1 = 1; //Enable p_w_picpath input } else { PA1 = 0; //Disable p_w_picpath input //Reset FIFO of EDP2 SYNCDELAY; FIFORESET = 0x80;// activate NAK-ALL to avoid race conditions SYNCDELAY; FIFORESET = 0x02;// reset, FIFO 2 SYNCDELAY; FIFORESET = 0x00;// deactivate NAK-AL SYNCDELAY; } }