diff --git a/README.md b/README.md index 64e3f9a..24f363a 100644 --- a/README.md +++ b/README.md @@ -14,7 +14,7 @@ IO扩展版提供了 - 6个编码器或IO输入,本次项目为1个编码器输入、1个物体传感器输入,其余冗余 - 8个阀板接口,本次项目没有用到 -接线时,12V电源连接到IO扩展板的电源接口,阀板从左到右应连接在阀板接口1~6上,相机线应连接相机触发接口`TRIG1`和对应的`GND`接口,编码器线应连接在编码器输入接口`E1`和对应的`GND`接口。注意底板不连接任何外部电源。 +接线时,12V电源连接到IO扩展板的电源接口,相机线应连接相机触发接口`TRIG1`、`TRIG2`和对应的`GND`接口,编码器线应连接在编码器输入接口`E1`和对应的`GND`接口,物体传感器应连接输入接口`E3`和对应的`GND`接口。注意底板不连接任何外部电源。 开发和部署说明见[doc/develop_and_deploy.md](doc/develop_and_deploy.md) @@ -70,7 +70,7 @@ b分支编号-p生产环境项目名-t分选对象[-其他特点1[-其他特点2 b分支编号-d文档版本-hPCB设计版本-lFPGA设计版本-p协议版本-s脚本版本-aAPP代码版本-i驱动版本-c系统编译配置版本-e设备树版本 ``` -分支编号和分支命名中编号一致。各部分版本应在相应目录下创建文件注明,比如`2.1`版本的PCB设计:PCB工程目录中建立`version`文本文件,内容为文本`2.1`。对于涉及整体设计的大改动版本号加`1`,其余改动版本号加`0.1`。每个分支的版本各自独立,新分支的版本从`1.0`起计算 +分支编号和分支命名中编号一致。各部分版本应在相应目录下创建文件注明,比如`2.1`版本的PCB设计:PCB工程目录中建立`version`文本文件,内容为文本`2.1`。对于涉及整体设计的大改动版本号加`1`,其余改动版本号加`0.1`。每个分支的版本各自独立,新分支的版本从`1.0`起计算,也可从建立分支处原有版本起计算 ## 作者 diff --git a/doc/develop_and_deploy.md b/doc/develop_and_deploy.md index 9afde2c..afdcf4d 100644 --- a/doc/develop_and_deploy.md +++ b/doc/develop_and_deploy.md @@ -2,11 +2,26 @@ ## 开发 -本次开发基于zynq xc7z010-1clg400芯片,因此FPGA设计软件为Vitis中包含的[Vivado 2022.1](https://china.xilinx.com/support/download/index.html/content/xilinx/zh/downloadNav/vitis.html),Linux编译工具为[petalinux 2022.2](https://china.xilinx.com/support/download/index.html/content/xilinx/zh/downloadNav/embedded-design-tools.html),Linux应用程序编译工具为linaro的[arm-linux-gnueabihf-gcc 12.2.1](https://snapshots.linaro.org/gnu-toolchain/12.2-2023.04-1/)。 +本次开发基于zynq `xc7z010-1clg400`芯片,因此FPGA设计软件为Vitis中包含的[Vivado 2022.1](https://china.xilinx.com/support/download/index.html/content/xilinx/zh/downloadNav/vitis.html),Linux编译工具为[petalinux 2022.2](https://china.xilinx.com/support/download/index.html/content/xilinx/zh/downloadNav/embedded-design-tools.html),Linux应用程序编译工具为linaro的[arm-linux-gnueabihf-gcc 12.2.1](https://snapshots.linaro.org/gnu-toolchain/12.2-2023.04-1/)。 ### 生成硬件描述文件 -见[doc/hardware_description.md](hardware_description.md) +1. 下载[hardware/pl_platform](../hardware/pl_platform)文件夹到家目录,这里假设用户为miaow
在vivado 2022.1中执行tcl脚本,复原工程 + ```tcl + source /home/miaow/pl_platform/lower_machine.tcl + ``` + +2. 重新生成`block design`的`output products` + +3. 生成`bitstream`后创建硬件描述文件,命令为 + ```tcl + # 下面命令中32为计算机逻辑内核数,按实际设定 + launch_runs impl_1 -to_step write_bitstream -jobs 32 + + # 生成硬件描述文件 + write_hw_platform -fixed -include_bit -force -file /home/miaow/zynq/vivado_git/lower_machine/system_wrapper.xsa + ``` + 硬件描述文件为`system_wrapper.xsa` ### 创建PETALINUX工程 @@ -17,7 +32,7 @@ $ petalinux-create -t project --template zynq -n ps-linux ``` -2. 上传硬件描述文件[source/petalinux_hwdescription/system_wrapper.xsa](source/petalinux_hwdescription/system_wrapper.xsa)到`ps-linux`目录中并config +2. 上传release中的硬件描述文件`system_wrapper.xsa`到`ps-linux`目录中并config ```shell system_wrapper.xsa上传到~/ps-linux @@ -53,17 +68,15 @@ # └─Copy final images to tftpboot (不选) ``` -4. 创建两个模块 +4. 创建一个模块 ```shell - $ petalinux-create -t modules --name fifo --enable $ petalinux-create -t modules --name encoder --enable ``` -1. 分别上传驱动代码[source/linux_driver/fifo.c](../source/linux_driver/fifo.c)和[source/linux_driver/encoder.c](../source/linux_driver/encoder.c)到下面的目录中 +1. 上传驱动代码[source/linux_driver/encoder.c](../source/linux_driver/encoder.c)到下面的目录中 ```shell - ~/ps-linux/project-spec/meta-user/recipes-modules/fifo/files ~/ps-linux/project-spec/meta-user/recipes-modules/encoder/files ``` @@ -75,7 +88,7 @@ 上传source/petalinux_devicetree/system-user.dtsi ``` -2. 配置kernel,使用命令`petalinux-config -c kernel`,按下面提示或[source/petalinux_config/kernel.cfg](../source/petalinux_config/kernel.cfg)配置 +2. 配置`kernel`,使用命令`petalinux-config -c kernel`,按下面提示或[source/petalinux_config/kernel.cfg](../source/petalinux_config/kernel.cfg)配置 ```shell # File systems @@ -90,7 +103,7 @@ # └─OTG support (勾选为星号) ``` -3. 配置rootfs,使用命令`petalinux-config -c rootfs`,按下面提示或[source/petalinux_config/rootfs_config](../source/petalinux_config/rootfs_config)配置 +3. 配置`rootfs`,使用命令`petalinux-config -c rootfs`,按下面提示或[source/petalinux_config/rootfs_config](../source/petalinux_config/rootfs_config)配置 ```shell # Filesystem Packages @@ -190,18 +203,17 @@ # ├─imagefeature-package-management (勾选为星号) # modules # ├─encoder (不选) - # ├─fifo (不选) # PetaLinux RootFS Settings # ├─ADD_EXTRA_USERS (root:3703;petalinux:3703;) # ├─ADD_USERS_TO_GROUPS (petalinux:audio,video;) # └─ADD_USERS_TO_SUDOERS (petalinux) ``` -8. 替换`~/ps-linux/project-spec/meta-user/recipes-bsp/u-boot/files/platform-top.h`为[platform-top.h](./petalinux_config/platform-top.h),用于添加u-boot所需的环境变量,实现动态加载比特流文件 +8. 替换`~/ps-linux/project-spec/meta-user/recipes-bsp/u-boot/files/platform-top.h`为[platform-top.h](../source/petalinux_config/platform-top.h),用于添加u-boot所需的环境变量,实现动态加载比特流文件 ### 编译系统 -1. 编译工程,使用命令`petalinux-build`。编译完成,在当前工程目录下生成images文件夹,该命令将生成设备树文件、FSBL文件、U-Boot文件,Linux Kernel文件和rootfs文件镜像 +1. 编译工程,使用命令`petalinux-build`。编译完成,在当前工程目录下生成`images`文件夹,该命令将生成设备树文件、`FSBL`文件、`U-Boot`文件,`Linux Kernel`文件和`rootfs`文件镜像 2. 制作BOOT.BIN启动文件,具体命令如下: @@ -213,14 +225,13 @@ ### 编译驱动 -依次运行如下命令,单独编译3个驱动程序 +依次运行如下命令,编译驱动程序 ```shell -$ petalinux-build -c fifo $ petalinux-build -c encoder ``` -编译后的模块文件为` ps-linux/build/tmp/sysroots-components/zynq_generic/fifo/lib/modules/5.15.36-xilinx-v2022.2/extra/fifo.ko`和`ps-linux/build/tmp/sysroots-components/zynq_generic/encoder/lib/modules/5.15.36-xilinx-v2022.2/extra/encoder.ko` +编译后的模块文件为`ps-linux/build/tmp/sysroots-components/zynq_generic/encoder/lib/modules/5.15.36-xilinx-v2022.2/extra/encoder.ko` ### 编译应用程序 @@ -241,8 +252,6 @@ $ make CROSS_COMPILE=交叉编译工具链前缀 ### 修改文件系统 -> 注意:github的release中包含了修改完成的rootfs.tar.gz,因此无需重复本节的步骤,本节仅用作记录修改步骤 - 1. 给SD卡创建DOS分区表,然后分2个区并创建文件系统,细节如下表: | 扇区 | 大小 | 分区类型 | 文件系统 | 卷标 | @@ -250,15 +259,17 @@ $ make CROSS_COMPILE=交叉编译工具链前缀 | 2048~x扇区 | 100M | C W95 FAT32 (LBA) | FAT32 | boot | | x扇区~最后扇区 | ≈SD卡大小-100M | 83 Linux | ext4 | rootfs | -2. 将打包和编译得到的BOOT.BIN、boot.scr、system.bit和image.ub复制到boot分区;将rootfs.tar.gz解压到rootfs分区 +2. 将打包和编译得到的`BOOT.BIN`、`boot.scr`、`system.bit`和`image.ub`复制到`boot`分区;将`rootfs.tar.gz`解压到`rootfs`分区 - > 注意: 这里的system.bit为比特流文件,可以由petalinux从XSA文件中提取,也可以是vivado生成的,注意命名为system.bit。 + 这里的`system.bit`为比特流文件,可以由`petalinux`从`XSA`文件中提取,也可以是`vivado`生成的,注意重命名为`system.bit`。 3. 拨码开关拨到SD卡启动,插入SD卡到XME0724底板上,上电启动。 4. 终端软件连接底板上的串口,波特率115200,8位,1停止位,无校验 -5. 修改/etc/shadow文件,将root用户的密码删除,切换到root用户并设定密码为3703,具体命令如下: +> 注意:github的release中包含了修改完成的`rootfs.tar.gz`,因此无需重复下面的步骤,这里仅用作记录修改步骤 + +5. 修改`/etc/shadow`文件,将`root`用户的密码删除,切换到`root`用户并设定密码为`3703`,具体命令如下: ```shell $ sudo sed "1c root::15069:0:99999:7:::" /etc/shadow @@ -268,7 +279,7 @@ $ make CROSS_COMPILE=交叉编译工具链前缀 ``` -6. 配置网络和ssh服务,用root登录: +6. 配置网络和`ssh`服务,用`root`登录: ```shell $ vi /etc/network/interfaces @@ -293,17 +304,14 @@ $ make CROSS_COMPILE=交叉编译工具链前缀 $ sshpass -p "3703" ssh root@192.168.10.10 -p 22 ``` -8. 安装编译得到的驱动文件fifo.ko和encode.ko,并设置自动加载,对应自启脚本可以如下方式写入,也可以直接上传[script/loadfifo.sh](../script/loadfifo.sh)和[script/loadencoder.sh](../script/loadencoder.sh),ssh方式,root登录: +8. 安装编译得到的驱动文件`encode.ko`,并设置自动加载,对应自启脚本可以如下方式写入,也可以直接上传[script/loadencoder.sh](../script/loadencoder.sh),ssh方式,`root`登录: ```shell - 上传fifo.ko、encoder.ko到/lib/modules/[内核版本]/kernel/drivers/ + 上传encoder.ko到/lib/modules/[内核版本]/kernel/drivers/ $ cd /lib/modules/[内核版本]; depmod $ set +H - $ echo -e "#!/bin/sh\nmodprobe fifo" > /etc/init.d/loadfifo.sh $ echo -e "#!/bin/sh\nmodprobe encoder" > /etc/init.d/loadencoder.sh - $ chmod 755 /etc/init.d/loadfifo.sh /etc/init.d/loadencoder.sh $ cd /etc/rc5.d - $ ln -s ../init.d/loadfifo.sh S20loadfifo.sh $ ln -s ../init.d/loadencoder.sh S20loadencoder.sh ``` @@ -322,35 +330,35 @@ $ make CROSS_COMPILE=交叉编译工具链前缀 $ ln -s ../init.d/target.sh S99target.sh ``` -10. \[可选\] 设置.bashrc,修改PS1,对应脚本见[script/.profile](../script/.profile)和[script/.bashrc](../script/.bashrc) +10. \[可选\] 设置`.bashrc`,修改`PS1`,对应脚本见[script/.profile](../script/.profile)和[script/.bashrc](../script/.bashrc) - ```shell - $ cd ~; rm .bashrc .profile - 上传.bashrc和.profile到/home/root - $ if [ ! -a /home/petalinux/.profile ]; then cp /home/root/.profile /home/petalinux/ fi - $ if [ ! -a /home/petalinux/.bashrc ]; then cp /home/root/.bashrc /home/petalinux/ & chown petalinux:petalinux -R /home/petalinux fi - $ source ~/.profile - ``` + ```shell + $ cd ~; rm .bashrc .profile + 上传.bashrc和.profile到/home/root + $ if [ ! -a /home/petalinux/.profile ]; then cp /home/ root/.profile /home/petalinux/ fi + $ if [ ! -a /home/petalinux/.bashrc ]; then cp /home/root/. bashrc /home/petalinux/ & chown petalinux:petalinux -R / home/petalinux fi + $ source ~/.profile + ``` -11. \[可选\] 安装ncurses-6.3和htop +11. \[可选\] 安装`ncurses-6.3`和`htop` - ```shell - $ cd ~; rz # 上传ncurses-6.3.tar.gz - $ tar xmzf /home/root/ncurses-6.3.tar.gz -C /usr/ - $ rz # 上传htop.tar.gz - $ tar xmzf /home/root/htop.tar.gz -C /usr/ - $ echo "export TERMINFO=/usr/share/terminfo" >> /etc/profile - $ reboot - ``` + ```shell + $ cd ~; rz # 上传ncurses-6.3.tar.gz + $ tar xmzf /home/root/ncurses-6.3.tar.gz -C /usr/ + $ rz # 上传htop.tar.gz + $ tar xmzf /home/root/htop.tar.gz -C /usr/ + $ echo "export TERMINFO=/usr/share/terminfo" >> /etc/profile + $ reboot + ``` ### 直接写入镜像 -强烈推荐的傻瓜式的方法,在windows上准备好正版[DiskGenius标准版或专业版](https://www.diskgenius.cn/),盗版有BUG,从release中下载sdimage.pmfx文件 +强烈推荐的傻瓜式的方法,在windows上准备好正版[DiskGenius标准版或专业版](https://www.diskgenius.cn/),盗版有概率写入错误数据,从release中下载`sdimage.pmfx`文件 1. 在windows上插入16G的TF卡 -2. 打开DiskGenius +2. 打开`DiskGenius` 3. 左侧栏选中TF卡,右键,从镜像文件还原磁盘 -4. 选sdimage.pmfx文件 +4. 选`sdimage.pmfx`文件 5. 点击开始 把TF卡插回板子,启动方式拨到SD卡启动,上电。要进入系统,参考修改文件系统章节的第7步。 diff --git a/doc/hardware_description.assets/system_arch.jpg b/doc/hardware_description.assets/system_arch.jpg deleted file mode 100644 index ca76e22..0000000 Binary files a/doc/hardware_description.assets/system_arch.jpg and /dev/null differ diff --git a/doc/hardware_description.assets/system_arch.svg b/doc/hardware_description.assets/system_arch.svg new file mode 100644 index 0000000..ac15b3f --- /dev/null +++ b/doc/hardware_description.assets/system_arch.svg @@ -0,0 +1 @@ +DDRFIXED_IOip_encoder_0ip_encoder_v1.0 (Pre-Production)S00_AXIin_signalexrst_nout_signal_valve_posedgeout_signal_valveout_signal_camera_a_posedgeout_signal_camera_b_posedgeout_signal_camera_c_posedgeout_signal_camera_d_posedgeout_signal_camera_aout_signal_camera_bout_signal_camera_cout_signal_camera_ds00_axi_aclks00_axi_aresetnip_fan_0ip_fan_v1.0 (Pre-Production)S00_AXIfans00_axi_aclks00_axi_aresetnencoder_signalexrst_n_0fanout_signal_camera_aout_signal_camera_bout_signal_camera_cout_signal_camera_dprocessing_system7_0ZYNQ7 Processing SystemDDRFIXED_IOUSBIND_0M_AXI_GP0TTC0_WAVE0_OUTTTC0_WAVE1_OUTTTC0_WAVE2_OUTM_AXI_GP0_ACLKFCLK_CLK0FCLK_RESET0_Nps7_0_axi_periphAXI InterconnectS00_AXIM00_AXIM01_AXIM02_AXIACLKARESETNS00_ACLKS00_ARESETNM00_ACLKM00_ARESETNM01_ACLKM01_ARESETNM02_ACLKM02_ARESETNrst_ps7_0_200MProcessor System Resetslowest_sync_clkext_reset_inaux_reset_inmb_debug_sys_rstdcm_lockedmb_resetbus_struct_reset[0:0]peripheral_reset[0:0]interconnect_aresetn[0:0]peripheral_aresetn[0:0] \ No newline at end of file diff --git a/doc/hardware_description.md b/doc/hardware_description.md index ac8f19d..ebfef64 100644 --- a/doc/hardware_description.md +++ b/doc/hardware_description.md @@ -1,12 +1,12 @@ # 硬件平台 -PL端主要由4个外设组成,分别时**风扇控制器**(FAN),**编码和分频控制器**(ENCODER),**先入先出队列**(FIFO),**阀板控制器**(VALVE)。其中阀板控制器没有提供AXI接口,因此并没有映射寄存器,软件也无法进行控制。各个控制器的连接关系如下图所示。 +PL端主要由2个外设组成,分别时**风扇控制器**(FAN),**编码和分频控制器**(ENCODER),各个控制器的连接关系如下图所示。 -![2](hardware_description.assets/system_arch.jpg) +![2](hardware_description.assets/system_arch.svg) -由于开发板的PL端没有自带晶振,所以4个外设由统一的同步时钟驱动,时钟源来自PS端,为200MHz,软件不可修改。外部编码器信号输入**编码和分频控制器**,控制器根据软件设置的阀触发分频值和相机触发分频值对编码器信号进行分频,分频后的信号用于驱动喷阀动作和触发相机拍照。上位机的识别结果存储到**先入先出队列**中。 +由于开发板的PL端没有自带晶振,所以2个外设由统一的同步时钟驱动,时钟源来自PS端,为200MHz,软件不可修改。外部编码器信号和物体检测传感器信号输入**编码和分频控制器**,控制器根据软件设置的阀触发分频值和相机触发分频值对编码器信号进行分频,分频后的信号用于触发相机拍照。 -为同步触发相机和队列移出信号以及保持队列中数据的动态平衡,两个先入先出队列在相机触发同时输出一个数据,即**先入先出队列**的读信号和相机触发共用同一个信号。而由于电磁阀的物理特性导致电磁阀可能无法以触发相机的频率进行开关,因此**阀板控制器**对先入先出队列输出总线上的数据重采样,即按照**编码和分频控制器**输出的阀触发信号读入。两个先入先出队列移出的数据在**阀板控制器**中进行按位或运算,得到的数据转换为阀板协议,输出给阀板。**风扇控制器**用于驱动风扇的启停,给ZYNQ芯片进行降温,防止芯片过热导致工作中出现问题。由于风扇寿命短,因此目前采用散热片方案,风扇不开。 +**风扇控制器**用于驱动风扇的启停,给ZYNQ芯片进行降温,防止芯片过热导致工作中出现问题。由于风扇寿命短,因此目前采用散热片方案,风扇不开。 ## PS模块 @@ -37,37 +37,10 @@ encoder模块主要接口为in_signal、out_signal_camera_a_posedge、out_signal 1. in_signal接口与外部编码器相连,接收外部编码器信号 2. out_signal_camera_a到d最多课用于触发共4个相机 -3. out_signal_camera_posedge_a到d为上述信号的上升沿,其中out_signal_camera_posedge_a控制FIFO的读出 -4. out_signal_valve_posedge为out_signal_valve的上升沿,驱动**阀板控制器**动作 +3. out_signal_camera_posedge_a到d为上述信号的上升沿,固定不连接。 +4. out_signal_valve_posedge为out_signal_valve的上升沿,固定不连接。 5. exrst_n为可选的外部复位清零信号,可用于连接物体传感器,根据需要屏蔽相机触发输出 ENCODER模块输入输出频率的详细计算方式和寄存器说明见[doc/pl_reference_mannual.md](pl_reference_mannual.md)中的ENCODER控制器部分 -## FIFO模块 - -FIFO模块的主要接口为rd_en、dout[383:0]、empty、full、almost_full、almost_empty、data_count[11:0]、fifo_valid - -1. rd_en接收ENCODER模块传来的信号,控制模块内部FIFO按ENCODER模块所需频率进行读取和输出 -2. dout[383:0]为FIFO中读出数据,数据位宽为384bit -3. empty信号为1表示fifo中数据已经为空,无法输出有效数据,但输出寄存器仍然保持上次输出的值 - -FIFO模块寄存器说明见[doc/pl_reference_mannual.md](pl_reference_mannual.md)中的FIFO控制器部分 - -## FAN模块 - -fan模块接口fan输出为PWM波形,连接到外部的风扇驱动电路。 - -fan模块寄存器说明见[doc/pl_reference_mannual.md](pl_reference_mannual.md)中的FAN控制器部分 - -> Note:fan模块代码中设计了PWM调速功能,对于带程序的交流风扇,无法观察到调速现象。但正常的启停可以做到 - -## VALVE_INTERFACES模块 - -VALVE_INTERFACES模块的主要接口为total_valve_data[383:0]、empty、valve_en、sclk[7:0]、sen[7:0]、sdata[7:0]。VALVE_INTERFACES会将total_valve_data_a和total_valve_data_b两路数据进行或运算,得到同为384位的单路数据。 - -1. total_valve_data接收FIFO模块中读出的数据。 - -2. empty信号与两个FIFO模块的empty信号相连。检测到任意一个empty信号为高时,无论输入数据如何,只按协议输出全关给阀板。 -3. valve_en信号上升沿将total_valve_data按协议发送给阀板 -4. sclk[7:0]、sen[7:0]、sdata[7:0]连接到外部差分芯片,为最多8块阀板的时钟信号线、使能信号线以及数据信号线 diff --git a/doc/pl_reference_mannual.assets/blocks.pptx b/doc/pl_reference_mannual.assets/blocks.pptx index 608c034..552ce90 100644 Binary files a/doc/pl_reference_mannual.assets/blocks.pptx and b/doc/pl_reference_mannual.assets/blocks.pptx differ diff --git a/doc/pl_reference_mannual.assets/encoder_regs.svg b/doc/pl_reference_mannual.assets/encoder_regs.svg index d3ed9cc..6ddaefb 100644 --- a/doc/pl_reference_mannual.assets/encoder_regs.svg +++ b/doc/pl_reference_mannual.assets/encoder_regs.svg @@ -1 +1 @@ -偏移寄存器313029282726252423222120191817161514131211109876543210ENCODER_CRICOVTSMODCLRReset value1001ENCODER_VDIVRReset value00000000000000000000000000000000ENCODER_CDIVRAReset value00000000000000000000000000000000ENCODER_CDIVRBReset value00000000000000000000000000000000ENCODER_CDIVRCReset value00000000000000000000000000000000ENCODER_CDIVRDReset value000000000000000000000000000000000x000x04VDIV[31:0]0x08CDIV[31:0]Reserved0x10CDIV[31:0]0x14CDIV[31:0]0x0CCDIV[31:0] \ No newline at end of file +偏移寄存器313029282726252423222120191817161514131211109876543210ENCODER_CRICOVTSMODCLRReset value1000ENCODER_VDIVRReset value00000000000000000000000000000000ENCODER_CDIVRAReset value00000000000000000000000000000000ENCODER_CDIVRBReset value00000000000000000000000000000000ENCODER_CDIVRCReset value00000000000000000000000000000000ENCODER_CDIVRDReset value000000000000000000000000000000000x10CDIV[31:0]0x14CDIV[31:0]0x0CCDIV[31:0]0x000x04VDIV[31:0]0x08CDIV[31:0]Reserved \ No newline at end of file diff --git a/doc/pl_reference_mannual.assets/fifo_cr.png b/doc/pl_reference_mannual.assets/fifo_cr.png deleted file mode 100644 index b964aaa..0000000 Binary files a/doc/pl_reference_mannual.assets/fifo_cr.png and /dev/null differ diff --git a/doc/pl_reference_mannual.assets/fifo_datx.png b/doc/pl_reference_mannual.assets/fifo_datx.png deleted file mode 100644 index 5482af5..0000000 Binary files a/doc/pl_reference_mannual.assets/fifo_datx.png and /dev/null differ diff --git a/doc/pl_reference_mannual.assets/fifo_ecr.png b/doc/pl_reference_mannual.assets/fifo_ecr.png deleted file mode 100644 index dfbf006..0000000 Binary files a/doc/pl_reference_mannual.assets/fifo_ecr.png and /dev/null differ diff --git a/doc/pl_reference_mannual.assets/fifo_regs.png b/doc/pl_reference_mannual.assets/fifo_regs.png deleted file mode 100644 index 2e0e6c8..0000000 Binary files a/doc/pl_reference_mannual.assets/fifo_regs.png and /dev/null differ diff --git a/doc/pl_reference_mannual.assets/fifo_sr.png b/doc/pl_reference_mannual.assets/fifo_sr.png deleted file mode 100644 index 22499d7..0000000 Binary files a/doc/pl_reference_mannual.assets/fifo_sr.png and /dev/null differ diff --git a/doc/pl_reference_mannual.assets/regs.xlsx b/doc/pl_reference_mannual.assets/regs.xlsx index 33a3205..c407676 100644 Binary files a/doc/pl_reference_mannual.assets/regs.xlsx and b/doc/pl_reference_mannual.assets/regs.xlsx differ diff --git a/doc/pl_reference_mannual.assets/system_arch.jpg b/doc/pl_reference_mannual.assets/system_arch.jpg deleted file mode 100644 index ca76e22..0000000 Binary files a/doc/pl_reference_mannual.assets/system_arch.jpg and /dev/null differ diff --git a/doc/pl_reference_mannual.assets/system_arch.svg b/doc/pl_reference_mannual.assets/system_arch.svg new file mode 100644 index 0000000..ac15b3f --- /dev/null +++ b/doc/pl_reference_mannual.assets/system_arch.svg @@ -0,0 +1 @@ +DDRFIXED_IOip_encoder_0ip_encoder_v1.0 (Pre-Production)S00_AXIin_signalexrst_nout_signal_valve_posedgeout_signal_valveout_signal_camera_a_posedgeout_signal_camera_b_posedgeout_signal_camera_c_posedgeout_signal_camera_d_posedgeout_signal_camera_aout_signal_camera_bout_signal_camera_cout_signal_camera_ds00_axi_aclks00_axi_aresetnip_fan_0ip_fan_v1.0 (Pre-Production)S00_AXIfans00_axi_aclks00_axi_aresetnencoder_signalexrst_n_0fanout_signal_camera_aout_signal_camera_bout_signal_camera_cout_signal_camera_dprocessing_system7_0ZYNQ7 Processing SystemDDRFIXED_IOUSBIND_0M_AXI_GP0TTC0_WAVE0_OUTTTC0_WAVE1_OUTTTC0_WAVE2_OUTM_AXI_GP0_ACLKFCLK_CLK0FCLK_RESET0_Nps7_0_axi_periphAXI InterconnectS00_AXIM00_AXIM01_AXIM02_AXIACLKARESETNS00_ACLKS00_ARESETNM00_ACLKM00_ARESETNM01_ACLKM01_ARESETNM02_ACLKM02_ARESETNrst_ps7_0_200MProcessor System Resetslowest_sync_clkext_reset_inaux_reset_inmb_debug_sys_rstdcm_lockedmb_resetbus_struct_reset[0:0]peripheral_reset[0:0]interconnect_aresetn[0:0]peripheral_aresetn[0:0] \ No newline at end of file diff --git a/doc/pl_reference_mannual.md b/doc/pl_reference_mannual.md index c05fbf1..4ce6ab3 100644 --- a/doc/pl_reference_mannual.md +++ b/doc/pl_reference_mannual.md @@ -4,11 +4,11 @@ ### 系统架构 -PL端主要由4个外设组成,分别时**风扇控制器**(FAN),**编码和分频控制器**(ENCODER),**先入先出队列**(FIFO)和**阀板控制器**(VALVE)。其中阀板控制器没有提供AXI接口,因此并没有映射寄存器,软件也无法进行控制。各个控制器的连接关系如下图所示。 +PL端主要由2个外设组成,分别时**风扇控制器**(FAN),**编码和分频控制器**(ENCODER)。各个控制器的连接关系如下图所示。 -![system_arch](pl_reference_mannual.assets/system_arch.jpg) +![system_arch](./pl_reference_mannual.assets/system_arch.svg) -4个外设由统一的同步时钟驱动,时钟源来自PS端,为200MHz,软件不可修改。外部编码器信号输入**编码和分频控制器**,控制器根据软件设置的阀触发分频值和相机触发分频值对编码器信号进行分频。为同步触发相机和移出队列,**先入先出队列**在相机触发同时输出一个数据,即**先入先出队列**读信号和相机触发共用同一个信号。而由于电磁阀的物理特性导致电磁阀无法以触发相机的频率进行开关,因此**阀板控制器**对先入先出队列输出总线上的数据进行重采样,即按照**编码和分频控制器**输出的阀触发信号更新并转换为阀板协议,输出电磁阀的状态。 +2个外设由统一的同步时钟驱动,时钟源来自PS端,为200MHz,软件不可修改。外部编码器信号和物体传感器信号输入**编码和分频控制器**,控制器根据软件设置的相机触发分频值对编码器信号进行分频。为同步触发相机。 具体的硬件设计和信号说明见[doc/hardware_description.md](hardware_description.md) @@ -16,7 +16,6 @@ PL端主要由4个外设组成,分别时**风扇控制器**(FAN),**编码和 | 边界地址 | 外设 | 总线 | | ----------------------- | ---------------- | --------- | -| 0x43c00000 - 0x43c0ffff | 先入先出队列 | M_AXI_GP0 | | 0x43c10000 - 0x43c1ffff | 编码和分频控制器 | M_AXI_GP0 | | 0x43c20000 - 0x43c2ffff | 风扇控制器 | M_AXI_GP0 | @@ -138,91 +137,3 @@ ENCODER寄存器可映射为32位可寻址寄存器,如下表所述: ![encoder_regs](pl_reference_mannual.assets/encoder_regs.svg) -## 先入先出队列 (FIFO) - -### FIFO简介 - -FIFO模块为下位机的核心模块,用于接收控制喷阀的信号,以先入先出原则,按顺序由encoder模块控制输出给阀板。 - -### FIFO主要特性 - -- 384bit数据位宽,最大4096深度 -- 实时计算存储数据数量,提供队列满,队列空等信号 -- 指示队列输出状态 -- 清空功能 - -### FIFO功能说明 - -下图给出了FIFO的主要信号: - -fifo_block - -FIFO模块在写同步信号拉高后接收用于控制喷阀的384bit位宽的数据,并在读使能拉高后将数据加载到AXI数据总线上,当队列读空后,empty信号拉高,不输出有效数据,表示关闭喷阀。复位信号拉高后将整个队列清空。COUNT信号表示当前在FIFO内存在多少个有效数据。 - -### FIFO寄存器说明 - -FIFO模块寄存器主要包括数据寄存器x (FIFO_DATx)(x=0...11) 、状态寄存器 (FIFO_SR) 、控制寄存器 (FIFO_CR) 。数据寄存器x (FIFO_DATx)(x=0...11) 用于寄存写入的384bit数据,并保持该数据。状态寄存器 (FIFO_SR)用于反映FIFO内部数据的寄存状态,标志FIFO是否被读空、写满以及FIFO内当前存在多少有效数据。控制寄存器 (FIFO_CR) 用于控制AXI总线上的数据被写入FIFO,以及实现复位清空操作。 - -**Base Address: 0x43c00000** - -#### FIFO数据寄存器x (FIFO_DATx) (x=0...11) - -FIFO的写宽度为384bit,因此需12个32位寄存器**FIFO_DAT0**-**FIFO_DAT11**,按小端字节序共同组成384bit位宽。将数据写入这12个寄存器后,应对位**WS**写入1,此时数据寄存器组中的数据写入到FIFO中。 - -偏移地址: 0x00...0x2C
复位值: 0x0000 0000 - -![image-20220613202916591](pl_reference_mannual.assets/fifo_datx.png) - -| **Field** | **Description** | -| :------------------------------ | :----------------------------------------------------------- | -| 位31:0 **DTIN[x\*32+31:x\*32]** | FIFO数据寄存器x写入数据位[x\*32+31:x\*32]
写入数据后该寄存器将保持写入的值,直到对**WS**位写入1,数据才会进入FIFO队列。不要读取该寄存器。结合VALVE外设可得
0: 对应喷阀关闭
1: 对应喷阀打开 | - - - -#### FIFO状态寄存器 (FIFO_SR) - -状态寄存器指示FIFO的内部状态,数据数量等,为只读寄存器,不可写 - -偏移地址: 0x30
复位值: 0x0000 0000 - -![image-20220613203939644](pl_reference_mannual.assets/fifo_sr.png) - -| **Field** | **Description** | -| :------------- | :----------------------------------------------------------- | -| 位31:17 保留 | 必须保持复位值 | -| 位16 **VLD** | 数据输出有效标志 (Valid)
0: 当前无有效输出,输出保持上一状态
1: 当前队列正在输出有效数据 | -| 位15 **AMEM** | 队列将空标志 (Almost Empty)
0: 队列没有被读空
1: 队列在一个读时钟周期后会被读空 | -| 位14 **EM** | 队列空标志 (Empty)
0: 队列中存在有效数据,没有被读空
1: 队列中已经没有有效数据 | -| 位13 **AMFU** | 队列将满标志 (Almost Full)
0: 队列没有被写满
1: 队列在一个写时钟周期后会被写满 | -| 位12 **FU** | 队列满标志 (Almost Full)
0: 队列中的有效数据小于FIFO数据深度
1: 队列中的有效数据达到FIFO数据深度 | -| 位11:0 **CNT** | 队列数据数量 (Data Count)
该值指示队列中的数据数量
注意:一个数据为384位宽 | - -#### FIFO空计数寄存器 (FIFO_ECR) - -队列为空后被读的次数 - -偏移地址: 0x34
复位值: 0x0000 0000 - -![image-20220613212701816](pl_reference_mannual.assets/fifo_ecr.png) - -| **Field** | **Description** | -| :------------- | :----------------------------------------------------------- | -| 位31:0 **CNT** | 队列为空读次数 (Empty Count)
该值指示队列为空后被读的次数
注意:改寄存器只读,仅在FIFO复位时自动清零 | - -#### FIFO控制寄存器 (FIFO_CR) - -偏移地址: 0x38
复位值: 0x0000 00xx - -![image-20220613212701816](pl_reference_mannual.assets/fifo_cr.png) - -| **Field** | **Description** | -| :---------- | :----------------------------------------------------------- | -| 位31:2 保留 | 必须保持复位值 | -| 位1 **CLR** | 清空队列 (Clear)
对该位写入1,队列将清空,同时队列输出为全0。
注意:不要写入除1以外的任何值。 | -| 位0 **WS** | 写入同步 (Write Synchronization)
对该位写入1,**FIFO_DATx**的数据按字节小端序进入队列。
注意:不要写入除1以外的任何值。 | - -#### FIFO寄存器映射 - -FIFO寄存器可映射为32位可寻址寄存器,如下表所述: - - diff --git a/doc/version b/doc/version index 840ca8c..400122e 100644 --- a/doc/version +++ b/doc/version @@ -1 +1 @@ -1.4 \ No newline at end of file +1.5 \ No newline at end of file diff --git a/hardware/pl_platform/README.md b/hardware/pl_platform/README.md deleted file mode 100644 index 6790377..0000000 --- a/hardware/pl_platform/README.md +++ /dev/null @@ -1 +0,0 @@ -PL端的fpga工程待补充 \ No newline at end of file diff --git a/hardware/pl_platform/bd/system.tcl b/hardware/pl_platform/bd/system.tcl new file mode 100644 index 0000000..031d029 --- /dev/null +++ b/hardware/pl_platform/bd/system.tcl @@ -0,0 +1,648 @@ + +################################################################ +# This is a generated script based on design: system +# +# Though there are limitations about the generated script, +# the main purpose of this utility is to make learning +# IP Integrator Tcl commands easier. +################################################################ + +namespace eval _tcl { +proc get_script_folder {} { + set script_path [file normalize [info script]] + set script_folder [file dirname $script_path] + return $script_folder +} +} +variable script_folder +set script_folder [_tcl::get_script_folder] + +################################################################ +# Check if script is running in correct Vivado version. +################################################################ +set scripts_vivado_version 2022.1 +set current_vivado_version [version -short] + +if { [string first $scripts_vivado_version $current_vivado_version] == -1 } { + puts "" + catch {common::send_gid_msg -ssname BD::TCL -id 2041 -severity "ERROR" "This script was generated using Vivado <$scripts_vivado_version> and is being run in <$current_vivado_version> of Vivado. Please run the script in Vivado <$scripts_vivado_version> then open the design in Vivado <$current_vivado_version>. Upgrade the design by running \"Tools => Report => Report IP Status...\", then run write_bd_tcl to create an updated script."} + + return 1 +} + +################################################################ +# START +################################################################ + +# To test this script, run the following commands from Vivado Tcl console: +# source system_script.tcl + +# If there is no project opened, this script will create a +# project, but make sure you do not have an existing project +# <./myproj/project_1.xpr> in the current working folder. + +set list_projs [get_projects -quiet] +if { $list_projs eq "" } { + create_project project_1 myproj -part xc7z010clg400-1 +} + + +# CHANGE DESIGN NAME HERE +variable design_name +set design_name system + +# If you do not already have an existing IP Integrator design open, +# you can create a design using the following command: +# create_bd_design $design_name + +# Creating design if needed +set errMsg "" +set nRet 0 + +set cur_design [current_bd_design -quiet] +set list_cells [get_bd_cells -quiet] + +if { ${design_name} eq "" } { + # USE CASES: + # 1) Design_name not set + + set errMsg "Please set the variable to a non-empty value." + set nRet 1 + +} elseif { ${cur_design} ne "" && ${list_cells} eq "" } { + # USE CASES: + # 2): Current design opened AND is empty AND names same. + # 3): Current design opened AND is empty AND names diff; design_name NOT in project. + # 4): Current design opened AND is empty AND names diff; design_name exists in project. + + if { $cur_design ne $design_name } { + common::send_gid_msg -ssname BD::TCL -id 2001 -severity "INFO" "Changing value of from <$design_name> to <$cur_design> since current design is empty." + set design_name [get_property NAME $cur_design] + } + common::send_gid_msg -ssname BD::TCL -id 2002 -severity "INFO" "Constructing design in IPI design <$cur_design>..." + +} elseif { ${cur_design} ne "" && $list_cells ne "" && $cur_design eq $design_name } { + # USE CASES: + # 5) Current design opened AND has components AND same names. + + set errMsg "Design <$design_name> already exists in your project, please set the variable to another value." + set nRet 1 +} elseif { [get_files -quiet ${design_name}.bd] ne "" } { + # USE CASES: + # 6) Current opened design, has components, but diff names, design_name exists in project. + # 7) No opened design, design_name exists in project. + + set errMsg "Design <$design_name> already exists in your project, please set the variable to another value." + set nRet 2 + +} else { + # USE CASES: + # 8) No opened design, design_name not in project. + # 9) Current opened design, has components, but diff names, design_name not in project. + + common::send_gid_msg -ssname BD::TCL -id 2003 -severity "INFO" "Currently there is no design <$design_name> in project, so creating one..." + + create_bd_design $design_name + + common::send_gid_msg -ssname BD::TCL -id 2004 -severity "INFO" "Making design <$design_name> as current_bd_design." + current_bd_design $design_name + +} + +common::send_gid_msg -ssname BD::TCL -id 2005 -severity "INFO" "Currently the variable is equal to \"$design_name\"." + +if { $nRet != 0 } { + catch {common::send_gid_msg -ssname BD::TCL -id 2006 -severity "ERROR" $errMsg} + return $nRet +} + +set bCheckIPsPassed 1 +################################################################## +# CHECK IPs +################################################################## +set bCheckIPs 1 +if { $bCheckIPs == 1 } { + set list_check_ips "\ +user.org:user:ip_encoder:1.1\ +user.org:user:ip_fan:1.0\ +xilinx.com:ip:processing_system7:5.5\ +xilinx.com:ip:proc_sys_reset:5.0\ +" + + set list_ips_missing "" + common::send_gid_msg -ssname BD::TCL -id 2011 -severity "INFO" "Checking if the following IPs exist in the project's IP catalog: $list_check_ips ." + + foreach ip_vlnv $list_check_ips { + set ip_obj [get_ipdefs -all $ip_vlnv] + if { $ip_obj eq "" } { + lappend list_ips_missing $ip_vlnv + } + } + + if { $list_ips_missing ne "" } { + catch {common::send_gid_msg -ssname BD::TCL -id 2012 -severity "ERROR" "The following IPs are not found in the IP Catalog:\n $list_ips_missing\n\nResolution: Please add the repository containing the IP(s) to the project." } + set bCheckIPsPassed 0 + } + +} + +if { $bCheckIPsPassed != 1 } { + common::send_gid_msg -ssname BD::TCL -id 2023 -severity "WARNING" "Will not continue with creation of design due to the error(s) above." + return 3 +} + +################################################################## +# DESIGN PROCs +################################################################## + + + +# Procedure to create entire design; Provide argument to make +# procedure reusable. If parentCell is "", will use root. +proc create_root_design { parentCell } { + + variable script_folder + variable design_name + + if { $parentCell eq "" } { + set parentCell [get_bd_cells /] + } + + # Get object for parentCell + set parentObj [get_bd_cells $parentCell] + if { $parentObj == "" } { + catch {common::send_gid_msg -ssname BD::TCL -id 2090 -severity "ERROR" "Unable to find parent cell <$parentCell>!"} + return + } + + # Make sure parentObj is hier blk + set parentType [get_property TYPE $parentObj] + if { $parentType ne "hier" } { + catch {common::send_gid_msg -ssname BD::TCL -id 2091 -severity "ERROR" "Parent <$parentObj> has TYPE = <$parentType>. Expected to be ."} + return + } + + # Save current instance; Restore later + set oldCurInst [current_bd_instance .] + + # Set parent object as current + current_bd_instance $parentObj + + + # Create interface ports + set DDR [ create_bd_intf_port -mode Master -vlnv xilinx.com:interface:ddrx_rtl:1.0 DDR ] + + set FIXED_IO [ create_bd_intf_port -mode Master -vlnv xilinx.com:display_processing_system7:fixedio_rtl:1.0 FIXED_IO ] + + + # Create ports + set encoder_signal [ create_bd_port -dir I encoder_signal ] + set exrst_n [ create_bd_port -dir I exrst_n ] + set fan [ create_bd_port -dir O fan ] + set out_signal_camera_a [ create_bd_port -dir O out_signal_camera_a ] + set out_signal_camera_b [ create_bd_port -dir O out_signal_camera_b ] + set out_signal_camera_c [ create_bd_port -dir O out_signal_camera_c ] + set out_signal_camera_d [ create_bd_port -dir O out_signal_camera_d ] + + # Create instance: ip_encoder_0, and set properties + set ip_encoder_0 [ create_bd_cell -type ip -vlnv user.org:user:ip_encoder:1.1 ip_encoder_0 ] + + # Create instance: ip_fan_0, and set properties + set ip_fan_0 [ create_bd_cell -type ip -vlnv user.org:user:ip_fan:1.0 ip_fan_0 ] + + # Create instance: processing_system7_0, and set properties + set processing_system7_0 [ create_bd_cell -type ip -vlnv xilinx.com:ip:processing_system7:5.5 processing_system7_0 ] + set_property -dict [ list \ + CONFIG.PCW_ACT_APU_PERIPHERAL_FREQMHZ {666.666687} \ + CONFIG.PCW_ACT_CAN_PERIPHERAL_FREQMHZ {10.000000} \ + CONFIG.PCW_ACT_DCI_PERIPHERAL_FREQMHZ {10.158730} \ + CONFIG.PCW_ACT_ENET0_PERIPHERAL_FREQMHZ {125.000000} \ + CONFIG.PCW_ACT_ENET1_PERIPHERAL_FREQMHZ {10.000000} \ + CONFIG.PCW_ACT_FPGA0_PERIPHERAL_FREQMHZ {200.000000} \ + CONFIG.PCW_ACT_FPGA1_PERIPHERAL_FREQMHZ {10.000000} \ + CONFIG.PCW_ACT_FPGA2_PERIPHERAL_FREQMHZ {10.000000} \ + CONFIG.PCW_ACT_FPGA3_PERIPHERAL_FREQMHZ {10.000000} \ + CONFIG.PCW_ACT_PCAP_PERIPHERAL_FREQMHZ {200.000000} \ + CONFIG.PCW_ACT_QSPI_PERIPHERAL_FREQMHZ {200.000000} \ + CONFIG.PCW_ACT_SDIO_PERIPHERAL_FREQMHZ {100.000000} \ + CONFIG.PCW_ACT_SMC_PERIPHERAL_FREQMHZ {10.000000} \ + CONFIG.PCW_ACT_SPI_PERIPHERAL_FREQMHZ {10.000000} \ + CONFIG.PCW_ACT_TPIU_PERIPHERAL_FREQMHZ {200.000000} \ + CONFIG.PCW_ACT_TTC0_CLK0_PERIPHERAL_FREQMHZ {111.111115} \ + CONFIG.PCW_ACT_TTC0_CLK1_PERIPHERAL_FREQMHZ {111.111115} \ + CONFIG.PCW_ACT_TTC0_CLK2_PERIPHERAL_FREQMHZ {111.111115} \ + CONFIG.PCW_ACT_TTC1_CLK0_PERIPHERAL_FREQMHZ {111.111115} \ + CONFIG.PCW_ACT_TTC1_CLK1_PERIPHERAL_FREQMHZ {111.111115} \ + CONFIG.PCW_ACT_TTC1_CLK2_PERIPHERAL_FREQMHZ {111.111115} \ + CONFIG.PCW_ACT_UART_PERIPHERAL_FREQMHZ {100.000000} \ + CONFIG.PCW_ACT_WDT_PERIPHERAL_FREQMHZ {111.111115} \ + CONFIG.PCW_ARMPLL_CTRL_FBDIV {40} \ + CONFIG.PCW_CAN_PERIPHERAL_DIVISOR0 {1} \ + CONFIG.PCW_CAN_PERIPHERAL_DIVISOR1 {1} \ + CONFIG.PCW_CLK0_FREQ {200000000} \ + CONFIG.PCW_CLK1_FREQ {10000000} \ + CONFIG.PCW_CLK2_FREQ {10000000} \ + CONFIG.PCW_CLK3_FREQ {10000000} \ + CONFIG.PCW_CPU_CPU_PLL_FREQMHZ {1333.333} \ + CONFIG.PCW_CPU_PERIPHERAL_DIVISOR0 {2} \ + CONFIG.PCW_DCI_PERIPHERAL_DIVISOR0 {15} \ + CONFIG.PCW_DCI_PERIPHERAL_DIVISOR1 {7} \ + CONFIG.PCW_DDRPLL_CTRL_FBDIV {32} \ + CONFIG.PCW_DDR_DDR_PLL_FREQMHZ {1066.667} \ + CONFIG.PCW_DDR_PERIPHERAL_DIVISOR0 {2} \ + CONFIG.PCW_DDR_RAM_HIGHADDR {0x1FFFFFFF} \ + CONFIG.PCW_ENET0_ENET0_IO {MIO 16 .. 27} \ + CONFIG.PCW_ENET0_GRP_MDIO_ENABLE {1} \ + CONFIG.PCW_ENET0_GRP_MDIO_IO {MIO 52 .. 53} \ + CONFIG.PCW_ENET0_PERIPHERAL_CLKSRC {IO PLL} \ + CONFIG.PCW_ENET0_PERIPHERAL_DIVISOR0 {8} \ + CONFIG.PCW_ENET0_PERIPHERAL_DIVISOR1 {1} \ + CONFIG.PCW_ENET0_PERIPHERAL_ENABLE {1} \ + CONFIG.PCW_ENET0_PERIPHERAL_FREQMHZ {1000 Mbps} \ + CONFIG.PCW_ENET0_RESET_ENABLE {1} \ + CONFIG.PCW_ENET0_RESET_IO {MIO 7} \ + CONFIG.PCW_ENET1_PERIPHERAL_DIVISOR0 {1} \ + CONFIG.PCW_ENET1_PERIPHERAL_DIVISOR1 {1} \ + CONFIG.PCW_ENET1_RESET_ENABLE {0} \ + CONFIG.PCW_ENET_RESET_ENABLE {1} \ + CONFIG.PCW_ENET_RESET_SELECT {Share reset pin} \ + CONFIG.PCW_EN_EMIO_ENET0 {0} \ + CONFIG.PCW_EN_EMIO_SDIO1 {0} \ + CONFIG.PCW_EN_EMIO_TTC0 {1} \ + CONFIG.PCW_EN_EMIO_UART0 {0} \ + CONFIG.PCW_EN_ENET0 {1} \ + CONFIG.PCW_EN_GPIO {1} \ + CONFIG.PCW_EN_QSPI {1} \ + CONFIG.PCW_EN_SDIO0 {1} \ + CONFIG.PCW_EN_SDIO1 {1} \ + CONFIG.PCW_EN_TTC0 {1} \ + CONFIG.PCW_EN_UART0 {1} \ + CONFIG.PCW_EN_USB0 {1} \ + CONFIG.PCW_FCLK0_PERIPHERAL_DIVISOR0 {5} \ + CONFIG.PCW_FCLK0_PERIPHERAL_DIVISOR1 {1} \ + CONFIG.PCW_FCLK1_PERIPHERAL_DIVISOR0 {1} \ + CONFIG.PCW_FCLK1_PERIPHERAL_DIVISOR1 {1} \ + CONFIG.PCW_FCLK2_PERIPHERAL_DIVISOR0 {1} \ + CONFIG.PCW_FCLK2_PERIPHERAL_DIVISOR1 {1} \ + CONFIG.PCW_FCLK3_PERIPHERAL_DIVISOR0 {1} \ + CONFIG.PCW_FCLK3_PERIPHERAL_DIVISOR1 {1} \ + CONFIG.PCW_FPGA0_PERIPHERAL_FREQMHZ {200} \ + CONFIG.PCW_FPGA_FCLK0_ENABLE {1} \ + CONFIG.PCW_FPGA_FCLK1_ENABLE {0} \ + CONFIG.PCW_FPGA_FCLK2_ENABLE {0} \ + CONFIG.PCW_FPGA_FCLK3_ENABLE {0} \ + CONFIG.PCW_GPIO_MIO_GPIO_ENABLE {1} \ + CONFIG.PCW_GPIO_MIO_GPIO_IO {MIO} \ + CONFIG.PCW_I2C0_RESET_ENABLE {0} \ + CONFIG.PCW_I2C1_RESET_ENABLE {0} \ + CONFIG.PCW_I2C_PERIPHERAL_FREQMHZ {25} \ + CONFIG.PCW_I2C_RESET_ENABLE {1} \ + CONFIG.PCW_IOPLL_CTRL_FBDIV {30} \ + CONFIG.PCW_IO_IO_PLL_FREQMHZ {1000.000} \ + CONFIG.PCW_MIO_0_DIRECTION {inout} \ + CONFIG.PCW_MIO_0_IOTYPE {LVCMOS 3.3V} \ + CONFIG.PCW_MIO_0_PULLUP {enabled} \ + CONFIG.PCW_MIO_0_SLEW {slow} \ + CONFIG.PCW_MIO_10_DIRECTION {inout} \ + CONFIG.PCW_MIO_10_IOTYPE {LVCMOS 3.3V} \ + CONFIG.PCW_MIO_10_PULLUP {enabled} \ + CONFIG.PCW_MIO_10_SLEW {slow} \ + CONFIG.PCW_MIO_11_DIRECTION {inout} \ + CONFIG.PCW_MIO_11_IOTYPE {LVCMOS 3.3V} \ + CONFIG.PCW_MIO_11_PULLUP {enabled} \ + CONFIG.PCW_MIO_11_SLEW {slow} \ + CONFIG.PCW_MIO_12_DIRECTION {inout} \ + CONFIG.PCW_MIO_12_IOTYPE {LVCMOS 3.3V} \ + CONFIG.PCW_MIO_12_PULLUP {enabled} \ + CONFIG.PCW_MIO_12_SLEW {slow} \ + CONFIG.PCW_MIO_13_DIRECTION {inout} \ + CONFIG.PCW_MIO_13_IOTYPE {LVCMOS 3.3V} \ + CONFIG.PCW_MIO_13_PULLUP {enabled} \ + CONFIG.PCW_MIO_13_SLEW {slow} \ + CONFIG.PCW_MIO_14_DIRECTION {in} \ + CONFIG.PCW_MIO_14_IOTYPE {LVCMOS 3.3V} \ + CONFIG.PCW_MIO_14_PULLUP {enabled} \ + CONFIG.PCW_MIO_14_SLEW {slow} \ + CONFIG.PCW_MIO_15_DIRECTION {out} \ + CONFIG.PCW_MIO_15_IOTYPE {LVCMOS 3.3V} \ + CONFIG.PCW_MIO_15_PULLUP {enabled} \ + CONFIG.PCW_MIO_15_SLEW {slow} \ + CONFIG.PCW_MIO_16_DIRECTION {out} \ + CONFIG.PCW_MIO_16_IOTYPE {LVCMOS 1.8V} \ + CONFIG.PCW_MIO_16_PULLUP {enabled} \ + CONFIG.PCW_MIO_16_SLEW {fast} \ + CONFIG.PCW_MIO_17_DIRECTION {out} \ + CONFIG.PCW_MIO_17_IOTYPE {LVCMOS 1.8V} \ + CONFIG.PCW_MIO_17_PULLUP {enabled} \ + CONFIG.PCW_MIO_17_SLEW {fast} \ + CONFIG.PCW_MIO_18_DIRECTION {out} \ + CONFIG.PCW_MIO_18_IOTYPE {LVCMOS 1.8V} \ + CONFIG.PCW_MIO_18_PULLUP {enabled} \ + CONFIG.PCW_MIO_18_SLEW {fast} \ + CONFIG.PCW_MIO_19_DIRECTION {out} \ + CONFIG.PCW_MIO_19_IOTYPE {LVCMOS 1.8V} \ + CONFIG.PCW_MIO_19_PULLUP {enabled} \ + CONFIG.PCW_MIO_19_SLEW {fast} \ + CONFIG.PCW_MIO_1_DIRECTION {out} \ + CONFIG.PCW_MIO_1_IOTYPE {LVCMOS 3.3V} \ + CONFIG.PCW_MIO_1_PULLUP {enabled} \ + CONFIG.PCW_MIO_1_SLEW {fast} \ + CONFIG.PCW_MIO_20_DIRECTION {out} \ + CONFIG.PCW_MIO_20_IOTYPE {LVCMOS 1.8V} \ + CONFIG.PCW_MIO_20_PULLUP {enabled} \ + CONFIG.PCW_MIO_20_SLEW {fast} \ + CONFIG.PCW_MIO_21_DIRECTION {out} \ + CONFIG.PCW_MIO_21_IOTYPE {LVCMOS 1.8V} \ + CONFIG.PCW_MIO_21_PULLUP {enabled} \ + CONFIG.PCW_MIO_21_SLEW {fast} \ + CONFIG.PCW_MIO_22_DIRECTION {in} \ + CONFIG.PCW_MIO_22_IOTYPE {LVCMOS 1.8V} \ + CONFIG.PCW_MIO_22_PULLUP {enabled} \ + CONFIG.PCW_MIO_22_SLEW {fast} \ + CONFIG.PCW_MIO_23_DIRECTION {in} \ + CONFIG.PCW_MIO_23_IOTYPE {LVCMOS 1.8V} \ + CONFIG.PCW_MIO_23_PULLUP {enabled} \ + CONFIG.PCW_MIO_23_SLEW {fast} \ + CONFIG.PCW_MIO_24_DIRECTION {in} \ + CONFIG.PCW_MIO_24_IOTYPE {LVCMOS 1.8V} \ + CONFIG.PCW_MIO_24_PULLUP {enabled} \ + CONFIG.PCW_MIO_24_SLEW {fast} \ + CONFIG.PCW_MIO_25_DIRECTION {in} \ + CONFIG.PCW_MIO_25_IOTYPE {LVCMOS 1.8V} \ + CONFIG.PCW_MIO_25_PULLUP {enabled} \ + CONFIG.PCW_MIO_25_SLEW {fast} \ + CONFIG.PCW_MIO_26_DIRECTION {in} \ + CONFIG.PCW_MIO_26_IOTYPE {LVCMOS 1.8V} \ + CONFIG.PCW_MIO_26_PULLUP {enabled} \ + CONFIG.PCW_MIO_26_SLEW {fast} \ + CONFIG.PCW_MIO_27_DIRECTION {in} \ + CONFIG.PCW_MIO_27_IOTYPE {LVCMOS 1.8V} \ + CONFIG.PCW_MIO_27_PULLUP {enabled} \ + CONFIG.PCW_MIO_27_SLEW {fast} \ + CONFIG.PCW_MIO_28_DIRECTION {inout} \ + CONFIG.PCW_MIO_28_IOTYPE {LVCMOS 1.8V} \ + CONFIG.PCW_MIO_28_PULLUP {enabled} \ + CONFIG.PCW_MIO_28_SLEW {slow} \ + CONFIG.PCW_MIO_29_DIRECTION {in} \ + CONFIG.PCW_MIO_29_IOTYPE {LVCMOS 1.8V} \ + CONFIG.PCW_MIO_29_PULLUP {enabled} \ + CONFIG.PCW_MIO_29_SLEW {slow} \ + CONFIG.PCW_MIO_2_DIRECTION {inout} \ + CONFIG.PCW_MIO_2_IOTYPE {LVCMOS 3.3V} \ + CONFIG.PCW_MIO_2_PULLUP {disabled} \ + CONFIG.PCW_MIO_2_SLEW {fast} \ + CONFIG.PCW_MIO_30_DIRECTION {out} \ + CONFIG.PCW_MIO_30_IOTYPE {LVCMOS 1.8V} \ + CONFIG.PCW_MIO_30_PULLUP {enabled} \ + CONFIG.PCW_MIO_30_SLEW {slow} \ + CONFIG.PCW_MIO_31_DIRECTION {in} \ + CONFIG.PCW_MIO_31_IOTYPE {LVCMOS 1.8V} \ + CONFIG.PCW_MIO_31_PULLUP {enabled} \ + CONFIG.PCW_MIO_31_SLEW {slow} \ + CONFIG.PCW_MIO_32_DIRECTION {inout} \ + CONFIG.PCW_MIO_32_IOTYPE {LVCMOS 1.8V} \ + CONFIG.PCW_MIO_32_PULLUP {enabled} \ + CONFIG.PCW_MIO_32_SLEW {slow} \ + CONFIG.PCW_MIO_33_DIRECTION {inout} \ + CONFIG.PCW_MIO_33_IOTYPE {LVCMOS 1.8V} \ + CONFIG.PCW_MIO_33_PULLUP {enabled} \ + CONFIG.PCW_MIO_33_SLEW {slow} \ + CONFIG.PCW_MIO_34_DIRECTION {inout} \ + CONFIG.PCW_MIO_34_IOTYPE {LVCMOS 1.8V} \ + CONFIG.PCW_MIO_34_PULLUP {enabled} \ + CONFIG.PCW_MIO_34_SLEW {slow} \ + CONFIG.PCW_MIO_35_DIRECTION {inout} \ + CONFIG.PCW_MIO_35_IOTYPE {LVCMOS 1.8V} \ + CONFIG.PCW_MIO_35_PULLUP {enabled} \ + CONFIG.PCW_MIO_35_SLEW {slow} \ + CONFIG.PCW_MIO_36_DIRECTION {in} \ + CONFIG.PCW_MIO_36_IOTYPE {LVCMOS 1.8V} \ + CONFIG.PCW_MIO_36_PULLUP {enabled} \ + CONFIG.PCW_MIO_36_SLEW {slow} \ + CONFIG.PCW_MIO_37_DIRECTION {inout} \ + CONFIG.PCW_MIO_37_IOTYPE {LVCMOS 1.8V} \ + CONFIG.PCW_MIO_37_PULLUP {enabled} \ + CONFIG.PCW_MIO_37_SLEW {slow} \ + CONFIG.PCW_MIO_38_DIRECTION {inout} \ + CONFIG.PCW_MIO_38_IOTYPE {LVCMOS 1.8V} \ + CONFIG.PCW_MIO_38_PULLUP {enabled} \ + CONFIG.PCW_MIO_38_SLEW {slow} \ + CONFIG.PCW_MIO_39_DIRECTION {inout} \ + CONFIG.PCW_MIO_39_IOTYPE {LVCMOS 1.8V} \ + CONFIG.PCW_MIO_39_PULLUP {enabled} \ + CONFIG.PCW_MIO_39_SLEW {slow} \ + CONFIG.PCW_MIO_3_DIRECTION {inout} \ + CONFIG.PCW_MIO_3_IOTYPE {LVCMOS 3.3V} \ + CONFIG.PCW_MIO_3_PULLUP {disabled} \ + CONFIG.PCW_MIO_3_SLEW {fast} \ + CONFIG.PCW_MIO_40_DIRECTION {inout} \ + CONFIG.PCW_MIO_40_IOTYPE {LVCMOS 1.8V} \ + CONFIG.PCW_MIO_40_PULLUP {enabled} \ + CONFIG.PCW_MIO_40_SLEW {slow} \ + CONFIG.PCW_MIO_41_DIRECTION {inout} \ + CONFIG.PCW_MIO_41_IOTYPE {LVCMOS 1.8V} \ + CONFIG.PCW_MIO_41_PULLUP {enabled} \ + CONFIG.PCW_MIO_41_SLEW {slow} \ + CONFIG.PCW_MIO_42_DIRECTION {inout} \ + CONFIG.PCW_MIO_42_IOTYPE {LVCMOS 1.8V} \ + CONFIG.PCW_MIO_42_PULLUP {enabled} \ + CONFIG.PCW_MIO_42_SLEW {slow} \ + CONFIG.PCW_MIO_43_DIRECTION {inout} \ + CONFIG.PCW_MIO_43_IOTYPE {LVCMOS 1.8V} \ + CONFIG.PCW_MIO_43_PULLUP {enabled} \ + CONFIG.PCW_MIO_43_SLEW {slow} \ + CONFIG.PCW_MIO_44_DIRECTION {inout} \ + CONFIG.PCW_MIO_44_IOTYPE {LVCMOS 1.8V} \ + CONFIG.PCW_MIO_44_PULLUP {enabled} \ + CONFIG.PCW_MIO_44_SLEW {slow} \ + CONFIG.PCW_MIO_45_DIRECTION {inout} \ + CONFIG.PCW_MIO_45_IOTYPE {LVCMOS 1.8V} \ + CONFIG.PCW_MIO_45_PULLUP {enabled} \ + CONFIG.PCW_MIO_45_SLEW {slow} \ + CONFIG.PCW_MIO_46_DIRECTION {inout} \ + CONFIG.PCW_MIO_46_IOTYPE {LVCMOS 1.8V} \ + CONFIG.PCW_MIO_46_PULLUP {enabled} \ + CONFIG.PCW_MIO_46_SLEW {slow} \ + CONFIG.PCW_MIO_47_DIRECTION {inout} \ + CONFIG.PCW_MIO_47_IOTYPE {LVCMOS 1.8V} \ + CONFIG.PCW_MIO_47_PULLUP {enabled} \ + CONFIG.PCW_MIO_47_SLEW {slow} \ + CONFIG.PCW_MIO_48_DIRECTION {inout} \ + CONFIG.PCW_MIO_48_IOTYPE {LVCMOS 1.8V} \ + CONFIG.PCW_MIO_48_PULLUP {enabled} \ + CONFIG.PCW_MIO_48_SLEW {slow} \ + CONFIG.PCW_MIO_49_DIRECTION {inout} \ + CONFIG.PCW_MIO_49_IOTYPE {LVCMOS 1.8V} \ + CONFIG.PCW_MIO_49_PULLUP {enabled} \ + CONFIG.PCW_MIO_49_SLEW {slow} \ + CONFIG.PCW_MIO_4_DIRECTION {inout} \ + CONFIG.PCW_MIO_4_IOTYPE {LVCMOS 3.3V} \ + CONFIG.PCW_MIO_4_PULLUP {disabled} \ + CONFIG.PCW_MIO_4_SLEW {fast} \ + CONFIG.PCW_MIO_50_DIRECTION {inout} \ + CONFIG.PCW_MIO_50_IOTYPE {LVCMOS 1.8V} \ + CONFIG.PCW_MIO_50_PULLUP {enabled} \ + CONFIG.PCW_MIO_50_SLEW {slow} \ + CONFIG.PCW_MIO_51_DIRECTION {inout} \ + CONFIG.PCW_MIO_51_IOTYPE {LVCMOS 1.8V} \ + CONFIG.PCW_MIO_51_PULLUP {enabled} \ + CONFIG.PCW_MIO_51_SLEW {slow} \ + CONFIG.PCW_MIO_52_DIRECTION {out} \ + CONFIG.PCW_MIO_52_IOTYPE {LVCMOS 1.8V} \ + CONFIG.PCW_MIO_52_PULLUP {enabled} \ + CONFIG.PCW_MIO_52_SLEW {slow} \ + CONFIG.PCW_MIO_53_DIRECTION {inout} \ + CONFIG.PCW_MIO_53_IOTYPE {LVCMOS 1.8V} \ + CONFIG.PCW_MIO_53_PULLUP {enabled} \ + CONFIG.PCW_MIO_53_SLEW {slow} \ + CONFIG.PCW_MIO_5_DIRECTION {inout} \ + CONFIG.PCW_MIO_5_IOTYPE {LVCMOS 3.3V} \ + CONFIG.PCW_MIO_5_PULLUP {disabled} \ + CONFIG.PCW_MIO_5_SLEW {fast} \ + CONFIG.PCW_MIO_6_DIRECTION {out} \ + CONFIG.PCW_MIO_6_IOTYPE {LVCMOS 3.3V} \ + CONFIG.PCW_MIO_6_PULLUP {disabled} \ + CONFIG.PCW_MIO_6_SLEW {fast} \ + CONFIG.PCW_MIO_7_DIRECTION {out} \ + CONFIG.PCW_MIO_7_IOTYPE {LVCMOS 3.3V} \ + CONFIG.PCW_MIO_7_PULLUP {disabled} \ + CONFIG.PCW_MIO_7_SLEW {slow} \ + CONFIG.PCW_MIO_8_DIRECTION {out} \ + CONFIG.PCW_MIO_8_IOTYPE {LVCMOS 3.3V} \ + CONFIG.PCW_MIO_8_PULLUP {disabled} \ + CONFIG.PCW_MIO_8_SLEW {slow} \ + CONFIG.PCW_MIO_9_DIRECTION {inout} \ + CONFIG.PCW_MIO_9_IOTYPE {LVCMOS 3.3V} \ + CONFIG.PCW_MIO_9_PULLUP {enabled} \ + CONFIG.PCW_MIO_9_SLEW {slow} \ + CONFIG.PCW_MIO_TREE_PERIPHERALS {\ +GPIO#Quad SPI Flash#Quad SPI Flash#Quad SPI Flash#Quad SPI Flash#Quad SPI\ +Flash#Quad SPI Flash#ENET Reset#USB Reset#GPIO#GPIO#GPIO#GPIO#GPIO#UART 0#UART\ +0#Enet 0#Enet 0#Enet 0#Enet 0#Enet 0#Enet 0#Enet 0#Enet 0#Enet 0#Enet 0#Enet\ +0#Enet 0#USB 0#USB 0#USB 0#USB 0#USB 0#USB 0#USB 0#USB 0#USB 0#USB 0#USB 0#USB\ +0#SD 0#SD 0#SD 0#SD 0#SD 0#SD 0#SD 1#SD 1#SD 1#SD 1#SD 1#SD 1#Enet 0#Enet 0} \ + CONFIG.PCW_MIO_TREE_SIGNALS {\ +gpio[0]#qspi0_ss_b#qspi0_io[0]#qspi0_io[1]#qspi0_io[2]#qspi0_io[3]/HOLD_B#qspi0_sclk#reset#reset#gpio[9]#gpio[10]#gpio[11]#gpio[12]#gpio[13]#rx#tx#tx_clk#txd[0]#txd[1]#txd[2]#txd[3]#tx_ctl#rx_clk#rxd[0]#rxd[1]#rxd[2]#rxd[3]#rx_ctl#data[4]#dir#stp#nxt#data[0]#data[1]#data[2]#data[3]#clk#data[5]#data[6]#data[7]#clk#cmd#data[0]#data[1]#data[2]#data[3]#data[0]#cmd#clk#data[1]#data[2]#data[3]#mdc#mdio} \ + CONFIG.PCW_NAND_GRP_D8_ENABLE {0} \ + CONFIG.PCW_NAND_PERIPHERAL_ENABLE {0} \ + CONFIG.PCW_NOR_GRP_A25_ENABLE {0} \ + CONFIG.PCW_NOR_GRP_CS0_ENABLE {0} \ + CONFIG.PCW_NOR_GRP_CS1_ENABLE {0} \ + CONFIG.PCW_NOR_GRP_SRAM_CS0_ENABLE {0} \ + CONFIG.PCW_NOR_GRP_SRAM_CS1_ENABLE {0} \ + CONFIG.PCW_NOR_GRP_SRAM_INT_ENABLE {0} \ + CONFIG.PCW_NOR_PERIPHERAL_ENABLE {0} \ + CONFIG.PCW_PCAP_PERIPHERAL_DIVISOR0 {5} \ + CONFIG.PCW_PRESET_BANK1_VOLTAGE {LVCMOS 1.8V} \ + CONFIG.PCW_QSPI_GRP_FBCLK_ENABLE {0} \ + CONFIG.PCW_QSPI_GRP_IO1_ENABLE {0} \ + CONFIG.PCW_QSPI_GRP_SINGLE_SS_ENABLE {1} \ + CONFIG.PCW_QSPI_GRP_SINGLE_SS_IO {MIO 1 .. 6} \ + CONFIG.PCW_QSPI_GRP_SS1_ENABLE {0} \ + CONFIG.PCW_QSPI_PERIPHERAL_DIVISOR0 {5} \ + CONFIG.PCW_QSPI_PERIPHERAL_ENABLE {1} \ + CONFIG.PCW_QSPI_PERIPHERAL_FREQMHZ {200} \ + CONFIG.PCW_QSPI_QSPI_IO {MIO 1 .. 6} \ + CONFIG.PCW_SD0_GRP_CD_ENABLE {0} \ + CONFIG.PCW_SD0_GRP_POW_ENABLE {0} \ + CONFIG.PCW_SD0_GRP_WP_ENABLE {0} \ + CONFIG.PCW_SD0_PERIPHERAL_ENABLE {1} \ + CONFIG.PCW_SD0_SD0_IO {MIO 40 .. 45} \ + CONFIG.PCW_SD1_GRP_CD_ENABLE {0} \ + CONFIG.PCW_SD1_GRP_POW_ENABLE {0} \ + CONFIG.PCW_SD1_GRP_WP_ENABLE {0} \ + CONFIG.PCW_SD1_PERIPHERAL_ENABLE {1} \ + CONFIG.PCW_SD1_SD1_IO {MIO 46 .. 51} \ + CONFIG.PCW_SDIO_PERIPHERAL_DIVISOR0 {10} \ + CONFIG.PCW_SDIO_PERIPHERAL_FREQMHZ {100} \ + CONFIG.PCW_SDIO_PERIPHERAL_VALID {1} \ + CONFIG.PCW_SINGLE_QSPI_DATA_MODE {x4} \ + CONFIG.PCW_SMC_PERIPHERAL_DIVISOR0 {1} \ + CONFIG.PCW_SPI_PERIPHERAL_DIVISOR0 {1} \ + CONFIG.PCW_TPIU_PERIPHERAL_DIVISOR0 {1} \ + CONFIG.PCW_TTC0_CLK0_PERIPHERAL_FREQMHZ {133.333333} \ + CONFIG.PCW_TTC0_CLK1_PERIPHERAL_FREQMHZ {133.333333} \ + CONFIG.PCW_TTC0_CLK2_PERIPHERAL_FREQMHZ {133.333333} \ + CONFIG.PCW_TTC0_PERIPHERAL_ENABLE {1} \ + CONFIG.PCW_TTC0_TTC0_IO {EMIO} \ + CONFIG.PCW_TTC_PERIPHERAL_FREQMHZ {50} \ + CONFIG.PCW_UART0_GRP_FULL_ENABLE {0} \ + CONFIG.PCW_UART0_PERIPHERAL_ENABLE {1} \ + CONFIG.PCW_UART0_UART0_IO {MIO 14 .. 15} \ + CONFIG.PCW_UART_PERIPHERAL_DIVISOR0 {10} \ + CONFIG.PCW_UART_PERIPHERAL_FREQMHZ {100} \ + CONFIG.PCW_UART_PERIPHERAL_VALID {1} \ + CONFIG.PCW_UIPARAM_ACT_DDR_FREQ_MHZ {533.333374} \ + CONFIG.PCW_UIPARAM_DDR_BANK_ADDR_COUNT {3} \ + CONFIG.PCW_UIPARAM_DDR_CL {7} \ + CONFIG.PCW_UIPARAM_DDR_COL_ADDR_COUNT {10} \ + CONFIG.PCW_UIPARAM_DDR_CWL {6} \ + CONFIG.PCW_UIPARAM_DDR_DEVICE_CAPACITY {2048 MBits} \ + CONFIG.PCW_UIPARAM_DDR_DRAM_WIDTH {16 Bits} \ + CONFIG.PCW_UIPARAM_DDR_PARTNO {MT41J128M16 HA-125} \ + CONFIG.PCW_UIPARAM_DDR_ROW_ADDR_COUNT {14} \ + CONFIG.PCW_UIPARAM_DDR_SPEED_BIN {DDR3_1066F} \ + CONFIG.PCW_UIPARAM_DDR_T_FAW {40.0} \ + CONFIG.PCW_UIPARAM_DDR_T_RAS_MIN {35.0} \ + CONFIG.PCW_UIPARAM_DDR_T_RC {48.75} \ + CONFIG.PCW_UIPARAM_DDR_T_RCD {7} \ + CONFIG.PCW_UIPARAM_DDR_T_RP {7} \ + CONFIG.PCW_USB0_PERIPHERAL_ENABLE {1} \ + CONFIG.PCW_USB0_PERIPHERAL_FREQMHZ {60} \ + CONFIG.PCW_USB0_RESET_ENABLE {1} \ + CONFIG.PCW_USB0_RESET_IO {MIO 8} \ + CONFIG.PCW_USB0_USB0_IO {MIO 28 .. 39} \ + CONFIG.PCW_USB1_RESET_ENABLE {0} \ + CONFIG.PCW_USB_RESET_ENABLE {1} \ + CONFIG.PCW_USB_RESET_SELECT {Share reset pin} \ + ] $processing_system7_0 + + # Create instance: ps7_0_axi_periph, and set properties + set ps7_0_axi_periph [ create_bd_cell -type ip -vlnv xilinx.com:ip:axi_interconnect:2.1 ps7_0_axi_periph ] + set_property -dict [ list \ + CONFIG.NUM_MI {2} \ + ] $ps7_0_axi_periph + + # Create instance: rst_ps7_0_200M, and set properties + set rst_ps7_0_200M [ create_bd_cell -type ip -vlnv xilinx.com:ip:proc_sys_reset:5.0 rst_ps7_0_200M ] + + # Create interface connections + connect_bd_intf_net -intf_net processing_system7_0_DDR [get_bd_intf_ports DDR] [get_bd_intf_pins processing_system7_0/DDR] + connect_bd_intf_net -intf_net processing_system7_0_FIXED_IO [get_bd_intf_ports FIXED_IO] [get_bd_intf_pins processing_system7_0/FIXED_IO] + connect_bd_intf_net -intf_net processing_system7_0_M_AXI_GP0 [get_bd_intf_pins processing_system7_0/M_AXI_GP0] [get_bd_intf_pins ps7_0_axi_periph/S00_AXI] + connect_bd_intf_net -intf_net ps7_0_axi_periph_M00_AXI [get_bd_intf_pins ip_encoder_0/S00_AXI] [get_bd_intf_pins ps7_0_axi_periph/M00_AXI] + connect_bd_intf_net -intf_net ps7_0_axi_periph_M01_AXI [get_bd_intf_pins ip_fan_0/S00_AXI] [get_bd_intf_pins ps7_0_axi_periph/M01_AXI] + + # Create port connections + connect_bd_net -net exrst_n_0_1 [get_bd_ports exrst_n] [get_bd_pins ip_encoder_0/exrst_n] + connect_bd_net -net in_signal_0_1 [get_bd_ports encoder_signal] [get_bd_pins ip_encoder_0/in_signal] + connect_bd_net -net ip_encoder_0_out_signal_camera_a [get_bd_ports out_signal_camera_a] [get_bd_pins ip_encoder_0/out_signal_camera_a] + connect_bd_net -net ip_encoder_0_out_signal_camera_b [get_bd_ports out_signal_camera_b] [get_bd_pins ip_encoder_0/out_signal_camera_b] + connect_bd_net -net ip_encoder_0_out_signal_camera_c [get_bd_ports out_signal_camera_c] [get_bd_pins ip_encoder_0/out_signal_camera_c] + connect_bd_net -net ip_encoder_0_out_signal_camera_d [get_bd_ports out_signal_camera_d] [get_bd_pins ip_encoder_0/out_signal_camera_d] + connect_bd_net -net ip_fan_0_fan [get_bd_ports fan] [get_bd_pins ip_fan_0/fan] + connect_bd_net -net processing_system7_0_FCLK_CLK0 [get_bd_pins ip_encoder_0/s00_axi_aclk] [get_bd_pins ip_fan_0/s00_axi_aclk] [get_bd_pins processing_system7_0/FCLK_CLK0] [get_bd_pins processing_system7_0/M_AXI_GP0_ACLK] [get_bd_pins ps7_0_axi_periph/ACLK] [get_bd_pins ps7_0_axi_periph/M00_ACLK] [get_bd_pins ps7_0_axi_periph/M01_ACLK] [get_bd_pins ps7_0_axi_periph/S00_ACLK] [get_bd_pins rst_ps7_0_200M/slowest_sync_clk] + connect_bd_net -net processing_system7_0_FCLK_RESET0_N [get_bd_pins processing_system7_0/FCLK_RESET0_N] [get_bd_pins rst_ps7_0_200M/ext_reset_in] + connect_bd_net -net rst_ps7_0_200M_peripheral_aresetn [get_bd_pins ip_encoder_0/s00_axi_aresetn] [get_bd_pins ip_fan_0/s00_axi_aresetn] [get_bd_pins ps7_0_axi_periph/ARESETN] [get_bd_pins ps7_0_axi_periph/M00_ARESETN] [get_bd_pins ps7_0_axi_periph/M01_ARESETN] [get_bd_pins ps7_0_axi_periph/S00_ARESETN] [get_bd_pins rst_ps7_0_200M/peripheral_aresetn] + + # Create address segments + assign_bd_address -offset 0x43C10000 -range 0x00010000 -target_address_space [get_bd_addr_spaces processing_system7_0/Data] [get_bd_addr_segs ip_encoder_0/S00_AXI/S00_AXI_reg] -force + assign_bd_address -offset 0x43C20000 -range 0x00010000 -target_address_space [get_bd_addr_spaces processing_system7_0/Data] [get_bd_addr_segs ip_fan_0/S00_AXI/S00_AXI_reg] -force + + + # Restore current instance + current_bd_instance $oldCurInst + + validate_bd_design + save_bd_design +} +# End of create_root_design() + + +################################################################## +# MAIN FLOW +################################################################## + +create_root_design "" + + diff --git a/hardware/pl_platform/cstr/lower_machine.xdc b/hardware/pl_platform/cstr/lower_machine.xdc new file mode 100644 index 0000000..fcbfbd2 --- /dev/null +++ b/hardware/pl_platform/cstr/lower_machine.xdc @@ -0,0 +1,30 @@ + +set_property PACKAGE_PIN R14 [get_ports encoder_signal] +set_property IOSTANDARD LVCMOS33 [get_ports encoder_signal] + + +set_property PACKAGE_PIN J20 [get_ports fan] +set_property IOSTANDARD LVCMOS33 [get_ports fan] +set_property SLEW SLOW [get_ports fan] + + +set_property PACKAGE_PIN T10 [get_ports out_signal_camera_a] +set_property IOSTANDARD LVCMOS33 [get_ports out_signal_camera_a] +set_property SLEW FAST [get_ports out_signal_camera_a] +set_property IOSTANDARD LVCMOS33 [get_ports out_signal_camera_b] +set_property IOSTANDARD LVCMOS33 [get_ports out_signal_camera_c] +set_property IOSTANDARD LVCMOS33 [get_ports out_signal_camera_d] +set_property PACKAGE_PIN U12 [get_ports out_signal_camera_b] +set_property PACKAGE_PIN V12 [get_ports out_signal_camera_c] +set_property PACKAGE_PIN W13 [get_ports out_signal_camera_d] +set_property SLEW FAST [get_ports out_signal_camera_b] +set_property SLEW FAST [get_ports out_signal_camera_c] +set_property SLEW FAST [get_ports out_signal_camera_d] + +set_property OFFCHIP_TERM NONE [get_ports fan] +set_property OFFCHIP_TERM NONE [get_ports out_signal_camera_a] +set_property OFFCHIP_TERM NONE [get_ports out_signal_camera_b] +set_property OFFCHIP_TERM NONE [get_ports out_signal_camera_c] +set_property OFFCHIP_TERM NONE [get_ports out_signal_camera_d] +set_property IOSTANDARD LVCMOS33 [get_ports exrst_n] +set_property PACKAGE_PIN T12 [get_ports exrst_n] diff --git a/hardware/pl_platform/ip_repo/ip_encoder_1.0/.Xil/.ip_encoder_0.xcix.lock b/hardware/pl_platform/ip_repo/ip_encoder_1.0/.Xil/.ip_encoder_0.xcix.lock new file mode 100644 index 0000000..e69de29 diff --git a/hardware/pl_platform/ip_repo/ip_encoder_1.0/bd/bd.tcl b/hardware/pl_platform/ip_repo/ip_encoder_1.0/bd/bd.tcl new file mode 100644 index 0000000..4804aeb --- /dev/null +++ b/hardware/pl_platform/ip_repo/ip_encoder_1.0/bd/bd.tcl @@ -0,0 +1,86 @@ + +proc init { cellpath otherInfo } { + + set cell_handle [get_bd_cells $cellpath] + set all_busif [get_bd_intf_pins $cellpath/*] + set axi_standard_param_list [list ID_WIDTH AWUSER_WIDTH ARUSER_WIDTH WUSER_WIDTH RUSER_WIDTH BUSER_WIDTH] + set full_sbusif_list [list ] + + foreach busif $all_busif { + if { [string equal -nocase [get_property MODE $busif] "slave"] == 1 } { + set busif_param_list [list] + set busif_name [get_property NAME $busif] + if { [lsearch -exact -nocase $full_sbusif_list $busif_name ] == -1 } { + continue + } + foreach tparam $axi_standard_param_list { + lappend busif_param_list "C_${busif_name}_${tparam}" + } + bd::mark_propagate_only $cell_handle $busif_param_list + } + } +} + + +proc pre_propagate {cellpath otherInfo } { + + set cell_handle [get_bd_cells $cellpath] + set all_busif [get_bd_intf_pins $cellpath/*] + set axi_standard_param_list [list ID_WIDTH AWUSER_WIDTH ARUSER_WIDTH WUSER_WIDTH RUSER_WIDTH BUSER_WIDTH] + + foreach busif $all_busif { + if { [string equal -nocase [get_property CONFIG.PROTOCOL $busif] "AXI4"] != 1 } { + continue + } + if { [string equal -nocase [get_property MODE $busif] "master"] != 1 } { + continue + } + + set busif_name [get_property NAME $busif] + foreach tparam $axi_standard_param_list { + set busif_param_name "C_${busif_name}_${tparam}" + + set val_on_cell_intf_pin [get_property CONFIG.${tparam} $busif] + set val_on_cell [get_property CONFIG.${busif_param_name} $cell_handle] + + if { [string equal -nocase $val_on_cell_intf_pin $val_on_cell] != 1 } { + if { $val_on_cell != "" } { + set_property CONFIG.${tparam} $val_on_cell $busif + } + } + } + } +} + + +proc propagate {cellpath otherInfo } { + + set cell_handle [get_bd_cells $cellpath] + set all_busif [get_bd_intf_pins $cellpath/*] + set axi_standard_param_list [list ID_WIDTH AWUSER_WIDTH ARUSER_WIDTH WUSER_WIDTH RUSER_WIDTH BUSER_WIDTH] + + foreach busif $all_busif { + if { [string equal -nocase [get_property CONFIG.PROTOCOL $busif] "AXI4"] != 1 } { + continue + } + if { [string equal -nocase [get_property MODE $busif] "slave"] != 1 } { + continue + } + + set busif_name [get_property NAME $busif] + foreach tparam $axi_standard_param_list { + set busif_param_name "C_${busif_name}_${tparam}" + + set val_on_cell_intf_pin [get_property CONFIG.${tparam} $busif] + set val_on_cell [get_property CONFIG.${busif_param_name} $cell_handle] + + if { [string equal -nocase $val_on_cell_intf_pin $val_on_cell] != 1 } { + #override property of bd_interface_net to bd_cell -- only for slaves. May check for supported values.. + if { $val_on_cell_intf_pin != "" } { + set_property CONFIG.${busif_param_name} $val_on_cell_intf_pin $cell_handle + } + } + } + } +} + diff --git a/hardware/pl_platform/ip_repo/ip_encoder_1.0/component.xml b/hardware/pl_platform/ip_repo/ip_encoder_1.0/component.xml new file mode 100644 index 0000000..b733991 --- /dev/null +++ b/hardware/pl_platform/ip_repo/ip_encoder_1.0/component.xml @@ -0,0 +1,1105 @@ + + + user.org + user + ip_encoder + 1.1 + + + S00_AXI + + + + + + + + + AWADDR + + + s00_axi_awaddr + + + + + AWPROT + + + s00_axi_awprot + + + + + AWVALID + + + s00_axi_awvalid + + + + + AWREADY + + + s00_axi_awready + + + + + WDATA + + + s00_axi_wdata + + + + + WSTRB + + + s00_axi_wstrb + + + + + WVALID + + + s00_axi_wvalid + + + + + WREADY + + + s00_axi_wready + + + + + BRESP + + + s00_axi_bresp + + + + + BVALID + + + s00_axi_bvalid + + + + + BREADY + + + s00_axi_bready + + + + + ARADDR + + + s00_axi_araddr + + + + + ARPROT + + + s00_axi_arprot + + + + + ARVALID + + + s00_axi_arvalid + + + + + ARREADY + + + s00_axi_arready + + + + + RDATA + + + s00_axi_rdata + + + + + RRESP + + + s00_axi_rresp + + + + + RVALID + + + s00_axi_rvalid + + + + + RREADY + + + s00_axi_rready + + + + + + WIZ_DATA_WIDTH + 32 + + + WIZ_NUM_REG + 4 + + + SUPPORTS_NARROW_BURST + 0 + + + + + S00_AXI_RST + + + + + + + RST + + + s00_axi_aresetn + + + + + + POLARITY + ACTIVE_LOW + + + + + S00_AXI_CLK + + + + + + + CLK + + + s00_axi_aclk + + + + + + ASSOCIATED_BUSIF + S00_AXI + + + ASSOCIATED_RESET + s00_axi_aresetn + + + + + + + S00_AXI + + S00_AXI_reg + 0 + 4096 + 32 + register + + + OFFSET_BASE_PARAM + C_S00_AXI_BASEADDR + + + OFFSET_HIGH_PARAM + C_S00_AXI_HIGHADDR + + + + + + + + + xilinx_verilogsynthesis + Verilog Synthesis + verilogSource:vivado.xilinx.com:synthesis + verilog + ip_encoder_v1_0 + + xilinx_verilogsynthesis_view_fileset + + + + viewChecksum + 01ec01e9 + + + + + xilinx_verilogbehavioralsimulation + Verilog Simulation + verilogSource:vivado.xilinx.com:simulation + verilog + ip_encoder_v1_0 + + xilinx_verilogbehavioralsimulation_view_fileset + + + + viewChecksum + 01ec01e9 + + + + + xilinx_softwaredriver + Software Driver + :vivado.xilinx.com:sw.driver + + xilinx_softwaredriver_view_fileset + + + + viewChecksum + 5ea3f00b + + + + + xilinx_xpgui + UI Layout + :vivado.xilinx.com:xgui.ui + + xilinx_xpgui_view_fileset + + + + viewChecksum + cb63bd89 + + + + + bd_tcl + Block Diagram + :vivado.xilinx.com:block.diagram + + bd_tcl_view_fileset + + + + viewChecksum + 45a2f450 + + + + + + + in_signal + + in + + + std_logic + xilinx_verilogsynthesis + xilinx_verilogbehavioralsimulation + + + + + + exrst_n + + in + + + std_logic + xilinx_verilogsynthesis + xilinx_verilogbehavioralsimulation + + + + + + out_signal_valve_posedge + + out + + + std_logic + xilinx_verilogsynthesis + xilinx_verilogbehavioralsimulation + + + + + + out_signal_valve + + out + + + std_logic + xilinx_verilogsynthesis + xilinx_verilogbehavioralsimulation + + + + + + out_signal_camera_a_posedge + + out + + + std_logic + xilinx_verilogsynthesis + xilinx_verilogbehavioralsimulation + + + + + + out_signal_camera_b_posedge + + out + + + std_logic + xilinx_verilogsynthesis + xilinx_verilogbehavioralsimulation + + + + + + out_signal_camera_c_posedge + + out + + + std_logic + xilinx_verilogsynthesis + xilinx_verilogbehavioralsimulation + + + + + + out_signal_camera_d_posedge + + out + + + std_logic + xilinx_verilogsynthesis + xilinx_verilogbehavioralsimulation + + + + + + out_signal_camera_a + + out + + + std_logic + xilinx_verilogsynthesis + xilinx_verilogbehavioralsimulation + + + + + + out_signal_camera_b + + out + + + std_logic + xilinx_verilogsynthesis + xilinx_verilogbehavioralsimulation + + + + + + out_signal_camera_c + + out + + + std_logic + xilinx_verilogsynthesis + xilinx_verilogbehavioralsimulation + + + + + + out_signal_camera_d + + out + + + std_logic + xilinx_verilogsynthesis + xilinx_verilogbehavioralsimulation + + + + + + s00_axi_aclk + + in + + + wire + xilinx_verilogsynthesis + xilinx_verilogbehavioralsimulation + + + + + + s00_axi_aresetn + + in + + + wire + xilinx_verilogsynthesis + xilinx_verilogbehavioralsimulation + + + + + + s00_axi_awaddr + + in + + 4 + 0 + + + + wire + xilinx_verilogsynthesis + xilinx_verilogbehavioralsimulation + + + + + + s00_axi_awprot + + in + + 2 + 0 + + + + wire + xilinx_verilogsynthesis + xilinx_verilogbehavioralsimulation + + + + + + s00_axi_awvalid + + in + + + wire + xilinx_verilogsynthesis + xilinx_verilogbehavioralsimulation + + + + + + s00_axi_awready + + out + + + wire + xilinx_verilogsynthesis + xilinx_verilogbehavioralsimulation + + + + + + s00_axi_wdata + + in + + 31 + 0 + + + + wire + xilinx_verilogsynthesis + xilinx_verilogbehavioralsimulation + + + + + + s00_axi_wstrb + + in + + 3 + 0 + + + + wire + xilinx_verilogsynthesis + xilinx_verilogbehavioralsimulation + + + + + + s00_axi_wvalid + + in + + + wire + xilinx_verilogsynthesis + xilinx_verilogbehavioralsimulation + + + + + + s00_axi_wready + + out + + + wire + xilinx_verilogsynthesis + xilinx_verilogbehavioralsimulation + + + + + + s00_axi_bresp + + out + + 1 + 0 + + + + wire + xilinx_verilogsynthesis + xilinx_verilogbehavioralsimulation + + + + + + s00_axi_bvalid + + out + + + wire + xilinx_verilogsynthesis + xilinx_verilogbehavioralsimulation + + + + + + s00_axi_bready + + in + + + wire + xilinx_verilogsynthesis + xilinx_verilogbehavioralsimulation + + + + + + s00_axi_araddr + + in + + 4 + 0 + + + + wire + xilinx_verilogsynthesis + xilinx_verilogbehavioralsimulation + + + + + + s00_axi_arprot + + in + + 2 + 0 + + + + wire + xilinx_verilogsynthesis + xilinx_verilogbehavioralsimulation + + + + + + s00_axi_arvalid + + in + + + wire + xilinx_verilogsynthesis + xilinx_verilogbehavioralsimulation + + + + + + s00_axi_arready + + out + + + wire + xilinx_verilogsynthesis + xilinx_verilogbehavioralsimulation + + + + + + s00_axi_rdata + + out + + 31 + 0 + + + + wire + xilinx_verilogsynthesis + xilinx_verilogbehavioralsimulation + + + + + + s00_axi_rresp + + out + + 1 + 0 + + + + wire + xilinx_verilogsynthesis + xilinx_verilogbehavioralsimulation + + + + + + s00_axi_rvalid + + out + + + wire + xilinx_verilogsynthesis + xilinx_verilogbehavioralsimulation + + + + + + s00_axi_rready + + in + + + wire + xilinx_verilogsynthesis + xilinx_verilogbehavioralsimulation + + + + + + + + C_S00_AXI_DATA_WIDTH + C S00 AXI DATA WIDTH + Width of S_AXI data bus + 32 + + + C_S00_AXI_ADDR_WIDTH + C S00 AXI ADDR WIDTH + Width of S_AXI address bus + 5 + + + + + + choice_list_6fc15197 + 32 + + + choice_list_9d8b0d81 + ACTIVE_HIGH + ACTIVE_LOW + + + choice_pairs_ce1226b1 + 1 + 0 + + + + + xilinx_verilogsynthesis_view_fileset + + src/encoder.v + verilogSource + + + hdl/ip_encoder_v1_0_S00_AXI.v + verilogSource + + + hdl/ip_encoder_v1_0.v + verilogSource + CHECKSUM_33abba7b + + + + xilinx_verilogbehavioralsimulation_view_fileset + + src/encoder.v + verilogSource + + + hdl/ip_encoder_v1_0_S00_AXI.v + verilogSource + + + hdl/ip_encoder_v1_0.v + verilogSource + + + + xilinx_softwaredriver_view_fileset + + drivers/ip_encoder_v1_0/data/ip_encoder.mdd + mdd + driver_mdd + + + drivers/ip_encoder_v1_0/data/ip_encoder.tcl + tclSource + driver_tcl + + + drivers/ip_encoder_v1_0/src/Makefile + driver_src + + + drivers/ip_encoder_v1_0/src/ip_encoder.h + cSource + driver_src + + + drivers/ip_encoder_v1_0/src/ip_encoder.c + cSource + driver_src + + + drivers/ip_encoder_v1_0/src/ip_encoder_selftest.c + cSource + driver_src + + + + xilinx_xpgui_view_fileset + + xgui/ip_encoder_v1_1.tcl + tclSource + CHECKSUM_cb63bd89 + XGUI_VERSION_2 + + + + bd_tcl_view_fileset + + bd/bd.tcl + tclSource + + + + ip_encoder + + + C_S00_AXI_DATA_WIDTH + C S00 AXI DATA WIDTH + Width of S_AXI data bus + 32 + + + + false + + + + + + C_S00_AXI_ADDR_WIDTH + C S00 AXI ADDR WIDTH + Width of S_AXI address bus + 5 + + + + false + + + + + + C_S00_AXI_BASEADDR + C S00 AXI BASEADDR + 0xFFFFFFFF + + + + false + + + + + + C_S00_AXI_HIGHADDR + C S00 AXI HIGHADDR + 0x00000000 + + + + false + + + + + + Component_Name + ip_encoder_v1_0 + + + + + + zynq + + + AXI_Peripheral + + ip_encoder_v1.0 + 20 + + user.org:user:ip_encoder:1.0 + + 2023-04-26T08:46:12Z + + /home/miaow/zynq/ip_repo/ip_encoder_1.0 + /home/miaow/zynq/ip_repo/ip_encoder_1.0 + /home/miaow/zynq/ip_repo/ip_encoder_1.0 + /home/miaow/zynq/ip_repo/ip_encoder_1.0 + /home/miaow/zynq/ip_repo/ip_encoder_1.0 + /home/miaow/zynq/ip_repo/ip_encoder_1.0 + /home/miaow/zynq/ip_repo/ip_encoder_1.0 + /home/miaow/zynq/ip_repo/ip_encoder_1.0 + /home/miaow/zynq/ip_repo/ip_encoder_1.0 + /home/miaow/zynq/ip_repo/ip_encoder_1.0 + /home/miaow/zynq/ip_repo/ip_encoder_1.0 + /home/miaow/zynq/ip_repo/ip_encoder_1.0 + /home/miaow/zynq/ip_repo/ip_encoder_1.0 + /home/miaow/zynq/ip_repo/ip_encoder_1.0 + /home/miaow/zynq/ip_repo/ip_encoder_1.0 + /home/miaow/zynq/ip_repo/ip_encoder_1.0 + /home/miaow/zynq/ip_repo/ip_encoder_1.0 + /home/miaow/zynq/ip_repo/ip_encoder_1.0 + /home/miaow/zynq/ip_repo/ip_encoder_1.0 + /home/miaow/zynq/ip_repo/ip_encoder_1.0 + /home/miaow/zynq/ip_repo/ip_encoder_1.0 + /home/miaow/zynq/ip_repo/ip_encoder_1.0 + /home/miaow/zynq/ip_repo/ip_encoder_1.0 + /home/miaow/zynq/ip_repo/ip_encoder_1.0 + /home/miaow/zynq/ip_repo/ip_encoder_1.0 + /home/miaow/zynq/ip_repo/ip_encoder_1.0 + /home/miaow/zynq/ip_repo/ip_encoder_1.0 + /home/miaow/zynq/ip_repo/ip_encoder_1.0 + /home/miaow/zynq/ip_repo/ip_encoder_1.0 + /home/miaow/zynq/ip_repo/ip_encoder_1.0 + /home/miaow/zynq/ip_repo/ip_encoder_1.0 + /home/miaow/zynq/ip_repo/ip_encoder_1.0 + /home/miaow/zynq/ip_repo/ip_encoder_1.0 + /home/miaow/zynq/ip_repo/ip_encoder_1.0 + /home/miaow/zynq/ip_repo/ip_encoder_1.0 + /home/miaow/zynq/ip_repo/ip_encoder_1.0 + /home/miaow/zynq/ip_repo/ip_encoder_1.0 + /home/miaow/zynq/ip_repo/ip_encoder_1.0 + /home/miaow/zynq/ip_repo/ip_encoder_1.0 + /home/miaow/zynq/ip_repo/ip_encoder_1.0 + /home/miaow/zynq/ip_repo/ip_encoder_1.0 + /home/miaow/zynq/ip_repo/ip_encoder_1.0 + /home/miaow/zynq/ip_repo/ip_encoder_1.0 + /home/miaow/zynq/ip_repo/ip_encoder_1.0 + /home/miaow/zynq/ip_repo/ip_encoder_1.0 + /home/miaow/zynq/ip_repo/ip_encoder_1.0 + /home/miaow/zynq/ip_repo/ip_encoder_1.0 + /home/miaow/zynq/ip_repo/ip_encoder_1.0 + /home/miaow/zynq/ip_repo/ip_encoder_1.0 + /home/miaow/zynq/ip_repo/ip_encoder_1.0 + /home/miaow/zynq/ip_repo/ip_encoder_1.0 + /home/miaow/zynq/ip_repo/ip_encoder_1.0 + /home/miaow/zynq/ip_repo/ip_encoder_1.0 + /home/miaow/zynq/ip_repo/ip_encoder_1.0 + /home/miaow/zynq/ip_repo/ip_encoder_1.0 + /home/miaow/zynq/ip_repo/ip_encoder_1.0 + /home/miaow/zynq/ip_repo/ip_encoder_1.0 + /home/miaow/zynq/ip_repo/ip_encoder_1.0 + /home/miaow/zynq/ip_repo/ip_encoder_1.0 + /home/miaow/zynq/ip_repo/ip_encoder_1.0 + /home/miaow/zynq/ip_repo/ip_encoder_1.0 + /home/miaow/zynq/ip_repo/ip_encoder_1.0 + /home/miaow/zynq/ip_repo/ip_encoder_1.0 + /home/miaow/zynq/ip_repo/ip_encoder_1.0 + /home/miaow/zynq/ip_repo/ip_encoder_1.0 + /home/miaow/zynq/ip_repo/ip_encoder_1.0 + /home/miaow/zynq/ip_repo/ip_encoder_1.0 + /home/miaow/zynq/ip_repo/ip_encoder_1.0 + /home/miaow/zynq/ip_repo/ip_encoder_1.0 + /home/miaow/zynq/ip_repo/ip_encoder_1.0 + /home/miaow/zynq/ip_repo/ip_encoder_1.0 + /home/miaow/zynq/ip_repo/ip_encoder_1.0 + /home/miaow/zynq/ip_repo/ip_encoder_1.0 + /home/miaow/zynq/ip_repo/ip_encoder_1.0 + /home/miaow/zynq/ip_repo/ip_encoder_1.0 + /home/miaow/zynq/ip_repo/ip_encoder_1.0 + /home/miaow/zynq/ip_repo/ip_encoder_1.0 + /home/miaow/zynq/ip_repo/ip_encoder_1.0 + /home/miaow/zynq/ip_repo/ip_encoder_1.0 + /home/miaow/zynq/ip_repo/ip_encoder_1.0 + /home/miaow/zynq/ip_repo/ip_encoder_1.0 + /home/miaow/zynq/ip_repo/ip_encoder_1.0 + /home/miaow/zynq/ip_repo/ip_encoder_1.0 + /home/miaow/zynq/ip_repo/ip_encoder_1.0 + /home/miaow/zynq/ip_repo/ip_encoder_1.0 + /home/miaow/zynq/ip_repo/ip_encoder_1.0 + /home/miaow/zynq/ip_repo/ip_encoder_1.0 + /home/miaow/zynq/ip_repo/ip_encoder_1.0 + /home/miaow/zynq/ip_repo/ip_encoder_1.0 + /home/miaow/zynq/ip_repo/ip_encoder_1.0 + /home/miaow/zynq/ip_repo/ip_encoder_1.0 + /home/miaow/zynq/ip_repo/ip_encoder_1.0 + /home/miaow/zynq/ip_repo/ip_encoder_1.0 + /home/miaow/zynq/ip_repo/ip_encoder_1.0 + /home/miaow/zynq/ip_repo/ip_encoder_1.0 + /home/miaow/zynq/ip_repo/ip_encoder_1.0 + /home/miaow/zynq/ip_repo/ip_encoder_1.0 + /home/miaow/zynq/ip_repo/ip_encoder_1.0 + /home/miaow/zynq/ip_repo/ip_encoder_1.0 + /home/miaow/zynq/ip_repo/ip_encoder_1.0 + /home/miaow/zynq/ip_repo/ip_encoder_1.0 + /home/miaow/zynq/ip_repo/ip_encoder_1.0 + /home/miaow/zynq/ip_repo/ip_encoder_1.0 + /home/miaow/zynq/ip_repo/ip_encoder_1.0 + /home/miaow/zynq/ip_repo/ip_encoder_1.0 + + + + 2022.1 + + + + + + + + + + + + + + diff --git a/hardware/pl_platform/ip_repo/ip_encoder_1.0/drivers/ip_encoder_v1_0/data/ip_encoder.mdd b/hardware/pl_platform/ip_repo/ip_encoder_1.0/drivers/ip_encoder_v1_0/data/ip_encoder.mdd new file mode 100644 index 0000000..ba75dbe --- /dev/null +++ b/hardware/pl_platform/ip_repo/ip_encoder_1.0/drivers/ip_encoder_v1_0/data/ip_encoder.mdd @@ -0,0 +1,10 @@ + + +OPTION psf_version = 2.1; + +BEGIN DRIVER ip_encoder + OPTION supported_peripherals = (ip_encoder); + OPTION copyfiles = all; + OPTION VERSION = 1.0; + OPTION NAME = ip_encoder; +END DRIVER diff --git a/hardware/pl_platform/ip_repo/ip_encoder_1.0/drivers/ip_encoder_v1_0/data/ip_encoder.tcl b/hardware/pl_platform/ip_repo/ip_encoder_1.0/drivers/ip_encoder_v1_0/data/ip_encoder.tcl new file mode 100644 index 0000000..e4dbbf0 --- /dev/null +++ b/hardware/pl_platform/ip_repo/ip_encoder_1.0/drivers/ip_encoder_v1_0/data/ip_encoder.tcl @@ -0,0 +1,5 @@ + + +proc generate {drv_handle} { + xdefine_include_file $drv_handle "xparameters.h" "ip_encoder" "NUM_INSTANCES" "DEVICE_ID" "C_S00_AXI_BASEADDR" "C_S00_AXI_HIGHADDR" +} diff --git a/hardware/pl_platform/ip_repo/ip_encoder_1.0/drivers/ip_encoder_v1_0/src/Makefile b/hardware/pl_platform/ip_repo/ip_encoder_1.0/drivers/ip_encoder_v1_0/src/Makefile new file mode 100644 index 0000000..18d6967 --- /dev/null +++ b/hardware/pl_platform/ip_repo/ip_encoder_1.0/drivers/ip_encoder_v1_0/src/Makefile @@ -0,0 +1,26 @@ +COMPILER= +ARCHIVER= +CP=cp +COMPILER_FLAGS= +EXTRA_COMPILER_FLAGS= +LIB=libxil.a + +RELEASEDIR=../../../lib +INCLUDEDIR=../../../include +INCLUDES=-I./. -I${INCLUDEDIR} + +INCLUDEFILES=*.h +LIBSOURCES=*.c +OUTS = *.o + +libs: + echo "Compiling ip_encoder..." + $(COMPILER) $(COMPILER_FLAGS) $(EXTRA_COMPILER_FLAGS) $(INCLUDES) $(LIBSOURCES) + $(ARCHIVER) -r ${RELEASEDIR}/${LIB} ${OUTS} + make clean + +include: + ${CP} $(INCLUDEFILES) $(INCLUDEDIR) + +clean: + rm -rf ${OUTS} diff --git a/hardware/pl_platform/ip_repo/ip_encoder_1.0/drivers/ip_encoder_v1_0/src/ip_encoder.c b/hardware/pl_platform/ip_repo/ip_encoder_1.0/drivers/ip_encoder_v1_0/src/ip_encoder.c new file mode 100644 index 0000000..d3162a7 --- /dev/null +++ b/hardware/pl_platform/ip_repo/ip_encoder_1.0/drivers/ip_encoder_v1_0/src/ip_encoder.c @@ -0,0 +1,6 @@ + + +/***************************** Include Files *******************************/ +#include "ip_encoder.h" + +/************************** Function Definitions ***************************/ diff --git a/hardware/pl_platform/ip_repo/ip_encoder_1.0/drivers/ip_encoder_v1_0/src/ip_encoder.h b/hardware/pl_platform/ip_repo/ip_encoder_1.0/drivers/ip_encoder_v1_0/src/ip_encoder.h new file mode 100644 index 0000000..562108a --- /dev/null +++ b/hardware/pl_platform/ip_repo/ip_encoder_1.0/drivers/ip_encoder_v1_0/src/ip_encoder.h @@ -0,0 +1,79 @@ + +#ifndef IP_ENCODER_H +#define IP_ENCODER_H + + +/****************** Include Files ********************/ +#include "xil_types.h" +#include "xstatus.h" + +#define IP_ENCODER_S00_AXI_SLV_REG0_OFFSET 0 +#define IP_ENCODER_S00_AXI_SLV_REG1_OFFSET 4 +#define IP_ENCODER_S00_AXI_SLV_REG2_OFFSET 8 +#define IP_ENCODER_S00_AXI_SLV_REG3_OFFSET 12 + + +/**************************** Type Definitions *****************************/ +/** + * + * Write a value to a IP_ENCODER register. A 32 bit write is performed. + * If the component is implemented in a smaller width, only the least + * significant data is written. + * + * @param BaseAddress is the base address of the IP_ENCODERdevice. + * @param RegOffset is the register offset from the base to write to. + * @param Data is the data written to the register. + * + * @return None. + * + * @note + * C-style signature: + * void IP_ENCODER_mWriteReg(u32 BaseAddress, unsigned RegOffset, u32 Data) + * + */ +#define IP_ENCODER_mWriteReg(BaseAddress, RegOffset, Data) \ + Xil_Out32((BaseAddress) + (RegOffset), (u32)(Data)) + +/** + * + * Read a value from a IP_ENCODER register. A 32 bit read is performed. + * If the component is implemented in a smaller width, only the least + * significant data is read from the register. The most significant data + * will be read as 0. + * + * @param BaseAddress is the base address of the IP_ENCODER device. + * @param RegOffset is the register offset from the base to write to. + * + * @return Data is the data from the register. + * + * @note + * C-style signature: + * u32 IP_ENCODER_mReadReg(u32 BaseAddress, unsigned RegOffset) + * + */ +#define IP_ENCODER_mReadReg(BaseAddress, RegOffset) \ + Xil_In32((BaseAddress) + (RegOffset)) + +/************************** Function Prototypes ****************************/ +/** + * + * Run a self-test on the driver/device. Note this may be a destructive test if + * resets of the device are performed. + * + * If the hardware system is not built correctly, this function may never + * return to the caller. + * + * @param baseaddr_p is the base address of the IP_ENCODER instance to be worked on. + * + * @return + * + * - XST_SUCCESS if all self-test code passed + * - XST_FAILURE if any self-test code failed + * + * @note Caching must be turned off for this function to work. + * @note Self test may fail if data memory and device are not on the same bus. + * + */ +XStatus IP_ENCODER_Reg_SelfTest(void * baseaddr_p); + +#endif // IP_ENCODER_H diff --git a/hardware/pl_platform/ip_repo/ip_encoder_1.0/drivers/ip_encoder_v1_0/src/ip_encoder_selftest.c b/hardware/pl_platform/ip_repo/ip_encoder_1.0/drivers/ip_encoder_v1_0/src/ip_encoder_selftest.c new file mode 100644 index 0000000..bc1f76c --- /dev/null +++ b/hardware/pl_platform/ip_repo/ip_encoder_1.0/drivers/ip_encoder_v1_0/src/ip_encoder_selftest.c @@ -0,0 +1,60 @@ + +/***************************** Include Files *******************************/ +#include "ip_encoder.h" +#include "xparameters.h" +#include "stdio.h" +#include "xil_io.h" + +/************************** Constant Definitions ***************************/ +#define READ_WRITE_MUL_FACTOR 0x10 + +/************************** Function Definitions ***************************/ +/** + * + * Run a self-test on the driver/device. Note this may be a destructive test if + * resets of the device are performed. + * + * If the hardware system is not built correctly, this function may never + * return to the caller. + * + * @param baseaddr_p is the base address of the IP_ENCODERinstance to be worked on. + * + * @return + * + * - XST_SUCCESS if all self-test code passed + * - XST_FAILURE if any self-test code failed + * + * @note Caching must be turned off for this function to work. + * @note Self test may fail if data memory and device are not on the same bus. + * + */ +XStatus IP_ENCODER_Reg_SelfTest(void * baseaddr_p) +{ + u32 baseaddr; + int write_loop_index; + int read_loop_index; + int Index; + + baseaddr = (u32) baseaddr_p; + + xil_printf("******************************\n\r"); + xil_printf("* User Peripheral Self Test\n\r"); + xil_printf("******************************\n\n\r"); + + /* + * Write to user logic slave module register(s) and read back + */ + xil_printf("User logic slave module test...\n\r"); + + for (write_loop_index = 0 ; write_loop_index < 4; write_loop_index++) + IP_ENCODER_mWriteReg (baseaddr, write_loop_index*4, (write_loop_index+1)*READ_WRITE_MUL_FACTOR); + for (read_loop_index = 0 ; read_loop_index < 4; read_loop_index++) + if ( IP_ENCODER_mReadReg (baseaddr, read_loop_index*4) != (read_loop_index+1)*READ_WRITE_MUL_FACTOR){ + xil_printf ("Error reading register value at address %x\n", (int)baseaddr + read_loop_index*4); + return XST_FAILURE; + } + + xil_printf(" - slave register write/read passed\n\n\r"); + + return XST_SUCCESS; +} diff --git a/hardware/pl_platform/ip_repo/ip_encoder_1.0/example_designs/bfm_design/design.tcl b/hardware/pl_platform/ip_repo/ip_encoder_1.0/example_designs/bfm_design/design.tcl new file mode 100644 index 0000000..65a930e --- /dev/null +++ b/hardware/pl_platform/ip_repo/ip_encoder_1.0/example_designs/bfm_design/design.tcl @@ -0,0 +1,88 @@ +proc create_ipi_design { offsetfile design_name } { + create_bd_design $design_name + open_bd_design $design_name + + # Create Clock and Reset Ports + set ACLK [ create_bd_port -dir I -type clk ACLK ] + set_property -dict [ list CONFIG.FREQ_HZ {100000000} CONFIG.PHASE {0.000} CONFIG.CLK_DOMAIN "${design_name}_ACLK" ] $ACLK + set ARESETN [ create_bd_port -dir I -type rst ARESETN ] + set_property -dict [ list CONFIG.POLARITY {ACTIVE_LOW} ] $ARESETN + set_property CONFIG.ASSOCIATED_RESET ARESETN $ACLK + + # Create instance: ip_encoder_0, and set properties + set ip_encoder_0 [ create_bd_cell -type ip -vlnv user.org:user:ip_encoder:1.0 ip_encoder_0] + + # Create instance: master_0, and set properties + set master_0 [ create_bd_cell -type ip -vlnv xilinx.com:ip:axi_vip master_0] + set_property -dict [ list CONFIG.PROTOCOL {AXI4LITE} CONFIG.INTERFACE_MODE {MASTER} ] $master_0 + + # Create interface connections + connect_bd_intf_net [get_bd_intf_pins master_0/M_AXI ] [get_bd_intf_pins ip_encoder_0/S00_AXI] + + # Create port connections + connect_bd_net -net aclk_net [get_bd_ports ACLK] [get_bd_pins master_0/ACLK] [get_bd_pins ip_encoder_0/S00_AXI_ACLK] + connect_bd_net -net aresetn_net [get_bd_ports ARESETN] [get_bd_pins master_0/ARESETN] [get_bd_pins ip_encoder_0/S00_AXI_ARESETN] +set_property target_simulator XSim [current_project] +set_property -name {xsim.simulate.runtime} -value {100ms} -objects [get_filesets sim_1] + + # Auto assign address + assign_bd_address + + # Copy all address to interface_address.vh file + set bd_path [file dirname [get_property NAME [get_files ${design_name}.bd]]] + upvar 1 $offsetfile offset_file + set offset_file "${bd_path}/ip_encoder_v1_0_tb_include.svh" + set fp [open $offset_file "w"] + puts $fp "`ifndef ip_encoder_v1_0_tb_include_vh_" + puts $fp "`define ip_encoder_v1_0_tb_include_vh_\n" + puts $fp "//Configuration current bd names" + puts $fp "`define BD_NAME ${design_name}" + puts $fp "`define BD_INST_NAME ${design_name}_i" + puts $fp "`define BD_WRAPPER ${design_name}_wrapper\n" + puts $fp "//Configuration address parameters" + + puts $fp "`endif" + close $fp +} + +set ip_path [file dirname [file normalize [get_property XML_FILE_NAME [ipx::get_cores user.org:user:ip_encoder:1.0]]]] +set test_bench_file ${ip_path}/example_designs/bfm_design/ip_encoder_v1_0_tb.sv +set interface_address_vh_file "" + +# Set IP Repository and Update IP Catalogue +set repo_paths [get_property ip_repo_paths [current_fileset]] +if { [lsearch -exact -nocase $repo_paths $ip_path ] == -1 } { + set_property ip_repo_paths "$ip_path [get_property ip_repo_paths [current_fileset]]" [current_fileset] + update_ip_catalog +} + +set design_name "" +set all_bd {} +set all_bd_files [get_files *.bd -quiet] +foreach file $all_bd_files { +set file_name [string range $file [expr {[string last "/" $file] + 1}] end] +set bd_name [string range $file_name 0 [expr {[string last "." $file_name] -1}]] +lappend all_bd $bd_name +} + +for { set i 1 } { 1 } { incr i } { + set design_name "ip_encoder_v1_0_bfm_${i}" + if { [lsearch -exact -nocase $all_bd $design_name ] == -1 } { + break + } +} + +create_ipi_design interface_address_vh_file ${design_name} +validate_bd_design + +set wrapper_file [make_wrapper -files [get_files ${design_name}.bd] -top -force] +import_files -force -norecurse $wrapper_file + +set_property SOURCE_SET sources_1 [get_filesets sim_1] +import_files -fileset sim_1 -norecurse -force $test_bench_file +remove_files -quiet -fileset sim_1 ip_encoder_v1_0_tb_include.vh +import_files -fileset sim_1 -norecurse -force $interface_address_vh_file +set_property top ip_encoder_v1_0_tb [get_filesets sim_1] +set_property top_lib {} [get_filesets sim_1] +set_property top_file {} [get_filesets sim_1] +launch_simulation -simset sim_1 -mode behavioral diff --git a/hardware/pl_platform/ip_repo/ip_encoder_1.0/example_designs/bfm_design/ip_encoder_v1_0_tb.sv b/hardware/pl_platform/ip_repo/ip_encoder_1.0/example_designs/bfm_design/ip_encoder_v1_0_tb.sv new file mode 100644 index 0000000..e5939a0 --- /dev/null +++ b/hardware/pl_platform/ip_repo/ip_encoder_1.0/example_designs/bfm_design/ip_encoder_v1_0_tb.sv @@ -0,0 +1,197 @@ + +`timescale 1ns / 1ps +`include "ip_encoder_v1_0_tb_include.svh" + +import axi_vip_pkg::*; +import ip_encoder_v1_0_bfm_1_master_0_0_pkg::*; + +module ip_encoder_v1_0_tb(); + + +xil_axi_uint error_cnt = 0; +xil_axi_uint comparison_cnt = 0; +axi_transaction wr_transaction; +axi_transaction rd_transaction; +axi_monitor_transaction mst_monitor_transaction; +axi_monitor_transaction master_moniter_transaction_queue[$]; +xil_axi_uint master_moniter_transaction_queue_size =0; +axi_monitor_transaction mst_scb_transaction; +axi_monitor_transaction passthrough_monitor_transaction; +axi_monitor_transaction passthrough_master_moniter_transaction_queue[$]; +xil_axi_uint passthrough_master_moniter_transaction_queue_size =0; +axi_monitor_transaction passthrough_mst_scb_transaction; +axi_monitor_transaction passthrough_slave_moniter_transaction_queue[$]; +xil_axi_uint passthrough_slave_moniter_transaction_queue_size =0; +axi_monitor_transaction passthrough_slv_scb_transaction; +axi_monitor_transaction slv_monitor_transaction; +axi_monitor_transaction slave_moniter_transaction_queue[$]; +xil_axi_uint slave_moniter_transaction_queue_size =0; +axi_monitor_transaction slv_scb_transaction; +xil_axi_uint mst_agent_verbosity = 0; +xil_axi_uint slv_agent_verbosity = 0; +xil_axi_uint passthrough_agent_verbosity = 0; +bit clock; +bit reset; +integer result_slave; +bit [31:0] S00_AXI_test_data[3:0]; + localparam LC_AXI_BURST_LENGTH = 8; + localparam LC_AXI_DATA_WIDTH = 32; +task automatic COMPARE_DATA; + input [(LC_AXI_BURST_LENGTH * LC_AXI_DATA_WIDTH)-1:0]expected; + input [(LC_AXI_BURST_LENGTH * LC_AXI_DATA_WIDTH)-1:0]actual; + begin + if (expected === 'hx || actual === 'hx) begin + $display("TESTBENCH ERROR! COMPARE_DATA cannot be performed with an expected or actual vector that is all 'x'!"); + result_slave = 0; $stop; + end + if (actual != expected) begin + $display("TESTBENCH ERROR! Data expected is not equal to actual.", " expected = 0x%h",expected, " actual = 0x%h",actual); + result_slave = 0; + $stop; + end + else + begin + $display("TESTBENCH Passed! Data expected is equal to actual.", + " expected = 0x%h",expected, " actual = 0x%h",actual); + end + end +endtask +integer i; +integer j; +xil_axi_uint trans_cnt_before_switch = 48; +xil_axi_uint passthrough_cmd_switch_cnt = 0; +event passthrough_mastermode_start_event; +event passthrough_mastermode_end_event; +event passthrough_slavemode_end_event; +xil_axi_uint mtestID; +xil_axi_ulong mtestADDR; +xil_axi_len_t mtestBurstLength; +xil_axi_size_t mtestDataSize; +xil_axi_burst_t mtestBurstType; +xil_axi_lock_t mtestLOCK; +xil_axi_cache_t mtestCacheType = 0; +xil_axi_prot_t mtestProtectionType = 3'b000; +xil_axi_region_t mtestRegion = 4'b000; +xil_axi_qos_t mtestQOS = 4'b000; +xil_axi_data_beat dbeat; +xil_axi_data_beat [255:0] mtestWUSER; +xil_axi_data_beat mtestAWUSER = 'h0; +xil_axi_data_beat mtestARUSER = 0; +xil_axi_data_beat [255:0] mtestRUSER; +xil_axi_uint mtestBUSER = 0; +xil_axi_resp_t mtestBresp; +xil_axi_resp_t[255:0] mtestRresp; +bit [63:0] mtestWDataL; +bit [63:0] mtestRDataL; +axi_transaction pss_wr_transaction; +axi_transaction pss_rd_transaction; +axi_transaction reactive_transaction; +axi_transaction rd_payload_transaction; +axi_transaction wr_rand; +axi_transaction rd_rand; +axi_transaction wr_reactive; +axi_transaction rd_reactive; +axi_transaction wr_reactive2; +axi_transaction rd_reactive2; +axi_ready_gen bready_gen; +axi_ready_gen rready_gen; +axi_ready_gen awready_gen; +axi_ready_gen wready_gen; +axi_ready_gen arready_gen; +axi_ready_gen bready_gen2; +axi_ready_gen rready_gen2; +axi_ready_gen awready_gen2; +axi_ready_gen wready_gen2; +axi_ready_gen arready_gen2; +xil_axi_payload_byte data_mem[xil_axi_ulong]; +ip_encoder_v1_0_bfm_1_master_0_0_mst_t mst_agent_0; + + `BD_WRAPPER DUT( + .ARESETN(reset), + .ACLK(clock) + ); + +initial begin + mst_agent_0 = new("master vip agent",DUT.`BD_INST_NAME.master_0.inst.IF);//ms + mst_agent_0.vif_proxy.set_dummy_drive_type(XIL_AXI_VIF_DRIVE_NONE); + mst_agent_0.set_agent_tag("Master VIP"); + mst_agent_0.set_verbosity(mst_agent_verbosity); + mst_agent_0.start_master(); + $timeformat (-12, 1, " ps", 1); + end + initial begin + reset <= 1'b0; + #200ns; + reset <= 1'b1; + repeat (5) @(negedge clock); + end + always #5 clock <= ~clock; + initial begin + S_AXI_TEST ( ); + + #1ns; + $finish; + end +task automatic S_AXI_TEST; +begin +#1; + $display("Sequential write transfers example similar to AXI BFM WRITE_BURST method starts"); + mtestID = 0; + mtestADDR = 64'h00000000; + mtestBurstLength = 0; + mtestDataSize = xil_axi_size_t'(xil_clog2(32/8)); + mtestBurstType = XIL_AXI_BURST_TYPE_INCR; + mtestLOCK = XIL_AXI_ALOCK_NOLOCK; + mtestCacheType = 0; + mtestProtectionType = 0; + mtestRegion = 0; + mtestQOS = 0; + result_slave = 1; + mtestWDataL[31:0] = 32'h00000001; + for(int i = 0; i < 4;i++) begin + S00_AXI_test_data[i] <= mtestWDataL[31:0]; + mst_agent_0.AXI4LITE_WRITE_BURST( + mtestADDR, + mtestProtectionType, + mtestWDataL, + mtestBresp + ); + mtestWDataL[31:0] = mtestWDataL[31:0] + 1; + mtestADDR = mtestADDR + 64'h4; + end + $display("Sequential write transfers example similar to AXI BFM WRITE_BURST method completes"); + $display("Sequential read transfers example similar to AXI BFM READ_BURST method starts"); + mtestID = 0; + mtestADDR = 64'h00000000; + mtestBurstLength = 0; + mtestDataSize = xil_axi_size_t'(xil_clog2(32/8)); + mtestBurstType = XIL_AXI_BURST_TYPE_INCR; + mtestLOCK = XIL_AXI_ALOCK_NOLOCK; + mtestCacheType = 0; + mtestProtectionType = 0; + mtestRegion = 0; + mtestQOS = 0; + for(int i = 0; i < 4;i++) begin + mst_agent_0.AXI4LITE_READ_BURST( + mtestADDR, + mtestProtectionType, + mtestRDataL, + mtestRresp + ); + mtestADDR = mtestADDR + 64'h4; + COMPARE_DATA(S00_AXI_test_data[i],mtestRDataL); + end + $display("Sequential read transfers example similar to AXI BFM READ_BURST method completes"); + $display("Sequential read transfers example similar to AXI VIP READ_BURST method completes"); + $display("---------------------------------------------------------"); + $display("EXAMPLE TEST S00_AXI: PTGEN_TEST_FINISHED!"); + if ( result_slave ) begin + $display("PTGEN_TEST: PASSED!"); + end else begin + $display("PTGEN_TEST: FAILED!"); + end + $display("---------------------------------------------------------"); + end +endtask + +endmodule diff --git a/hardware/pl_platform/ip_repo/ip_encoder_1.0/example_designs/debug_hw_design/design.tcl b/hardware/pl_platform/ip_repo/ip_encoder_1.0/example_designs/debug_hw_design/design.tcl new file mode 100644 index 0000000..370404f --- /dev/null +++ b/hardware/pl_platform/ip_repo/ip_encoder_1.0/example_designs/debug_hw_design/design.tcl @@ -0,0 +1,118 @@ + +proc create_ipi_design { offsetfile design_name } { + + create_bd_design $design_name + open_bd_design $design_name + + # Create and configure Clock/Reset + create_bd_cell -type ip -vlnv xilinx.com:ip:clk_wiz sys_clk_0 + create_bd_cell -type ip -vlnv xilinx.com:ip:proc_sys_reset sys_reset_0 + + #Constraints will be provided manually while pin planning. + create_bd_port -dir I -type rst reset_rtl + set_property CONFIG.POLARITY [get_property CONFIG.POLARITY [get_bd_pins sys_clk_0/reset]] [get_bd_ports reset_rtl] + connect_bd_net [get_bd_pins sys_reset_0/ext_reset_in] [get_bd_ports reset_rtl] + connect_bd_net [get_bd_ports reset_rtl] [get_bd_pins sys_clk_0/reset] + set external_reset_port reset_rtl + create_bd_port -dir I -type clk clock_rtl + connect_bd_net [get_bd_pins sys_clk_0/clk_in1] [get_bd_ports clock_rtl] + set external_clock_port clock_rtl + + #Avoid IPI DRC, make clock port synchronous to reset + if { $external_clock_port ne "" && $external_reset_port ne "" } { + set_property CONFIG.ASSOCIATED_RESET $external_reset_port [get_bd_ports $external_clock_port] + } + + # Connect other sys_reset pins + connect_bd_net [get_bd_pins sys_reset_0/slowest_sync_clk] [get_bd_pins sys_clk_0/clk_out1] + connect_bd_net [get_bd_pins sys_clk_0/locked] [get_bd_pins sys_reset_0/dcm_locked] + + # Create instance: ip_encoder_0, and set properties + set ip_encoder_0 [ create_bd_cell -type ip -vlnv user.org:user:ip_encoder:1.0 ip_encoder_0 ] + + # Create instance: jtag_axi_0, and set properties + set jtag_axi_0 [ create_bd_cell -type ip -vlnv xilinx.com:ip:jtag_axi jtag_axi_0 ] + set_property -dict [list CONFIG.PROTOCOL {0}] [get_bd_cells jtag_axi_0] + connect_bd_net [get_bd_pins jtag_axi_0/aclk] [get_bd_pins sys_clk_0/clk_out1] + connect_bd_net [get_bd_pins jtag_axi_0/aresetn] [get_bd_pins sys_reset_0/peripheral_aresetn] + + # Create instance: axi_peri_interconnect, and set properties + set axi_peri_interconnect [ create_bd_cell -type ip -vlnv xilinx.com:ip:axi_interconnect axi_peri_interconnect ] + connect_bd_net [get_bd_pins axi_peri_interconnect/ACLK] [get_bd_pins sys_clk_0/clk_out1] + connect_bd_net [get_bd_pins axi_peri_interconnect/ARESETN] [get_bd_pins sys_reset_0/interconnect_aresetn] + set_property -dict [ list CONFIG.NUM_SI {1} ] $axi_peri_interconnect + connect_bd_net [get_bd_pins axi_peri_interconnect/S00_ACLK] [get_bd_pins sys_clk_0/clk_out1] + connect_bd_net [get_bd_pins axi_peri_interconnect/S00_ARESETN] [get_bd_pins sys_reset_0/peripheral_aresetn] + connect_bd_intf_net [get_bd_intf_pins jtag_axi_0/M_AXI] [get_bd_intf_pins axi_peri_interconnect/S00_AXI] + + set_property -dict [ list CONFIG.NUM_MI {1} ] $axi_peri_interconnect + connect_bd_net [get_bd_pins axi_peri_interconnect/M00_ACLK] [get_bd_pins sys_clk_0/clk_out1] + connect_bd_net [get_bd_pins axi_peri_interconnect/M00_ARESETN] [get_bd_pins sys_reset_0/peripheral_aresetn] + + # Connect all clock & reset of ip_encoder_0 slave interfaces.. + connect_bd_intf_net [get_bd_intf_pins axi_peri_interconnect/M00_AXI] [get_bd_intf_pins ip_encoder_0/S00_AXI] + connect_bd_net [get_bd_pins ip_encoder_0/s00_axi_aclk] [get_bd_pins sys_clk_0/clk_out1] + connect_bd_net [get_bd_pins ip_encoder_0/s00_axi_aresetn] [get_bd_pins sys_reset_0/peripheral_aresetn] + + + # Auto assign address + assign_bd_address + + # Copy all address to ip_encoder_v1_0_include.tcl file + set bd_path [get_property DIRECTORY [current_project]]/[current_project].srcs/[current_fileset]/bd + upvar 1 $offsetfile offset_file + set offset_file "${bd_path}/ip_encoder_v1_0_include.tcl" + set fp [open $offset_file "w"] + puts $fp "# Configuration address parameters" + + set offset [get_property OFFSET [get_bd_addr_segs /jtag_axi_0/Data/SEG_ip_encoder_0_S00_AXI_* ]] + puts $fp "set s00_axi_addr ${offset}" + + close $fp +} + +# Set IP Repository and Update IP Catalogue +set ip_path [file dirname [file normalize [get_property XML_FILE_NAME [ipx::get_cores user.org:user:ip_encoder:1.0]]]] +set hw_test_file ${ip_path}/example_designs/debug_hw_design/ip_encoder_v1_0_hw_test.tcl + +set repo_paths [get_property ip_repo_paths [current_fileset]] +if { [lsearch -exact -nocase $repo_paths $ip_path ] == -1 } { + set_property ip_repo_paths "$ip_path [get_property ip_repo_paths [current_fileset]]" [current_fileset] + update_ip_catalog +} + +set design_name "" +set all_bd {} +set all_bd_files [get_files *.bd -quiet] +foreach file $all_bd_files { +set file_name [string range $file [expr {[string last "/" $file] + 1}] end] +set bd_name [string range $file_name 0 [expr {[string last "." $file_name] -1}]] +lappend all_bd $bd_name +} + +for { set i 1 } { 1 } { incr i } { + set design_name "ip_encoder_v1_0_hw_${i}" + if { [lsearch -exact -nocase $all_bd $design_name ] == -1 } { + break + } +} + +set intf_address_include_file "" +create_ipi_design intf_address_include_file ${design_name} +save_bd_design +validate_bd_design + +set wrapper_file [make_wrapper -files [get_files ${design_name}.bd] -top -force] +import_files -force -norecurse $wrapper_file + +puts "-------------------------------------------------------------------------------------------------" +puts "INFO NEXT STEPS : Until this stage, debug hardware design has been created, " +puts " please perform following steps to test design in targeted board." +puts "1. Generate bitstream" +puts "2. Setup your targeted board, open hardware manager and open new(or existing) hardware target" +puts "3. Download generated bitstream" +puts "4. Run generated hardware test using below command, this invokes basic read/write operation" +puts " to every interface present in the peripheral : xilinx.com:user:myip:1.0" +puts " : source -notrace ${hw_test_file}" +puts "-------------------------------------------------------------------------------------------------" + diff --git a/hardware/pl_platform/ip_repo/ip_encoder_1.0/example_designs/debug_hw_design/ip_encoder_v1_0_hw_test.tcl b/hardware/pl_platform/ip_repo/ip_encoder_1.0/example_designs/debug_hw_design/ip_encoder_v1_0_hw_test.tcl new file mode 100644 index 0000000..a08bb26 --- /dev/null +++ b/hardware/pl_platform/ip_repo/ip_encoder_1.0/example_designs/debug_hw_design/ip_encoder_v1_0_hw_test.tcl @@ -0,0 +1,45 @@ +# Runtime Tcl commands to interact with - ip_encoder_v1_0 + +# Sourcing design address info tcl +set bd_path [get_property DIRECTORY [current_project]]/[current_project].srcs/[current_fileset]/bd +source ${bd_path}/ip_encoder_v1_0_include.tcl + +# jtag axi master interface hardware name, change as per your design. +set jtag_axi_master hw_axi_1 +set ec 0 + +# hw test script +# Delete all previous axis transactions +if { [llength [get_hw_axi_txns -quiet]] } { + delete_hw_axi_txn [get_hw_axi_txns -quiet] +} + + +# Test all lite slaves. +set wdata_1 abcd1234 + +# Test: S00_AXI +# Create a write transaction at s00_axi_addr address +create_hw_axi_txn w_s00_axi_addr [get_hw_axis $jtag_axi_master] -type write -address $s00_axi_addr -data $wdata_1 +# Create a read transaction at s00_axi_addr address +create_hw_axi_txn r_s00_axi_addr [get_hw_axis $jtag_axi_master] -type read -address $s00_axi_addr +# Initiate transactions +run_hw_axi r_s00_axi_addr +run_hw_axi w_s00_axi_addr +run_hw_axi r_s00_axi_addr +set rdata_tmp [get_property DATA [get_hw_axi_txn r_s00_axi_addr]] +# Compare read data +if { $rdata_tmp == $wdata_1 } { + puts "Data comparison test pass for - S00_AXI" +} else { + puts "Data comparison test fail for - S00_AXI, expected-$wdata_1 actual-$rdata_tmp" + inc ec +} + +# Check error flag +if { $ec == 0 } { + puts "PTGEN_TEST: PASSED!" +} else { + puts "PTGEN_TEST: FAILED!" +} + diff --git a/hardware/pl_platform/ip_repo/ip_encoder_1.0/hdl/ip_encoder_v1_0.v b/hardware/pl_platform/ip_repo/ip_encoder_1.0/hdl/ip_encoder_v1_0.v new file mode 100644 index 0000000..92d055a --- /dev/null +++ b/hardware/pl_platform/ip_repo/ip_encoder_1.0/hdl/ip_encoder_v1_0.v @@ -0,0 +1,102 @@ + +`timescale 1 ns / 1 ps + + module ip_encoder_v1_0 # + ( + // Users to add parameters here + + // User parameters ends + // Do not modify the parameters beyond this line + + + // Parameters of Axi Slave Bus Interface S00_AXI + parameter integer C_S00_AXI_DATA_WIDTH = 32, + parameter integer C_S00_AXI_ADDR_WIDTH = 5 + ) + ( + // Users to add ports here + input in_signal, + input exrst_n, + output out_signal_valve_posedge, + output out_signal_valve, + output out_signal_camera_a_posedge, + output out_signal_camera_b_posedge, + output out_signal_camera_c_posedge, + output out_signal_camera_d_posedge, + output out_signal_camera_a, + output out_signal_camera_b, + output out_signal_camera_c, + output out_signal_camera_d, + + // User ports ends + // Do not modify the ports beyond this line + + + // Ports of Axi Slave Bus Interface S00_AXI + input wire s00_axi_aclk, + input wire s00_axi_aresetn, + input wire [C_S00_AXI_ADDR_WIDTH-1 : 0] s00_axi_awaddr, + input wire [2 : 0] s00_axi_awprot, + input wire s00_axi_awvalid, + output wire s00_axi_awready, + input wire [C_S00_AXI_DATA_WIDTH-1 : 0] s00_axi_wdata, + input wire [(C_S00_AXI_DATA_WIDTH/8)-1 : 0] s00_axi_wstrb, + input wire s00_axi_wvalid, + output wire s00_axi_wready, + output wire [1 : 0] s00_axi_bresp, + output wire s00_axi_bvalid, + input wire s00_axi_bready, + input wire [C_S00_AXI_ADDR_WIDTH-1 : 0] s00_axi_araddr, + input wire [2 : 0] s00_axi_arprot, + input wire s00_axi_arvalid, + output wire s00_axi_arready, + output wire [C_S00_AXI_DATA_WIDTH-1 : 0] s00_axi_rdata, + output wire [1 : 0] s00_axi_rresp, + output wire s00_axi_rvalid, + input wire s00_axi_rready + ); +// Instantiation of Axi Bus Interface S00_AXI + ip_encoder_v1_0_S00_AXI # ( + .C_S_AXI_DATA_WIDTH(C_S00_AXI_DATA_WIDTH), + .C_S_AXI_ADDR_WIDTH(C_S00_AXI_ADDR_WIDTH) + ) ip_encoder_v1_0_S00_AXI_inst ( + .in_signal(in_signal), + .exrst_n (exrst_n), + .out_signal_valve_posedge(out_signal_valve_posedge), + .out_signal_valve(out_signal_valve), + .out_signal_camera_a_posedge(out_signal_camera_a_posedge), + .out_signal_camera_b_posedge(out_signal_camera_b_posedge), + .out_signal_camera_c_posedge(out_signal_camera_c_posedge), + .out_signal_camera_d_posedge(out_signal_camera_d_posedge), + .out_signal_camera_a(out_signal_camera_a), + .out_signal_camera_b(out_signal_camera_b), + .out_signal_camera_c(out_signal_camera_c), + .out_signal_camera_d(out_signal_camera_d), + .S_AXI_ACLK(s00_axi_aclk), + .S_AXI_ARESETN(s00_axi_aresetn), + .S_AXI_AWADDR(s00_axi_awaddr), + .S_AXI_AWPROT(s00_axi_awprot), + .S_AXI_AWVALID(s00_axi_awvalid), + .S_AXI_AWREADY(s00_axi_awready), + .S_AXI_WDATA(s00_axi_wdata), + .S_AXI_WSTRB(s00_axi_wstrb), + .S_AXI_WVALID(s00_axi_wvalid), + .S_AXI_WREADY(s00_axi_wready), + .S_AXI_BRESP(s00_axi_bresp), + .S_AXI_BVALID(s00_axi_bvalid), + .S_AXI_BREADY(s00_axi_bready), + .S_AXI_ARADDR(s00_axi_araddr), + .S_AXI_ARPROT(s00_axi_arprot), + .S_AXI_ARVALID(s00_axi_arvalid), + .S_AXI_ARREADY(s00_axi_arready), + .S_AXI_RDATA(s00_axi_rdata), + .S_AXI_RRESP(s00_axi_rresp), + .S_AXI_RVALID(s00_axi_rvalid), + .S_AXI_RREADY(s00_axi_rready) + ); + + // Add user logic here + + // User logic ends + + endmodule diff --git a/hardware/pl_platform/ip_repo/ip_encoder_1.0/hdl/ip_encoder_v1_0_S00_AXI.v b/hardware/pl_platform/ip_repo/ip_encoder_1.0/hdl/ip_encoder_v1_0_S00_AXI.v new file mode 100644 index 0000000..0179a57 --- /dev/null +++ b/hardware/pl_platform/ip_repo/ip_encoder_1.0/hdl/ip_encoder_v1_0_S00_AXI.v @@ -0,0 +1,482 @@ + +`timescale 1 ns / 1 ps + + module ip_encoder_v1_0_S00_AXI # + ( + // Users to add parameters here + + // User parameters ends + // Do not modify the parameters beyond this line + + // Width of S_AXI data bus + parameter integer C_S_AXI_DATA_WIDTH = 32, + // Width of S_AXI address bus + parameter integer C_S_AXI_ADDR_WIDTH = 5 + ) + ( + // Users to add ports here + input in_signal, + input exrst_n, + output out_signal_valve_posedge, + output out_signal_valve, + output out_signal_camera_a_posedge, + output out_signal_camera_b_posedge, + output out_signal_camera_c_posedge, + output out_signal_camera_d_posedge, + output out_signal_camera_a, + output out_signal_camera_b, + output out_signal_camera_c, + output out_signal_camera_d, + + // User ports ends + // Do not modify the ports beyond this line + + // Global Clock Signal + input wire S_AXI_ACLK, + // Global Reset Signal. This Signal is Active LOW + input wire S_AXI_ARESETN, + // Write address (issued by master, acceped by Slave) + input wire [C_S_AXI_ADDR_WIDTH-1 : 0] S_AXI_AWADDR, + // Write channel Protection type. This signal indicates the + // privilege and security level of the transaction, and whether + // the transaction is a data access or an instruction access. + input wire [2 : 0] S_AXI_AWPROT, + // Write address valid. This signal indicates that the master signaling + // valid write address and control information. + input wire S_AXI_AWVALID, + // Write address ready. This signal indicates that the slave is ready + // to accept an address and associated control signals. + output wire S_AXI_AWREADY, + // Write data (issued by master, acceped by Slave) + input wire [C_S_AXI_DATA_WIDTH-1 : 0] S_AXI_WDATA, + // Write strobes. This signal indicates which byte lanes hold + // valid data. There is one write strobe bit for each eight + // bits of the write data bus. + input wire [(C_S_AXI_DATA_WIDTH/8)-1 : 0] S_AXI_WSTRB, + // Write valid. This signal indicates that valid write + // data and strobes are available. + input wire S_AXI_WVALID, + // Write ready. This signal indicates that the slave + // can accept the write data. + output wire S_AXI_WREADY, + // Write response. This signal indicates the status + // of the write transaction. + output wire [1 : 0] S_AXI_BRESP, + // Write response valid. This signal indicates that the channel + // is signaling a valid write response. + output wire S_AXI_BVALID, + // Response ready. This signal indicates that the master + // can accept a write response. + input wire S_AXI_BREADY, + // Read address (issued by master, acceped by Slave) + input wire [C_S_AXI_ADDR_WIDTH-1 : 0] S_AXI_ARADDR, + // Protection type. This signal indicates the privilege + // and security level of the transaction, and whether the + // transaction is a data access or an instruction access. + input wire [2 : 0] S_AXI_ARPROT, + // Read address valid. This signal indicates that the channel + // is signaling valid read address and control information. + input wire S_AXI_ARVALID, + // Read address ready. This signal indicates that the slave is + // ready to accept an address and associated control signals. + output wire S_AXI_ARREADY, + // Read data (issued by slave) + output wire [C_S_AXI_DATA_WIDTH-1 : 0] S_AXI_RDATA, + // Read response. This signal indicates the status of the + // read transfer. + output wire [1 : 0] S_AXI_RRESP, + // Read valid. This signal indicates that the channel is + // signaling the required read data. + output wire S_AXI_RVALID, + // Read ready. This signal indicates that the master can + // accept the read data and response information. + input wire S_AXI_RREADY + ); + + // AXI4LITE signals + reg [C_S_AXI_ADDR_WIDTH-1 : 0] axi_awaddr; + reg axi_awready; + reg axi_wready; + reg [1 : 0] axi_bresp; + reg axi_bvalid; + reg [C_S_AXI_ADDR_WIDTH-1 : 0] axi_araddr; + reg axi_arready; + reg [C_S_AXI_DATA_WIDTH-1 : 0] axi_rdata; + reg [1 : 0] axi_rresp; + reg axi_rvalid; + + // Example-specific design signals + // local parameter for addressing 32 bit / 64 bit C_S_AXI_DATA_WIDTH + // ADDR_LSB is used for addressing 32/64 bit registers/memories + // ADDR_LSB = 2 for 32 bits (n downto 2) + // ADDR_LSB = 3 for 64 bits (n downto 3) + localparam integer ADDR_LSB = (C_S_AXI_DATA_WIDTH/32) + 1; + localparam integer OPT_MEM_ADDR_BITS = 2; + //---------------------------------------------- + //-- Signals for user logic register space example + //------------------------------------------------ + //-- Number of Slave Registers 8 + reg [C_S_AXI_DATA_WIDTH-1:0] slv_reg0; + reg [C_S_AXI_DATA_WIDTH-1:0] slv_reg1; + reg [C_S_AXI_DATA_WIDTH-1:0] slv_reg2; + reg [C_S_AXI_DATA_WIDTH-1:0] slv_reg3; + reg [C_S_AXI_DATA_WIDTH-1:0] slv_reg4; + reg [C_S_AXI_DATA_WIDTH-1:0] slv_reg5; + reg [C_S_AXI_DATA_WIDTH-1:0] slv_reg6; + reg [C_S_AXI_DATA_WIDTH-1:0] slv_reg7; + wire slv_reg_rden; + wire slv_reg_wren; + reg [C_S_AXI_DATA_WIDTH-1:0] reg_data_out; + integer byte_index; + reg aw_en; + + // I/O Connections assignments + + assign S_AXI_AWREADY = axi_awready; + assign S_AXI_WREADY = axi_wready; + assign S_AXI_BRESP = axi_bresp; + assign S_AXI_BVALID = axi_bvalid; + assign S_AXI_ARREADY = axi_arready; + assign S_AXI_RDATA = axi_rdata; + assign S_AXI_RRESP = axi_rresp; + assign S_AXI_RVALID = axi_rvalid; + // Implement axi_awready generation + // axi_awready is asserted for one S_AXI_ACLK clock cycle when both + // S_AXI_AWVALID and S_AXI_WVALID are asserted. axi_awready is + // de-asserted when reset is low. + + always @( posedge S_AXI_ACLK ) + begin + if ( S_AXI_ARESETN == 1'b0 ) + begin + axi_awready <= 1'b0; + aw_en <= 1'b1; + end + else + begin + if (~axi_awready && S_AXI_AWVALID && S_AXI_WVALID && aw_en) + begin + // slave is ready to accept write address when + // there is a valid write address and write data + // on the write address and data bus. This design + // expects no outstanding transactions. + axi_awready <= 1'b1; + aw_en <= 1'b0; + end + else if (S_AXI_BREADY && axi_bvalid) + begin + aw_en <= 1'b1; + axi_awready <= 1'b0; + end + else + begin + axi_awready <= 1'b0; + end + end + end + + // Implement axi_awaddr latching + // This process is used to latch the address when both + // S_AXI_AWVALID and S_AXI_WVALID are valid. + + always @( posedge S_AXI_ACLK ) + begin + if ( S_AXI_ARESETN == 1'b0 ) + begin + axi_awaddr <= 0; + end + else + begin + if (~axi_awready && S_AXI_AWVALID && S_AXI_WVALID && aw_en) + begin + // Write Address latching + axi_awaddr <= S_AXI_AWADDR; + end + end + end + + // Implement axi_wready generation + // axi_wready is asserted for one S_AXI_ACLK clock cycle when both + // S_AXI_AWVALID and S_AXI_WVALID are asserted. axi_wready is + // de-asserted when reset is low. + + always @( posedge S_AXI_ACLK ) + begin + if ( S_AXI_ARESETN == 1'b0 ) + begin + axi_wready <= 1'b0; + end + else + begin + if (~axi_wready && S_AXI_WVALID && S_AXI_AWVALID && aw_en ) + begin + // slave is ready to accept write data when + // there is a valid write address and write data + // on the write address and data bus. This design + // expects no outstanding transactions. + axi_wready <= 1'b1; + end + else + begin + axi_wready <= 1'b0; + end + end + end + + // Implement memory mapped register select and write logic generation + // The write data is accepted and written to memory mapped registers when + // axi_awready, S_AXI_WVALID, axi_wready and S_AXI_WVALID are asserted. Write strobes are used to + // select byte enables of slave registers while writing. + // These registers are cleared when reset (active low) is applied. + // Slave register write enable is asserted when valid address and data are available + // and the slave is ready to accept the write address and write data. + assign slv_reg_wren = axi_wready && S_AXI_WVALID && axi_awready && S_AXI_AWVALID; + + always @( posedge S_AXI_ACLK ) + begin + if ( S_AXI_ARESETN == 1'b0 ) + begin + slv_reg0 <= 32'h9; + slv_reg1 <= 0; + slv_reg2 <= 0; + slv_reg3 <= 0; + slv_reg4 <= 0; + slv_reg5 <= 0; + slv_reg6 <= 0; + slv_reg7 <= 0; + end + else begin + if (slv_reg_wren) + begin + case ( axi_awaddr[ADDR_LSB+OPT_MEM_ADDR_BITS:ADDR_LSB] ) + 3'h0: + for ( byte_index = 0; byte_index <= (C_S_AXI_DATA_WIDTH/8)-1; byte_index = byte_index+1 ) + if ( S_AXI_WSTRB[byte_index] == 1 ) begin + // Respective byte enables are asserted as per write strobes + // Slave register 0 + slv_reg0[(byte_index*8) +: 8] <= S_AXI_WDATA[(byte_index*8) +: 8]; + end + 3'h1: + for ( byte_index = 0; byte_index <= (C_S_AXI_DATA_WIDTH/8)-1; byte_index = byte_index+1 ) + if ( S_AXI_WSTRB[byte_index] == 1 ) begin + // Respective byte enables are asserted as per write strobes + // Slave register 1 + slv_reg1[(byte_index*8) +: 8] <= S_AXI_WDATA[(byte_index*8) +: 8]; + end + 3'h2: + for ( byte_index = 0; byte_index <= (C_S_AXI_DATA_WIDTH/8)-1; byte_index = byte_index+1 ) + if ( S_AXI_WSTRB[byte_index] == 1 ) begin + // Respective byte enables are asserted as per write strobes + // Slave register 2 + slv_reg2[(byte_index*8) +: 8] <= S_AXI_WDATA[(byte_index*8) +: 8]; + end + 3'h3: + for ( byte_index = 0; byte_index <= (C_S_AXI_DATA_WIDTH/8)-1; byte_index = byte_index+1 ) + if ( S_AXI_WSTRB[byte_index] == 1 ) begin + // Respective byte enables are asserted as per write strobes + // Slave register 3 + slv_reg3[(byte_index*8) +: 8] <= S_AXI_WDATA[(byte_index*8) +: 8]; + end + 3'h4: + for ( byte_index = 0; byte_index <= (C_S_AXI_DATA_WIDTH/8)-1; byte_index = byte_index+1 ) + if ( S_AXI_WSTRB[byte_index] == 1 ) begin + // Respective byte enables are asserted as per write strobes + // Slave register 3 + slv_reg4[(byte_index*8) +: 8] <= S_AXI_WDATA[(byte_index*8) +: 8]; + end + 3'h5: + for ( byte_index = 0; byte_index <= (C_S_AXI_DATA_WIDTH/8)-1; byte_index = byte_index+1 ) + if ( S_AXI_WSTRB[byte_index] == 1 ) begin + // Respective byte enables are asserted as per write strobes + // Slave register 3 + slv_reg5[(byte_index*8) +: 8] <= S_AXI_WDATA[(byte_index*8) +: 8]; + end + 3'h6: + for ( byte_index = 0; byte_index <= (C_S_AXI_DATA_WIDTH/8)-1; byte_index = byte_index+1 ) + if ( S_AXI_WSTRB[byte_index] == 1 ) begin + // Respective byte enables are asserted as per write strobes + // Slave register 3 + slv_reg6[(byte_index*8) +: 8] <= S_AXI_WDATA[(byte_index*8) +: 8]; + end + 3'h7: + for ( byte_index = 0; byte_index <= (C_S_AXI_DATA_WIDTH/8)-1; byte_index = byte_index+1 ) + if ( S_AXI_WSTRB[byte_index] == 1 ) begin + // Respective byte enables are asserted as per write strobes + // Slave register 3 + slv_reg7[(byte_index*8) +: 8] <= S_AXI_WDATA[(byte_index*8) +: 8]; + end + default : begin + slv_reg0 <= slv_reg0; + slv_reg1 <= slv_reg1; + slv_reg2 <= slv_reg2; + slv_reg3 <= slv_reg3; + slv_reg4 <= slv_reg4; + slv_reg5 <= slv_reg5; + slv_reg6 <= slv_reg6; + slv_reg7 <= slv_reg7; + end + endcase + end + end + end + + // Implement write response logic generation + // The write response and response valid signals are asserted by the slave + // when axi_wready, S_AXI_WVALID, axi_wready and S_AXI_WVALID are asserted. + // This marks the acceptance of address and indicates the status of + // write transaction. + + always @( posedge S_AXI_ACLK ) + begin + if ( S_AXI_ARESETN == 1'b0 ) + begin + axi_bvalid <= 0; + axi_bresp <= 2'b0; + end + else + begin + if (axi_awready && S_AXI_AWVALID && ~axi_bvalid && axi_wready && S_AXI_WVALID) + begin + // indicates a valid write response is available + axi_bvalid <= 1'b1; + axi_bresp <= 2'b0; // 'OKAY' response + end // work error responses in future + else + begin + if (S_AXI_BREADY && axi_bvalid) + //check if bready is asserted while bvalid is high) + //(there is a possibility that bready is always asserted high) + begin + axi_bvalid <= 1'b0; + end + end + end + end + + // Implement axi_arready generation + // axi_arready is asserted for one S_AXI_ACLK clock cycle when + // S_AXI_ARVALID is asserted. axi_awready is + // de-asserted when reset (active low) is asserted. + // The read address is also latched when S_AXI_ARVALID is + // asserted. axi_araddr is reset to zero on reset assertion. + + always @( posedge S_AXI_ACLK ) + begin + if ( S_AXI_ARESETN == 1'b0 ) + begin + axi_arready <= 1'b0; + axi_araddr <= 32'b0; + end + else + begin + if (~axi_arready && S_AXI_ARVALID) + begin + // indicates that the slave has acceped the valid read address + axi_arready <= 1'b1; + // Read address latching + axi_araddr <= S_AXI_ARADDR; + end + else + begin + axi_arready <= 1'b0; + end + end + end + + // Implement axi_arvalid generation + // axi_rvalid is asserted for one S_AXI_ACLK clock cycle when both + // S_AXI_ARVALID and axi_arready are asserted. The slave registers + // data are available on the axi_rdata bus at this instance. The + // assertion of axi_rvalid marks the validity of read data on the + // bus and axi_rresp indicates the status of read transaction.axi_rvalid + // is deasserted on reset (active low). axi_rresp and axi_rdata are + // cleared to zero on reset (active low). + always @( posedge S_AXI_ACLK ) + begin + if ( S_AXI_ARESETN == 1'b0 ) + begin + axi_rvalid <= 0; + axi_rresp <= 0; + end + else + begin + if (axi_arready && S_AXI_ARVALID && ~axi_rvalid) + begin + // Valid read data is available at the read data bus + axi_rvalid <= 1'b1; + axi_rresp <= 2'b0; // 'OKAY' response + end + else if (axi_rvalid && S_AXI_RREADY) + begin + // Read data is accepted by the master + axi_rvalid <= 1'b0; + end + end + end + + // Implement memory mapped register select and read logic generation + // Slave register read enable is asserted when valid address is available + // and the slave is ready to accept the read address. + assign slv_reg_rden = axi_arready & S_AXI_ARVALID & ~axi_rvalid; + always @(*) + begin + // Address decoding for reading registers + case ( axi_araddr[ADDR_LSB+OPT_MEM_ADDR_BITS:ADDR_LSB] ) + 3'h0 : reg_data_out <= slv_reg0; + 3'h1 : reg_data_out <= slv_reg1; + 3'h2 : reg_data_out <= slv_reg2; + 3'h3 : reg_data_out <= slv_reg3; + 3'h4 : reg_data_out <= slv_reg4; + 3'h5 : reg_data_out <= slv_reg5; + 3'h6 : reg_data_out <= slv_reg6; + 3'h7 : reg_data_out <= slv_reg7; + default : reg_data_out <= 0; + endcase + end + + // Output register or memory read data + always @( posedge S_AXI_ACLK ) + begin + if ( S_AXI_ARESETN == 1'b0 ) + begin + axi_rdata <= 0; + end + else + begin + // When there is a valid read address (S_AXI_ARVALID) with + // acceptance of read address by the slave (axi_arready), + // output the read dada + if (slv_reg_rden) + begin + axi_rdata <= reg_data_out; // register read data + end + end + end + + wire in_signal_tmp = slv_reg0[1] ? slv_reg0[2] : in_signal; //0:external 1:internal + wire encoder_rst_n = slv_reg0[0] & S_AXI_ARESETN & (slv_reg0[3] | exrst_n); + // Add user logic here + encoder encoder_inst( + .sys_clk(S_AXI_ACLK), + .rst_n(encoder_rst_n), + .in_signal(in_signal_tmp), + .valve_signal_divider(slv_reg1), + .camera_signal_divider_a(slv_reg2), + .camera_signal_divider_b(slv_reg3), + .camera_signal_divider_c(slv_reg4), + .camera_signal_divider_d(slv_reg5), + + .out_signal_valve_posedge(out_signal_valve_posedge), + .out_signal_valve(out_signal_valve), + .out_signal_camera_a_posedge(out_signal_camera_a_posedge), + .out_signal_camera_b_posedge(out_signal_camera_b_posedge), + .out_signal_camera_c_posedge(out_signal_camera_c_posedge), + .out_signal_camera_d_posedge(out_signal_camera_d_posedge), + .out_signal_camera_a(out_signal_camera_a), + .out_signal_camera_b(out_signal_camera_b), + .out_signal_camera_c(out_signal_camera_c), + .out_signal_camera_d(out_signal_camera_d) + ); + // User logic ends + + endmodule diff --git a/hardware/pl_platform/ip_repo/ip_encoder_1.0/ip_encoder_0.xcix b/hardware/pl_platform/ip_repo/ip_encoder_1.0/ip_encoder_0.xcix new file mode 100644 index 0000000..3373acb Binary files /dev/null and b/hardware/pl_platform/ip_repo/ip_encoder_1.0/ip_encoder_0.xcix differ diff --git a/hardware/pl_platform/ip_repo/ip_encoder_1.0/src/encoder.v b/hardware/pl_platform/ip_repo/ip_encoder_1.0/src/encoder.v new file mode 100644 index 0000000..8c2e876 --- /dev/null +++ b/hardware/pl_platform/ip_repo/ip_encoder_1.0/src/encoder.v @@ -0,0 +1,226 @@ +module encoder( + input sys_clk, + input rst_n, + input in_signal, + input [31:0] valve_signal_divider, + input [31:0] camera_signal_divider_a, + input [31:0] camera_signal_divider_b, + input [31:0] camera_signal_divider_c, + input [31:0] camera_signal_divider_d, + output out_signal_valve_posedge, + output reg out_signal_valve, + output out_signal_camera_a_posedge, + output out_signal_camera_b_posedge, + output out_signal_camera_c_posedge, + output out_signal_camera_d_posedge, + output reg out_signal_camera_a, + output reg out_signal_camera_b, + output reg out_signal_camera_c, + output reg out_signal_camera_d + ); + + wire [31:0] valve_signal_divider_div_2 = {1'b0, valve_signal_divider[31:1]}; + wire [31:0] camera_signal_divider_a_div_2 = {1'b0, camera_signal_divider_a[31:1]}; + wire [31:0] camera_signal_divider_b_div_2 = {1'b0, camera_signal_divider_b[31:1]}; + wire [31:0] camera_signal_divider_c_div_2 = {1'b0, camera_signal_divider_c[31:1]}; + wire [31:0] camera_signal_divider_d_div_2 = {1'b0, camera_signal_divider_d[31:1]}; + + reg [31:0] valve_signal_divider_tmp; + reg [31:0] camera_signal_divider_a_tmp; + reg [31:0] camera_signal_divider_b_tmp; + reg [31:0] camera_signal_divider_c_tmp; + reg [31:0] camera_signal_divider_d_tmp; + + wire rst_n_inter = (valve_signal_divider_tmp == valve_signal_divider) && (camera_signal_divider_a_tmp == camera_signal_divider_a) && (camera_signal_divider_b_tmp == camera_signal_divider_b)&& (camera_signal_divider_c_tmp == camera_signal_divider_c)&& (camera_signal_divider_d_tmp == camera_signal_divider_d)&& rst_n; + always @(posedge sys_clk) begin + valve_signal_divider_tmp <= valve_signal_divider; + camera_signal_divider_a_tmp <= camera_signal_divider_a; + camera_signal_divider_b_tmp <= camera_signal_divider_b; + camera_signal_divider_c_tmp <= camera_signal_divider_c; + camera_signal_divider_d_tmp <= camera_signal_divider_d; + end + + reg [1:0] in_signal_buffer; + wire in_signal_posedge = in_signal_buffer[0] && !in_signal_buffer[1]; + wire in_signal_negedge = !in_signal_buffer[0] && in_signal_buffer[1]; + wire in_signal_edge = in_signal_posedge || in_signal_negedge; + always @(posedge sys_clk) begin + if (!rst_n_inter) begin + in_signal_buffer <= 0; + end + else begin + in_signal_buffer[0] <= in_signal; + in_signal_buffer[1] <= in_signal_buffer[0]; + end + end + + reg [1:0] out_signal_valve_buffer; + // Actually, !out_signal_valve_buffer[0] && out_signal_valve_buffer[1] is the negedge, it is name posedge because I accidentally made a mistake. + // When I found the mistake, It's too much trouble to change the name, so it was not changed. + assign out_signal_valve_posedge = !out_signal_valve_buffer[0] && out_signal_valve_buffer[1];//实际为下降沿 + always @(posedge sys_clk) begin + if (!rst_n_inter) begin + out_signal_valve_buffer <= 0; + end + else begin + out_signal_valve_buffer[0] <= out_signal_valve; + out_signal_valve_buffer[1] <= out_signal_valve_buffer[0]; + end + end + + reg[1:0] out_signal_camera_a_buffer; + reg[1:0] out_signal_camera_b_buffer; + reg[1:0] out_signal_camera_c_buffer; + reg[1:0] out_signal_camera_d_buffer; + assign out_signal_camera_a_posedge = out_signal_camera_a_buffer[0] && !out_signal_camera_a_buffer[1]; + assign out_signal_camera_b_posedge = out_signal_camera_b_buffer[0] && !out_signal_camera_b_buffer[1]; + assign out_signal_camera_c_posedge = out_signal_camera_c_buffer[0] && !out_signal_camera_c_buffer[1]; + assign out_signal_camera_d_posedge = out_signal_camera_d_buffer[0] && !out_signal_camera_d_buffer[1]; + always @(posedge sys_clk) begin + if (!rst_n_inter) begin + out_signal_camera_a_buffer <= 0; + end + else begin + out_signal_camera_a_buffer[0] <= out_signal_camera_a; + out_signal_camera_a_buffer[1] <= out_signal_camera_a_buffer[0]; + end + end + + always @(posedge sys_clk) begin + if (!rst_n_inter) begin + out_signal_camera_b_buffer <= 0; + end + else begin + out_signal_camera_b_buffer[0] <= out_signal_camera_b; + out_signal_camera_b_buffer[1] <= out_signal_camera_b_buffer[0]; + end + end + + always @(posedge sys_clk) begin + if (!rst_n_inter) begin + out_signal_camera_c_buffer <= 0; + end + else begin + out_signal_camera_c_buffer[0] <= out_signal_camera_c; + out_signal_camera_c_buffer[1] <= out_signal_camera_c_buffer[0]; + end + end + + always @(posedge sys_clk) begin + if (!rst_n_inter) begin + out_signal_camera_d_buffer <= 0; + end + else begin + out_signal_camera_d_buffer[0] <= out_signal_camera_d; + out_signal_camera_d_buffer[1] <= out_signal_camera_d_buffer[0]; + end + end + + reg [31:0] counter_valve; + always @(posedge sys_clk) begin + if (!rst_n_inter) begin + counter_valve <= 0; + end + else if (counter_valve == valve_signal_divider_div_2) begin + counter_valve <= 0; + end + else if (in_signal_posedge) begin + counter_valve <= counter_valve + 1; + end + end + + reg [31:0] counter_camera_a; + reg [31:0] counter_camera_b; + reg [31:0] counter_camera_c; + reg [31:0] counter_camera_d; + always @(posedge sys_clk) begin + if (!rst_n_inter) begin + counter_camera_a <= 0; + end + else if (counter_camera_a == camera_signal_divider_a_div_2) begin + counter_camera_a <= 0; + end + else if (in_signal_posedge) begin + counter_camera_a <= counter_camera_a + 1; + end + end + always @(posedge sys_clk) begin + if (!rst_n_inter) begin + counter_camera_b <= 0; + end + else if (counter_camera_b == camera_signal_divider_b_div_2) begin + counter_camera_b <= 0; + end + else if (in_signal_posedge) begin + counter_camera_b <= counter_camera_b + 1; + end + end + always @(posedge sys_clk) begin + if (!rst_n_inter) begin + counter_camera_c <= 0; + end + else if (counter_camera_c == camera_signal_divider_c_div_2) begin + counter_camera_c <= 0; + end + else if (in_signal_posedge) begin + counter_camera_c <= counter_camera_c + 1; + end + end + always @(posedge sys_clk) begin + if (!rst_n_inter) begin + counter_camera_d <= 0; + end + else if (counter_camera_d == camera_signal_divider_d_div_2) begin + counter_camera_d <= 0; + end + else if (in_signal_posedge) begin + counter_camera_d <= counter_camera_d + 1; + end + end + + always @(posedge sys_clk) begin + if (!rst_n_inter) begin + out_signal_valve <= 0; + end + else if (counter_valve == valve_signal_divider_div_2) begin + out_signal_valve <= !out_signal_valve; + end + end + + always @(posedge sys_clk) begin + if (!rst_n_inter) begin + out_signal_camera_a <= 1; // Please set the camera to posedge trig mode, in case of trig at half period of the first cycle. + end + else if (counter_camera_a == camera_signal_divider_a_div_2) begin + out_signal_camera_a <= !out_signal_camera_a; + end + end + + always @(posedge sys_clk) begin + if (!rst_n_inter) begin + out_signal_camera_b <= 1; // Please set the camera to posedge trig mode, in case of trig at half period of the first cycle. + end + else if (counter_camera_b == camera_signal_divider_b_div_2) begin + out_signal_camera_b <= !out_signal_camera_b; + end + end + + always @(posedge sys_clk) begin + if (!rst_n_inter) begin + out_signal_camera_c <= 1; // Please set the camera to posedge trig mode, in case of trig at half period of the first cycle. + end + else if (counter_camera_c == camera_signal_divider_c_div_2) begin + out_signal_camera_c <= !out_signal_camera_c; + end + end + + always @(posedge sys_clk) begin + if (!rst_n_inter) begin + out_signal_camera_d <= 1; // Please set the camera to posedge trig mode, in case of trig at half period of the first cycle. + end + else if (counter_camera_d == camera_signal_divider_d_div_2) begin + out_signal_camera_d <= !out_signal_camera_d; + end + end + +endmodule \ No newline at end of file diff --git a/hardware/pl_platform/ip_repo/ip_encoder_1.0/xgui/ip_encoder_v1_0.tcl b/hardware/pl_platform/ip_repo/ip_encoder_1.0/xgui/ip_encoder_v1_0.tcl new file mode 100644 index 0000000..124ff1a --- /dev/null +++ b/hardware/pl_platform/ip_repo/ip_encoder_1.0/xgui/ip_encoder_v1_0.tcl @@ -0,0 +1,56 @@ +# Definitional proc to organize widgets for parameters. +proc init_gui { IPINST } { + ipgui::add_param $IPINST -name "Component_Name" + #Adding Page + ipgui::add_page $IPINST -name "Page 0" + + +} + +proc update_PARAM_VALUE.C_S00_AXI_DATA_WIDTH { PARAM_VALUE.C_S00_AXI_DATA_WIDTH } { + # Procedure called to update C_S00_AXI_DATA_WIDTH when any of the dependent parameters in the arguments change +} + +proc validate_PARAM_VALUE.C_S00_AXI_DATA_WIDTH { PARAM_VALUE.C_S00_AXI_DATA_WIDTH } { + # Procedure called to validate C_S00_AXI_DATA_WIDTH + return true +} + +proc update_PARAM_VALUE.C_S00_AXI_ADDR_WIDTH { PARAM_VALUE.C_S00_AXI_ADDR_WIDTH } { + # Procedure called to update C_S00_AXI_ADDR_WIDTH when any of the dependent parameters in the arguments change +} + +proc validate_PARAM_VALUE.C_S00_AXI_ADDR_WIDTH { PARAM_VALUE.C_S00_AXI_ADDR_WIDTH } { + # Procedure called to validate C_S00_AXI_ADDR_WIDTH + return true +} + +proc update_PARAM_VALUE.C_S00_AXI_BASEADDR { PARAM_VALUE.C_S00_AXI_BASEADDR } { + # Procedure called to update C_S00_AXI_BASEADDR when any of the dependent parameters in the arguments change +} + +proc validate_PARAM_VALUE.C_S00_AXI_BASEADDR { PARAM_VALUE.C_S00_AXI_BASEADDR } { + # Procedure called to validate C_S00_AXI_BASEADDR + return true +} + +proc update_PARAM_VALUE.C_S00_AXI_HIGHADDR { PARAM_VALUE.C_S00_AXI_HIGHADDR } { + # Procedure called to update C_S00_AXI_HIGHADDR when any of the dependent parameters in the arguments change +} + +proc validate_PARAM_VALUE.C_S00_AXI_HIGHADDR { PARAM_VALUE.C_S00_AXI_HIGHADDR } { + # Procedure called to validate C_S00_AXI_HIGHADDR + return true +} + + +proc update_MODELPARAM_VALUE.C_S00_AXI_DATA_WIDTH { MODELPARAM_VALUE.C_S00_AXI_DATA_WIDTH PARAM_VALUE.C_S00_AXI_DATA_WIDTH } { + # Procedure called to set VHDL generic/Verilog parameter value(s) based on TCL parameter value + set_property value [get_property value ${PARAM_VALUE.C_S00_AXI_DATA_WIDTH}] ${MODELPARAM_VALUE.C_S00_AXI_DATA_WIDTH} +} + +proc update_MODELPARAM_VALUE.C_S00_AXI_ADDR_WIDTH { MODELPARAM_VALUE.C_S00_AXI_ADDR_WIDTH PARAM_VALUE.C_S00_AXI_ADDR_WIDTH } { + # Procedure called to set VHDL generic/Verilog parameter value(s) based on TCL parameter value + set_property value [get_property value ${PARAM_VALUE.C_S00_AXI_ADDR_WIDTH}] ${MODELPARAM_VALUE.C_S00_AXI_ADDR_WIDTH} +} + diff --git a/hardware/pl_platform/ip_repo/ip_encoder_1.0/xgui/ip_encoder_v1_1.tcl b/hardware/pl_platform/ip_repo/ip_encoder_1.0/xgui/ip_encoder_v1_1.tcl new file mode 100644 index 0000000..a8982ff --- /dev/null +++ b/hardware/pl_platform/ip_repo/ip_encoder_1.0/xgui/ip_encoder_v1_1.tcl @@ -0,0 +1,53 @@ +# Definitional proc to organize widgets for parameters. +proc init_gui { IPINST } { + ipgui::add_param $IPINST -name "Component_Name" + +} + +proc update_PARAM_VALUE.C_S00_AXI_DATA_WIDTH { PARAM_VALUE.C_S00_AXI_DATA_WIDTH } { + # Procedure called to update C_S00_AXI_DATA_WIDTH when any of the dependent parameters in the arguments change +} + +proc validate_PARAM_VALUE.C_S00_AXI_DATA_WIDTH { PARAM_VALUE.C_S00_AXI_DATA_WIDTH } { + # Procedure called to validate C_S00_AXI_DATA_WIDTH + return true +} + +proc update_PARAM_VALUE.C_S00_AXI_ADDR_WIDTH { PARAM_VALUE.C_S00_AXI_ADDR_WIDTH } { + # Procedure called to update C_S00_AXI_ADDR_WIDTH when any of the dependent parameters in the arguments change +} + +proc validate_PARAM_VALUE.C_S00_AXI_ADDR_WIDTH { PARAM_VALUE.C_S00_AXI_ADDR_WIDTH } { + # Procedure called to validate C_S00_AXI_ADDR_WIDTH + return true +} + +proc update_PARAM_VALUE.C_S00_AXI_BASEADDR { PARAM_VALUE.C_S00_AXI_BASEADDR } { + # Procedure called to update C_S00_AXI_BASEADDR when any of the dependent parameters in the arguments change +} + +proc validate_PARAM_VALUE.C_S00_AXI_BASEADDR { PARAM_VALUE.C_S00_AXI_BASEADDR } { + # Procedure called to validate C_S00_AXI_BASEADDR + return true +} + +proc update_PARAM_VALUE.C_S00_AXI_HIGHADDR { PARAM_VALUE.C_S00_AXI_HIGHADDR } { + # Procedure called to update C_S00_AXI_HIGHADDR when any of the dependent parameters in the arguments change +} + +proc validate_PARAM_VALUE.C_S00_AXI_HIGHADDR { PARAM_VALUE.C_S00_AXI_HIGHADDR } { + # Procedure called to validate C_S00_AXI_HIGHADDR + return true +} + + +proc update_MODELPARAM_VALUE.C_S00_AXI_DATA_WIDTH { MODELPARAM_VALUE.C_S00_AXI_DATA_WIDTH PARAM_VALUE.C_S00_AXI_DATA_WIDTH } { + # Procedure called to set VHDL generic/Verilog parameter value(s) based on TCL parameter value + set_property value [get_property value ${PARAM_VALUE.C_S00_AXI_DATA_WIDTH}] ${MODELPARAM_VALUE.C_S00_AXI_DATA_WIDTH} +} + +proc update_MODELPARAM_VALUE.C_S00_AXI_ADDR_WIDTH { MODELPARAM_VALUE.C_S00_AXI_ADDR_WIDTH PARAM_VALUE.C_S00_AXI_ADDR_WIDTH } { + # Procedure called to set VHDL generic/Verilog parameter value(s) based on TCL parameter value + set_property value [get_property value ${PARAM_VALUE.C_S00_AXI_ADDR_WIDTH}] ${MODELPARAM_VALUE.C_S00_AXI_ADDR_WIDTH} +} + diff --git a/hardware/pl_platform/ip_repo/ip_fan_1.0/bd/bd.tcl b/hardware/pl_platform/ip_repo/ip_fan_1.0/bd/bd.tcl new file mode 100644 index 0000000..4804aeb --- /dev/null +++ b/hardware/pl_platform/ip_repo/ip_fan_1.0/bd/bd.tcl @@ -0,0 +1,86 @@ + +proc init { cellpath otherInfo } { + + set cell_handle [get_bd_cells $cellpath] + set all_busif [get_bd_intf_pins $cellpath/*] + set axi_standard_param_list [list ID_WIDTH AWUSER_WIDTH ARUSER_WIDTH WUSER_WIDTH RUSER_WIDTH BUSER_WIDTH] + set full_sbusif_list [list ] + + foreach busif $all_busif { + if { [string equal -nocase [get_property MODE $busif] "slave"] == 1 } { + set busif_param_list [list] + set busif_name [get_property NAME $busif] + if { [lsearch -exact -nocase $full_sbusif_list $busif_name ] == -1 } { + continue + } + foreach tparam $axi_standard_param_list { + lappend busif_param_list "C_${busif_name}_${tparam}" + } + bd::mark_propagate_only $cell_handle $busif_param_list + } + } +} + + +proc pre_propagate {cellpath otherInfo } { + + set cell_handle [get_bd_cells $cellpath] + set all_busif [get_bd_intf_pins $cellpath/*] + set axi_standard_param_list [list ID_WIDTH AWUSER_WIDTH ARUSER_WIDTH WUSER_WIDTH RUSER_WIDTH BUSER_WIDTH] + + foreach busif $all_busif { + if { [string equal -nocase [get_property CONFIG.PROTOCOL $busif] "AXI4"] != 1 } { + continue + } + if { [string equal -nocase [get_property MODE $busif] "master"] != 1 } { + continue + } + + set busif_name [get_property NAME $busif] + foreach tparam $axi_standard_param_list { + set busif_param_name "C_${busif_name}_${tparam}" + + set val_on_cell_intf_pin [get_property CONFIG.${tparam} $busif] + set val_on_cell [get_property CONFIG.${busif_param_name} $cell_handle] + + if { [string equal -nocase $val_on_cell_intf_pin $val_on_cell] != 1 } { + if { $val_on_cell != "" } { + set_property CONFIG.${tparam} $val_on_cell $busif + } + } + } + } +} + + +proc propagate {cellpath otherInfo } { + + set cell_handle [get_bd_cells $cellpath] + set all_busif [get_bd_intf_pins $cellpath/*] + set axi_standard_param_list [list ID_WIDTH AWUSER_WIDTH ARUSER_WIDTH WUSER_WIDTH RUSER_WIDTH BUSER_WIDTH] + + foreach busif $all_busif { + if { [string equal -nocase [get_property CONFIG.PROTOCOL $busif] "AXI4"] != 1 } { + continue + } + if { [string equal -nocase [get_property MODE $busif] "slave"] != 1 } { + continue + } + + set busif_name [get_property NAME $busif] + foreach tparam $axi_standard_param_list { + set busif_param_name "C_${busif_name}_${tparam}" + + set val_on_cell_intf_pin [get_property CONFIG.${tparam} $busif] + set val_on_cell [get_property CONFIG.${busif_param_name} $cell_handle] + + if { [string equal -nocase $val_on_cell_intf_pin $val_on_cell] != 1 } { + #override property of bd_interface_net to bd_cell -- only for slaves. May check for supported values.. + if { $val_on_cell_intf_pin != "" } { + set_property CONFIG.${busif_param_name} $val_on_cell_intf_pin $cell_handle + } + } + } + } +} + diff --git a/hardware/pl_platform/ip_repo/ip_fan_1.0/component.xml b/hardware/pl_platform/ip_repo/ip_fan_1.0/component.xml new file mode 100644 index 0000000..173f27d --- /dev/null +++ b/hardware/pl_platform/ip_repo/ip_fan_1.0/component.xml @@ -0,0 +1,993 @@ + + + user.org + user + ip_fan + 1.0 + + + S00_AXI + + + + + + + + + AWADDR + + + s00_axi_awaddr + + + + + AWPROT + + + s00_axi_awprot + + + + + AWVALID + + + s00_axi_awvalid + + + + + AWREADY + + + s00_axi_awready + + + + + WDATA + + + s00_axi_wdata + + + + + WSTRB + + + s00_axi_wstrb + + + + + WVALID + + + s00_axi_wvalid + + + + + WREADY + + + s00_axi_wready + + + + + BRESP + + + s00_axi_bresp + + + + + BVALID + + + s00_axi_bvalid + + + + + BREADY + + + s00_axi_bready + + + + + ARADDR + + + s00_axi_araddr + + + + + ARPROT + + + s00_axi_arprot + + + + + ARVALID + + + s00_axi_arvalid + + + + + ARREADY + + + s00_axi_arready + + + + + RDATA + + + s00_axi_rdata + + + + + RRESP + + + s00_axi_rresp + + + + + RVALID + + + s00_axi_rvalid + + + + + RREADY + + + s00_axi_rready + + + + + + WIZ_DATA_WIDTH + 32 + + + WIZ_NUM_REG + 4 + + + SUPPORTS_NARROW_BURST + 0 + + + + + S00_AXI_RST + + + + + + + RST + + + s00_axi_aresetn + + + + + + POLARITY + ACTIVE_LOW + + + + + S00_AXI_CLK + + + + + + + CLK + + + s00_axi_aclk + + + + + + ASSOCIATED_BUSIF + S00_AXI + + + ASSOCIATED_RESET + s00_axi_aresetn + + + + + + + S00_AXI + + S00_AXI_reg + 0 + 4096 + 32 + register + + + OFFSET_BASE_PARAM + C_S00_AXI_BASEADDR + + + OFFSET_HIGH_PARAM + C_S00_AXI_HIGHADDR + + + + + + + + + xilinx_verilogsynthesis + Verilog Synthesis + verilogSource:vivado.xilinx.com:synthesis + verilog + ip_fan_v1_0 + + xilinx_verilogsynthesis_view_fileset + + + + viewChecksum + 728a76ba + + + + + xilinx_verilogbehavioralsimulation + Verilog Simulation + verilogSource:vivado.xilinx.com:simulation + verilog + ip_fan_v1_0 + + xilinx_verilogbehavioralsimulation_view_fileset + + + + viewChecksum + 728a76ba + + + + + xilinx_softwaredriver + Software Driver + :vivado.xilinx.com:sw.driver + + xilinx_softwaredriver_view_fileset + + + + viewChecksum + 33320685 + + + + + xilinx_xpgui + UI Layout + :vivado.xilinx.com:xgui.ui + + xilinx_xpgui_view_fileset + + + + viewChecksum + 0e00759d + + + + + bd_tcl + Block Diagram + :vivado.xilinx.com:block.diagram + + bd_tcl_view_fileset + + + + viewChecksum + 45a2f450 + + + + + + + fan + + out + + + wire + xilinx_verilogsynthesis + xilinx_verilogbehavioralsimulation + + + + + + s00_axi_aclk + + in + + + wire + xilinx_verilogsynthesis + xilinx_verilogbehavioralsimulation + + + + + + s00_axi_aresetn + + in + + + wire + xilinx_verilogsynthesis + xilinx_verilogbehavioralsimulation + + + + + + s00_axi_awaddr + + in + + 3 + 0 + + + + wire + xilinx_verilogsynthesis + xilinx_verilogbehavioralsimulation + + + + + + s00_axi_awprot + + in + + 2 + 0 + + + + wire + xilinx_verilogsynthesis + xilinx_verilogbehavioralsimulation + + + + + + s00_axi_awvalid + + in + + + wire + xilinx_verilogsynthesis + xilinx_verilogbehavioralsimulation + + + + + + s00_axi_awready + + out + + + wire + xilinx_verilogsynthesis + xilinx_verilogbehavioralsimulation + + + + + + s00_axi_wdata + + in + + 31 + 0 + + + + wire + xilinx_verilogsynthesis + xilinx_verilogbehavioralsimulation + + + + + + s00_axi_wstrb + + in + + 3 + 0 + + + + wire + xilinx_verilogsynthesis + xilinx_verilogbehavioralsimulation + + + + + + s00_axi_wvalid + + in + + + wire + xilinx_verilogsynthesis + xilinx_verilogbehavioralsimulation + + + + + + s00_axi_wready + + out + + + wire + xilinx_verilogsynthesis + xilinx_verilogbehavioralsimulation + + + + + + s00_axi_bresp + + out + + 1 + 0 + + + + wire + xilinx_verilogsynthesis + xilinx_verilogbehavioralsimulation + + + + + + s00_axi_bvalid + + out + + + wire + xilinx_verilogsynthesis + xilinx_verilogbehavioralsimulation + + + + + + s00_axi_bready + + in + + + wire + xilinx_verilogsynthesis + xilinx_verilogbehavioralsimulation + + + + + + s00_axi_araddr + + in + + 3 + 0 + + + + wire + xilinx_verilogsynthesis + xilinx_verilogbehavioralsimulation + + + + + + s00_axi_arprot + + in + + 2 + 0 + + + + wire + xilinx_verilogsynthesis + xilinx_verilogbehavioralsimulation + + + + + + s00_axi_arvalid + + in + + + wire + xilinx_verilogsynthesis + xilinx_verilogbehavioralsimulation + + + + + + s00_axi_arready + + out + + + wire + xilinx_verilogsynthesis + xilinx_verilogbehavioralsimulation + + + + + + s00_axi_rdata + + out + + 31 + 0 + + + + wire + xilinx_verilogsynthesis + xilinx_verilogbehavioralsimulation + + + + + + s00_axi_rresp + + out + + 1 + 0 + + + + wire + xilinx_verilogsynthesis + xilinx_verilogbehavioralsimulation + + + + + + s00_axi_rvalid + + out + + + wire + xilinx_verilogsynthesis + xilinx_verilogbehavioralsimulation + + + + + + s00_axi_rready + + in + + + wire + xilinx_verilogsynthesis + xilinx_verilogbehavioralsimulation + + + + + + + + C_S00_AXI_DATA_WIDTH + C S00 AXI DATA WIDTH + Width of S_AXI data bus + 32 + + + C_S00_AXI_ADDR_WIDTH + C S00 AXI ADDR WIDTH + Width of S_AXI address bus + 4 + + + FAN_PWM_FREQ + Fan Pwm Freq + 10 + + + SYS_CLK_FREQ + Sys Clk Freq + 200000000 + + + + + + choice_list_6fc15197 + 32 + + + choice_list_9d8b0d81 + ACTIVE_HIGH + ACTIVE_LOW + + + choice_pairs_ce1226b1 + 1 + 0 + + + + + xilinx_verilogsynthesis_view_fileset + + hdl/ip_fan_v1_0_S00_AXI.v + verilogSource + + + hdl/ip_fan_v1_0.v + verilogSource + CHECKSUM_686eeef6 + + + + xilinx_verilogbehavioralsimulation_view_fileset + + hdl/ip_fan_v1_0_S00_AXI.v + verilogSource + + + hdl/ip_fan_v1_0.v + verilogSource + + + + xilinx_softwaredriver_view_fileset + + drivers/ip_fan_v1_0/data/ip_fan.mdd + mdd + driver_mdd + + + drivers/ip_fan_v1_0/data/ip_fan.tcl + tclSource + driver_tcl + + + drivers/ip_fan_v1_0/src/Makefile + driver_src + + + drivers/ip_fan_v1_0/src/ip_fan.h + cSource + driver_src + + + drivers/ip_fan_v1_0/src/ip_fan.c + cSource + driver_src + + + drivers/ip_fan_v1_0/src/ip_fan_selftest.c + cSource + driver_src + + + + xilinx_xpgui_view_fileset + + xgui/ip_fan_v1_0.tcl + tclSource + CHECKSUM_0e00759d + XGUI_VERSION_2 + + + + bd_tcl_view_fileset + + bd/bd.tcl + tclSource + + + + ip for controlling fan + + + C_S00_AXI_DATA_WIDTH + C S00 AXI DATA WIDTH + Width of S_AXI data bus + 32 + + + + false + + + + + + C_S00_AXI_ADDR_WIDTH + C S00 AXI ADDR WIDTH + Width of S_AXI address bus + 4 + + + + false + + + + + + C_S00_AXI_BASEADDR + C S00 AXI BASEADDR + 0xFFFFFFFF + + + + false + + + + + + C_S00_AXI_HIGHADDR + C S00 AXI HIGHADDR + 0x00000000 + + + + false + + + + + + Component_Name + ip_fan_v1_0 + + + FAN_PWM_FREQ + FAN_PWM_FREQ (HZ) + 10 + + + SYS_CLK_FREQ + SYS_CLK_FREQ (HZ) + 200000000 + + + + + + zynq + qzynq + azynq + + + AXI_Peripheral + + ip_fan_v1.0 + 13 + 2022-07-18T09:29:45Z + + /home/miaow/zynq/ip_repo/ip_fan_1.0 + /home/miaow/zynq/ip_repo/ip_fan_1.0 + /home/miaow/zynq/ip_repo/ip_fan_1.0 + /home/miaow/zynq/ip_repo/ip_fan_1.0 + /home/miaow/zynq/ip_repo/ip_fan_1.0 + /home/miaow/zynq/ip_repo/ip_fan_1.0 + /home/miaow/zynq/ip_repo/ip_fan_1.0 + /home/miaow/zynq/ip_repo/ip_fan_1.0 + /home/miaow/zynq/ip_repo/ip_fan_1.0 + /home/miaow/zynq/ip_repo/ip_fan_1.0 + /home/miaow/zynq/ip_repo/ip_fan_1.0 + /home/miaow/zynq/ip_repo/ip_fan_1.0 + /home/miaow/zynq/ip_repo/ip_fan_1.0 + /home/miaow/zynq/ip_repo/ip_fan_1.0 + /home/miaow/zynq/ip_repo/ip_fan_1.0 + /home/miaow/zynq/ip_repo/ip_fan_1.0 + /home/miaow/zynq/ip_repo/ip_fan_1.0 + /home/miaow/zynq/ip_repo/ip_fan_1.0 + /home/miaow/zynq/ip_repo/ip_fan_1.0 + /home/miaow/zynq/ip_repo/ip_fan_1.0 + /home/miaow/zynq/ip_repo/ip_fan_1.0 + /home/miaow/zynq/ip_repo/ip_fan_1.0 + /home/miaow/zynq/ip_repo/ip_fan_1.0 + /home/miaow/zynq/ip_repo/ip_fan_1.0 + /home/miaow/zynq/ip_repo/ip_fan_1.0 + /home/miaow/zynq/ip_repo/ip_fan_1.0 + /home/miaow/zynq/ip_repo/ip_fan_1.0 + /home/miaow/zynq/ip_repo/ip_fan_1.0 + /home/miaow/zynq/ip_repo/ip_fan_1.0 + /home/miaow/zynq/ip_repo/ip_fan_1.0 + /home/miaow/zynq/ip_repo/ip_fan_1.0 + /home/miaow/zynq/ip_repo/ip_fan_1.0 + /home/miaow/zynq/ip_repo/ip_fan_1.0 + /home/miaow/zynq/ip_repo/ip_fan_1.0 + /home/miaow/zynq/ip_repo/ip_fan_1.0 + /home/miaow/zynq/ip_repo/ip_fan_1.0 + /home/miaow/zynq/ip_repo/ip_fan_1.0 + /home/miaow/zynq/ip_repo/ip_fan_1.0 + /home/miaow/zynq/ip_repo/ip_fan_1.0 + /home/miaow/zynq/ip_repo/ip_fan_1.0 + /home/miaow/zynq/ip_repo/ip_fan_1.0 + /home/miaow/zynq/ip_repo/ip_fan_1.0 + /home/miaow/zynq/ip_repo/ip_fan_1.0 + /home/miaow/zynq/ip_repo/ip_fan_1.0 + /home/miaow/zynq/ip_repo/ip_fan_1.0 + /home/miaow/zynq/ip_repo/ip_fan_1.0 + /home/miaow/zynq/ip_repo/ip_fan_1.0 + /home/miaow/zynq/ip_repo/ip_fan_1.0 + /home/miaow/zynq/ip_repo/ip_fan_1.0 + /home/miaow/zynq/ip_repo/ip_fan_1.0 + /home/miaow/zynq/ip_repo/ip_fan_1.0 + /home/miaow/zynq/ip_repo/ip_fan_1.0 + /home/miaow/zynq/ip_repo/ip_fan_1.0 + /home/miaow/zynq/ip_repo/ip_fan_1.0 + /home/miaow/zynq/ip_repo/ip_fan_1.0 + /home/miaow/zynq/ip_repo/ip_fan_1.0 + /home/miaow/zynq/ip_repo/ip_fan_1.0 + /home/miaow/zynq/ip_repo/ip_fan_1.0 + /home/miaow/zynq/ip_repo/ip_fan_1.0 + /home/miaow/zynq/ip_repo/ip_fan_1.0 + /home/miaow/zynq/ip_repo/ip_fan_1.0 + /home/miaow/zynq/ip_repo/ip_fan_1.0 + /home/miaow/zynq/ip_repo/ip_fan_1.0 + /home/miaow/zynq/ip_repo/ip_fan_1.0 + /home/miaow/zynq/ip_repo/ip_fan_1.0 + /home/miaow/zynq/ip_repo/ip_fan_1.0 + /home/miaow/zynq/ip_repo/ip_fan_1.0 + /home/miaow/zynq/ip_repo/ip_fan_1.0 + /home/miaow/zynq/ip_repo/ip_fan_1.0 + /home/miaow/zynq/ip_repo/ip_fan_1.0 + /home/miaow/zynq/ip_repo/ip_fan_1.0 + /home/miaow/zynq/ip_repo/ip_fan_1.0 + /home/miaow/zynq/ip_repo/ip_fan_1.0 + /home/miaow/zynq/ip_repo/ip_fan_1.0 + /home/miaow/zynq/ip_repo/ip_fan_1.0 + /home/miaow/zynq/ip_repo/ip_fan_1.0 + /home/miaow/zynq/ip_repo/ip_fan_1.0 + /home/miaow/zynq/ip_repo/ip_fan_1.0 + /home/miaow/zynq/ip_repo/ip_fan_1.0 + /home/miaow/zynq/ip_repo/ip_fan_1.0 + /home/miaow/zynq/ip_repo/ip_fan_1.0 + /home/miaow/zynq/ip_repo/ip_fan_1.0 + /home/miaow/zynq/ip_repo/ip_fan_1.0 + /home/miaow/zynq/ip_repo/ip_fan_1.0 + /home/miaow/zynq/ip_repo/ip_fan_1.0 + /home/miaow/zynq/ip_repo/ip_fan_1.0 + /home/miaow/zynq/ip_repo/ip_fan_1.0 + /home/miaow/zynq/ip_repo/ip_fan_1.0 + /home/miaow/zynq/ip_repo/ip_fan_1.0 + /home/miaow/zynq/ip_repo/ip_fan_1.0 + /home/miaow/zynq/ip_repo/ip_fan_1.0 + /home/miaow/zynq/ip_repo/ip_fan_1.0 + /home/miaow/zynq/ip_repo/ip_fan_1.0 + /home/miaow/zynq/ip_repo/ip_fan_1.0 + /home/miaow/zynq/ip_repo/ip_fan_1.0 + /home/miaow/zynq/ip_repo/ip_fan_1.0 + /home/miaow/zynq/ip_repo/ip_fan_1.0 + /home/miaow/zynq/ip_repo/ip_fan_1.0 + /home/miaow/zynq/ip_repo/ip_fan_1.0 + /home/miaow/zynq/ip_repo/ip_fan_1.0 + /home/miaow/zynq/ip_repo/ip_fan_1.0 + /home/miaow/zynq/ip_repo/ip_fan_1.0 + /home/miaow/zynq/ip_repo/ip_fan_1.0 + /home/miaow/zynq/ip_repo/ip_fan_1.0 + /home/miaow/zynq/ip_repo/ip_fan_1.0 + /home/miaow/zynq/ip_repo/ip_fan_1.0 + /home/miaow/zynq/ip_repo/ip_fan_1.0 + /home/miaow/zynq/ip_repo/ip_fan_1.0 + /home/miaow/zynq/ip_repo/ip_fan_1.0 + /home/miaow/zynq/ip_repo/ip_fan_1.0 + /home/miaow/zynq/ip_repo/ip_fan_1.0 + /home/miaow/zynq/ip_repo/ip_fan_1.0 + /home/miaow/zynq/ip_repo/ip_fan_1.0 + /home/miaow/zynq/ip_repo/ip_fan_1.0 + /home/miaow/zynq/ip_repo/ip_fan_1.0 + /home/miaow/zynq/ip_repo/ip_fan_1.0 + /home/miaow/zynq/ip_repo/ip_fan_1.0 + /home/miaow/zynq/ip_repo/ip_fan_1.0 + /home/miaow/zynq/ip_repo/ip_fan_1.0 + /home/miaow/zynq/ip_repo/ip_fan_1.0 + /home/miaow/zynq/ip_repo/ip_fan_1.0 + /home/miaow/zynq/ip_repo/ip_fan_1.0 + /home/miaow/zynq/ip_repo/ip_fan_1.0 + /home/miaow/zynq/ip_repo/ip_fan_1.0 + /home/miaow/zynq/ip_repo/ip_fan_1.0 + /home/miaow/zynq/ip_repo/ip_fan_1.0 + /home/miaow/zynq/ip_repo/ip_fan_1.0 + /home/miaow/zynq/ip_repo/ip_fan_1.0 + /home/miaow/zynq/ip_repo/ip_fan_1.0 + /home/miaow/zynq/ip_repo/ip_fan_1.0 + + + + 2022.1 + + + + + + + + + diff --git a/hardware/pl_platform/ip_repo/ip_fan_1.0/drivers/ip_fan_v1_0/data/ip_fan.mdd b/hardware/pl_platform/ip_repo/ip_fan_1.0/drivers/ip_fan_v1_0/data/ip_fan.mdd new file mode 100644 index 0000000..0f8a4a3 --- /dev/null +++ b/hardware/pl_platform/ip_repo/ip_fan_1.0/drivers/ip_fan_v1_0/data/ip_fan.mdd @@ -0,0 +1,10 @@ + + +OPTION psf_version = 2.1; + +BEGIN DRIVER ip_fan + OPTION supported_peripherals = (ip_fan); + OPTION copyfiles = all; + OPTION VERSION = 1.0; + OPTION NAME = ip_fan; +END DRIVER diff --git a/hardware/pl_platform/ip_repo/ip_fan_1.0/drivers/ip_fan_v1_0/data/ip_fan.tcl b/hardware/pl_platform/ip_repo/ip_fan_1.0/drivers/ip_fan_v1_0/data/ip_fan.tcl new file mode 100644 index 0000000..437a934 --- /dev/null +++ b/hardware/pl_platform/ip_repo/ip_fan_1.0/drivers/ip_fan_v1_0/data/ip_fan.tcl @@ -0,0 +1,5 @@ + + +proc generate {drv_handle} { + xdefine_include_file $drv_handle "xparameters.h" "ip_fan" "NUM_INSTANCES" "DEVICE_ID" "C_S00_AXI_BASEADDR" "C_S00_AXI_HIGHADDR" +} diff --git a/hardware/pl_platform/ip_repo/ip_fan_1.0/drivers/ip_fan_v1_0/src/Makefile b/hardware/pl_platform/ip_repo/ip_fan_1.0/drivers/ip_fan_v1_0/src/Makefile new file mode 100644 index 0000000..87f6d25 --- /dev/null +++ b/hardware/pl_platform/ip_repo/ip_fan_1.0/drivers/ip_fan_v1_0/src/Makefile @@ -0,0 +1,26 @@ +COMPILER= +ARCHIVER= +CP=cp +COMPILER_FLAGS= +EXTRA_COMPILER_FLAGS= +LIB=libxil.a + +RELEASEDIR=../../../lib +INCLUDEDIR=../../../include +INCLUDES=-I./. -I${INCLUDEDIR} + +INCLUDEFILES=*.h +LIBSOURCES=*.c +OUTS = *.o + +libs: + echo "Compiling ip_fan..." + $(COMPILER) $(COMPILER_FLAGS) $(EXTRA_COMPILER_FLAGS) $(INCLUDES) $(LIBSOURCES) + $(ARCHIVER) -r ${RELEASEDIR}/${LIB} ${OUTS} + make clean + +include: + ${CP} $(INCLUDEFILES) $(INCLUDEDIR) + +clean: + rm -rf ${OUTS} diff --git a/hardware/pl_platform/ip_repo/ip_fan_1.0/drivers/ip_fan_v1_0/src/ip_fan.c b/hardware/pl_platform/ip_repo/ip_fan_1.0/drivers/ip_fan_v1_0/src/ip_fan.c new file mode 100644 index 0000000..cc2d5a1 --- /dev/null +++ b/hardware/pl_platform/ip_repo/ip_fan_1.0/drivers/ip_fan_v1_0/src/ip_fan.c @@ -0,0 +1,6 @@ + + +/***************************** Include Files *******************************/ +#include "ip_fan.h" + +/************************** Function Definitions ***************************/ diff --git a/hardware/pl_platform/ip_repo/ip_fan_1.0/drivers/ip_fan_v1_0/src/ip_fan.h b/hardware/pl_platform/ip_repo/ip_fan_1.0/drivers/ip_fan_v1_0/src/ip_fan.h new file mode 100644 index 0000000..94a8b77 --- /dev/null +++ b/hardware/pl_platform/ip_repo/ip_fan_1.0/drivers/ip_fan_v1_0/src/ip_fan.h @@ -0,0 +1,79 @@ + +#ifndef IP_FAN_H +#define IP_FAN_H + + +/****************** Include Files ********************/ +#include "xil_types.h" +#include "xstatus.h" + +#define IP_FAN_S00_AXI_SLV_REG0_OFFSET 0 +#define IP_FAN_S00_AXI_SLV_REG1_OFFSET 4 +#define IP_FAN_S00_AXI_SLV_REG2_OFFSET 8 +#define IP_FAN_S00_AXI_SLV_REG3_OFFSET 12 + + +/**************************** Type Definitions *****************************/ +/** + * + * Write a value to a IP_FAN register. A 32 bit write is performed. + * If the component is implemented in a smaller width, only the least + * significant data is written. + * + * @param BaseAddress is the base address of the IP_FANdevice. + * @param RegOffset is the register offset from the base to write to. + * @param Data is the data written to the register. + * + * @return None. + * + * @note + * C-style signature: + * void IP_FAN_mWriteReg(u32 BaseAddress, unsigned RegOffset, u32 Data) + * + */ +#define IP_FAN_mWriteReg(BaseAddress, RegOffset, Data) \ + Xil_Out32((BaseAddress) + (RegOffset), (u32)(Data)) + +/** + * + * Read a value from a IP_FAN register. A 32 bit read is performed. + * If the component is implemented in a smaller width, only the least + * significant data is read from the register. The most significant data + * will be read as 0. + * + * @param BaseAddress is the base address of the IP_FAN device. + * @param RegOffset is the register offset from the base to write to. + * + * @return Data is the data from the register. + * + * @note + * C-style signature: + * u32 IP_FAN_mReadReg(u32 BaseAddress, unsigned RegOffset) + * + */ +#define IP_FAN_mReadReg(BaseAddress, RegOffset) \ + Xil_In32((BaseAddress) + (RegOffset)) + +/************************** Function Prototypes ****************************/ +/** + * + * Run a self-test on the driver/device. Note this may be a destructive test if + * resets of the device are performed. + * + * If the hardware system is not built correctly, this function may never + * return to the caller. + * + * @param baseaddr_p is the base address of the IP_FAN instance to be worked on. + * + * @return + * + * - XST_SUCCESS if all self-test code passed + * - XST_FAILURE if any self-test code failed + * + * @note Caching must be turned off for this function to work. + * @note Self test may fail if data memory and device are not on the same bus. + * + */ +XStatus IP_FAN_Reg_SelfTest(void * baseaddr_p); + +#endif // IP_FAN_H diff --git a/hardware/pl_platform/ip_repo/ip_fan_1.0/drivers/ip_fan_v1_0/src/ip_fan_selftest.c b/hardware/pl_platform/ip_repo/ip_fan_1.0/drivers/ip_fan_v1_0/src/ip_fan_selftest.c new file mode 100644 index 0000000..682c8bf --- /dev/null +++ b/hardware/pl_platform/ip_repo/ip_fan_1.0/drivers/ip_fan_v1_0/src/ip_fan_selftest.c @@ -0,0 +1,60 @@ + +/***************************** Include Files *******************************/ +#include "ip_fan.h" +#include "xparameters.h" +#include "stdio.h" +#include "xil_io.h" + +/************************** Constant Definitions ***************************/ +#define READ_WRITE_MUL_FACTOR 0x10 + +/************************** Function Definitions ***************************/ +/** + * + * Run a self-test on the driver/device. Note this may be a destructive test if + * resets of the device are performed. + * + * If the hardware system is not built correctly, this function may never + * return to the caller. + * + * @param baseaddr_p is the base address of the IP_FANinstance to be worked on. + * + * @return + * + * - XST_SUCCESS if all self-test code passed + * - XST_FAILURE if any self-test code failed + * + * @note Caching must be turned off for this function to work. + * @note Self test may fail if data memory and device are not on the same bus. + * + */ +XStatus IP_FAN_Reg_SelfTest(void * baseaddr_p) +{ + u32 baseaddr; + int write_loop_index; + int read_loop_index; + int Index; + + baseaddr = (u32) baseaddr_p; + + xil_printf("******************************\n\r"); + xil_printf("* User Peripheral Self Test\n\r"); + xil_printf("******************************\n\n\r"); + + /* + * Write to user logic slave module register(s) and read back + */ + xil_printf("User logic slave module test...\n\r"); + + for (write_loop_index = 0 ; write_loop_index < 4; write_loop_index++) + IP_FAN_mWriteReg (baseaddr, write_loop_index*4, (write_loop_index+1)*READ_WRITE_MUL_FACTOR); + for (read_loop_index = 0 ; read_loop_index < 4; read_loop_index++) + if ( IP_FAN_mReadReg (baseaddr, read_loop_index*4) != (read_loop_index+1)*READ_WRITE_MUL_FACTOR){ + xil_printf ("Error reading register value at address %x\n", (int)baseaddr + read_loop_index*4); + return XST_FAILURE; + } + + xil_printf(" - slave register write/read passed\n\n\r"); + + return XST_SUCCESS; +} diff --git a/hardware/pl_platform/ip_repo/ip_fan_1.0/example_designs/bfm_design/design.tcl b/hardware/pl_platform/ip_repo/ip_fan_1.0/example_designs/bfm_design/design.tcl new file mode 100644 index 0000000..8a5abf6 --- /dev/null +++ b/hardware/pl_platform/ip_repo/ip_fan_1.0/example_designs/bfm_design/design.tcl @@ -0,0 +1,88 @@ +proc create_ipi_design { offsetfile design_name } { + create_bd_design $design_name + open_bd_design $design_name + + # Create Clock and Reset Ports + set ACLK [ create_bd_port -dir I -type clk ACLK ] + set_property -dict [ list CONFIG.FREQ_HZ {100000000} CONFIG.PHASE {0.000} CONFIG.CLK_DOMAIN "${design_name}_ACLK" ] $ACLK + set ARESETN [ create_bd_port -dir I -type rst ARESETN ] + set_property -dict [ list CONFIG.POLARITY {ACTIVE_LOW} ] $ARESETN + set_property CONFIG.ASSOCIATED_RESET ARESETN $ACLK + + # Create instance: ip_fan_0, and set properties + set ip_fan_0 [ create_bd_cell -type ip -vlnv user.org:user:ip_fan:1.0 ip_fan_0] + + # Create instance: master_0, and set properties + set master_0 [ create_bd_cell -type ip -vlnv xilinx.com:ip:axi_vip master_0] + set_property -dict [ list CONFIG.PROTOCOL {AXI4LITE} CONFIG.INTERFACE_MODE {MASTER} ] $master_0 + + # Create interface connections + connect_bd_intf_net [get_bd_intf_pins master_0/M_AXI ] [get_bd_intf_pins ip_fan_0/S00_AXI] + + # Create port connections + connect_bd_net -net aclk_net [get_bd_ports ACLK] [get_bd_pins master_0/ACLK] [get_bd_pins ip_fan_0/S00_AXI_ACLK] + connect_bd_net -net aresetn_net [get_bd_ports ARESETN] [get_bd_pins master_0/ARESETN] [get_bd_pins ip_fan_0/S00_AXI_ARESETN] +set_property target_simulator XSim [current_project] +set_property -name {xsim.simulate.runtime} -value {100ms} -objects [get_filesets sim_1] + + # Auto assign address + assign_bd_address + + # Copy all address to interface_address.vh file + set bd_path [file dirname [get_property NAME [get_files ${design_name}.bd]]] + upvar 1 $offsetfile offset_file + set offset_file "${bd_path}/ip_fan_v1_0_tb_include.svh" + set fp [open $offset_file "w"] + puts $fp "`ifndef ip_fan_v1_0_tb_include_vh_" + puts $fp "`define ip_fan_v1_0_tb_include_vh_\n" + puts $fp "//Configuration current bd names" + puts $fp "`define BD_NAME ${design_name}" + puts $fp "`define BD_INST_NAME ${design_name}_i" + puts $fp "`define BD_WRAPPER ${design_name}_wrapper\n" + puts $fp "//Configuration address parameters" + + puts $fp "`endif" + close $fp +} + +set ip_path [file dirname [file normalize [get_property XML_FILE_NAME [ipx::get_cores user.org:user:ip_fan:1.0]]]] +set test_bench_file ${ip_path}/example_designs/bfm_design/ip_fan_v1_0_tb.sv +set interface_address_vh_file "" + +# Set IP Repository and Update IP Catalogue +set repo_paths [get_property ip_repo_paths [current_fileset]] +if { [lsearch -exact -nocase $repo_paths $ip_path ] == -1 } { + set_property ip_repo_paths "$ip_path [get_property ip_repo_paths [current_fileset]]" [current_fileset] + update_ip_catalog +} + +set design_name "" +set all_bd {} +set all_bd_files [get_files *.bd -quiet] +foreach file $all_bd_files { +set file_name [string range $file [expr {[string last "/" $file] + 1}] end] +set bd_name [string range $file_name 0 [expr {[string last "." $file_name] -1}]] +lappend all_bd $bd_name +} + +for { set i 1 } { 1 } { incr i } { + set design_name "ip_fan_v1_0_bfm_${i}" + if { [lsearch -exact -nocase $all_bd $design_name ] == -1 } { + break + } +} + +create_ipi_design interface_address_vh_file ${design_name} +validate_bd_design + +set wrapper_file [make_wrapper -files [get_files ${design_name}.bd] -top -force] +import_files -force -norecurse $wrapper_file + +set_property SOURCE_SET sources_1 [get_filesets sim_1] +import_files -fileset sim_1 -norecurse -force $test_bench_file +remove_files -quiet -fileset sim_1 ip_fan_v1_0_tb_include.vh +import_files -fileset sim_1 -norecurse -force $interface_address_vh_file +set_property top ip_fan_v1_0_tb [get_filesets sim_1] +set_property top_lib {} [get_filesets sim_1] +set_property top_file {} [get_filesets sim_1] +launch_simulation -simset sim_1 -mode behavioral diff --git a/hardware/pl_platform/ip_repo/ip_fan_1.0/example_designs/bfm_design/ip_fan_v1_0_tb.sv b/hardware/pl_platform/ip_repo/ip_fan_1.0/example_designs/bfm_design/ip_fan_v1_0_tb.sv new file mode 100644 index 0000000..6002760 --- /dev/null +++ b/hardware/pl_platform/ip_repo/ip_fan_1.0/example_designs/bfm_design/ip_fan_v1_0_tb.sv @@ -0,0 +1,197 @@ + +`timescale 1ns / 1ps +`include "ip_fan_v1_0_tb_include.svh" + +import axi_vip_pkg::*; +import ip_fan_v1_0_bfm_1_master_0_0_pkg::*; + +module ip_fan_v1_0_tb(); + + +xil_axi_uint error_cnt = 0; +xil_axi_uint comparison_cnt = 0; +axi_transaction wr_transaction; +axi_transaction rd_transaction; +axi_monitor_transaction mst_monitor_transaction; +axi_monitor_transaction master_moniter_transaction_queue[$]; +xil_axi_uint master_moniter_transaction_queue_size =0; +axi_monitor_transaction mst_scb_transaction; +axi_monitor_transaction passthrough_monitor_transaction; +axi_monitor_transaction passthrough_master_moniter_transaction_queue[$]; +xil_axi_uint passthrough_master_moniter_transaction_queue_size =0; +axi_monitor_transaction passthrough_mst_scb_transaction; +axi_monitor_transaction passthrough_slave_moniter_transaction_queue[$]; +xil_axi_uint passthrough_slave_moniter_transaction_queue_size =0; +axi_monitor_transaction passthrough_slv_scb_transaction; +axi_monitor_transaction slv_monitor_transaction; +axi_monitor_transaction slave_moniter_transaction_queue[$]; +xil_axi_uint slave_moniter_transaction_queue_size =0; +axi_monitor_transaction slv_scb_transaction; +xil_axi_uint mst_agent_verbosity = 0; +xil_axi_uint slv_agent_verbosity = 0; +xil_axi_uint passthrough_agent_verbosity = 0; +bit clock; +bit reset; +integer result_slave; +bit [31:0] S00_AXI_test_data[3:0]; + localparam LC_AXI_BURST_LENGTH = 8; + localparam LC_AXI_DATA_WIDTH = 32; +task automatic COMPARE_DATA; + input [(LC_AXI_BURST_LENGTH * LC_AXI_DATA_WIDTH)-1:0]expected; + input [(LC_AXI_BURST_LENGTH * LC_AXI_DATA_WIDTH)-1:0]actual; + begin + if (expected === 'hx || actual === 'hx) begin + $display("TESTBENCH ERROR! COMPARE_DATA cannot be performed with an expected or actual vector that is all 'x'!"); + result_slave = 0; $stop; + end + if (actual != expected) begin + $display("TESTBENCH ERROR! Data expected is not equal to actual.", " expected = 0x%h",expected, " actual = 0x%h",actual); + result_slave = 0; + $stop; + end + else + begin + $display("TESTBENCH Passed! Data expected is equal to actual.", + " expected = 0x%h",expected, " actual = 0x%h",actual); + end + end +endtask +integer i; +integer j; +xil_axi_uint trans_cnt_before_switch = 48; +xil_axi_uint passthrough_cmd_switch_cnt = 0; +event passthrough_mastermode_start_event; +event passthrough_mastermode_end_event; +event passthrough_slavemode_end_event; +xil_axi_uint mtestID; +xil_axi_ulong mtestADDR; +xil_axi_len_t mtestBurstLength; +xil_axi_size_t mtestDataSize; +xil_axi_burst_t mtestBurstType; +xil_axi_lock_t mtestLOCK; +xil_axi_cache_t mtestCacheType = 0; +xil_axi_prot_t mtestProtectionType = 3'b000; +xil_axi_region_t mtestRegion = 4'b000; +xil_axi_qos_t mtestQOS = 4'b000; +xil_axi_data_beat dbeat; +xil_axi_data_beat [255:0] mtestWUSER; +xil_axi_data_beat mtestAWUSER = 'h0; +xil_axi_data_beat mtestARUSER = 0; +xil_axi_data_beat [255:0] mtestRUSER; +xil_axi_uint mtestBUSER = 0; +xil_axi_resp_t mtestBresp; +xil_axi_resp_t[255:0] mtestRresp; +bit [63:0] mtestWDataL; +bit [63:0] mtestRDataL; +axi_transaction pss_wr_transaction; +axi_transaction pss_rd_transaction; +axi_transaction reactive_transaction; +axi_transaction rd_payload_transaction; +axi_transaction wr_rand; +axi_transaction rd_rand; +axi_transaction wr_reactive; +axi_transaction rd_reactive; +axi_transaction wr_reactive2; +axi_transaction rd_reactive2; +axi_ready_gen bready_gen; +axi_ready_gen rready_gen; +axi_ready_gen awready_gen; +axi_ready_gen wready_gen; +axi_ready_gen arready_gen; +axi_ready_gen bready_gen2; +axi_ready_gen rready_gen2; +axi_ready_gen awready_gen2; +axi_ready_gen wready_gen2; +axi_ready_gen arready_gen2; +xil_axi_payload_byte data_mem[xil_axi_ulong]; +ip_fan_v1_0_bfm_1_master_0_0_mst_t mst_agent_0; + + `BD_WRAPPER DUT( + .ARESETN(reset), + .ACLK(clock) + ); + +initial begin + mst_agent_0 = new("master vip agent",DUT.`BD_INST_NAME.master_0.inst.IF);//ms + mst_agent_0.vif_proxy.set_dummy_drive_type(XIL_AXI_VIF_DRIVE_NONE); + mst_agent_0.set_agent_tag("Master VIP"); + mst_agent_0.set_verbosity(mst_agent_verbosity); + mst_agent_0.start_master(); + $timeformat (-12, 1, " ps", 1); + end + initial begin + reset <= 1'b0; + #200ns; + reset <= 1'b1; + repeat (5) @(negedge clock); + end + always #5 clock <= ~clock; + initial begin + S_AXI_TEST ( ); + + #1ns; + $finish; + end +task automatic S_AXI_TEST; +begin +#1; + $display("Sequential write transfers example similar to AXI BFM WRITE_BURST method starts"); + mtestID = 0; + mtestADDR = 64'h00000000; + mtestBurstLength = 0; + mtestDataSize = xil_axi_size_t'(xil_clog2(32/8)); + mtestBurstType = XIL_AXI_BURST_TYPE_INCR; + mtestLOCK = XIL_AXI_ALOCK_NOLOCK; + mtestCacheType = 0; + mtestProtectionType = 0; + mtestRegion = 0; + mtestQOS = 0; + result_slave = 1; + mtestWDataL[31:0] = 32'h00000001; + for(int i = 0; i < 4;i++) begin + S00_AXI_test_data[i] <= mtestWDataL[31:0]; + mst_agent_0.AXI4LITE_WRITE_BURST( + mtestADDR, + mtestProtectionType, + mtestWDataL, + mtestBresp + ); + mtestWDataL[31:0] = mtestWDataL[31:0] + 1; + mtestADDR = mtestADDR + 64'h4; + end + $display("Sequential write transfers example similar to AXI BFM WRITE_BURST method completes"); + $display("Sequential read transfers example similar to AXI BFM READ_BURST method starts"); + mtestID = 0; + mtestADDR = 64'h00000000; + mtestBurstLength = 0; + mtestDataSize = xil_axi_size_t'(xil_clog2(32/8)); + mtestBurstType = XIL_AXI_BURST_TYPE_INCR; + mtestLOCK = XIL_AXI_ALOCK_NOLOCK; + mtestCacheType = 0; + mtestProtectionType = 0; + mtestRegion = 0; + mtestQOS = 0; + for(int i = 0; i < 4;i++) begin + mst_agent_0.AXI4LITE_READ_BURST( + mtestADDR, + mtestProtectionType, + mtestRDataL, + mtestRresp + ); + mtestADDR = mtestADDR + 64'h4; + COMPARE_DATA(S00_AXI_test_data[i],mtestRDataL); + end + $display("Sequential read transfers example similar to AXI BFM READ_BURST method completes"); + $display("Sequential read transfers example similar to AXI VIP READ_BURST method completes"); + $display("---------------------------------------------------------"); + $display("EXAMPLE TEST S00_AXI: PTGEN_TEST_FINISHED!"); + if ( result_slave ) begin + $display("PTGEN_TEST: PASSED!"); + end else begin + $display("PTGEN_TEST: FAILED!"); + end + $display("---------------------------------------------------------"); + end +endtask + +endmodule diff --git a/hardware/pl_platform/ip_repo/ip_fan_1.0/example_designs/debug_hw_design/design.tcl b/hardware/pl_platform/ip_repo/ip_fan_1.0/example_designs/debug_hw_design/design.tcl new file mode 100644 index 0000000..420cb86 --- /dev/null +++ b/hardware/pl_platform/ip_repo/ip_fan_1.0/example_designs/debug_hw_design/design.tcl @@ -0,0 +1,118 @@ + +proc create_ipi_design { offsetfile design_name } { + + create_bd_design $design_name + open_bd_design $design_name + + # Create and configure Clock/Reset + create_bd_cell -type ip -vlnv xilinx.com:ip:clk_wiz sys_clk_0 + create_bd_cell -type ip -vlnv xilinx.com:ip:proc_sys_reset sys_reset_0 + + #Constraints will be provided manually while pin planning. + create_bd_port -dir I -type rst reset_rtl + set_property CONFIG.POLARITY [get_property CONFIG.POLARITY [get_bd_pins sys_clk_0/reset]] [get_bd_ports reset_rtl] + connect_bd_net [get_bd_pins sys_reset_0/ext_reset_in] [get_bd_ports reset_rtl] + connect_bd_net [get_bd_ports reset_rtl] [get_bd_pins sys_clk_0/reset] + set external_reset_port reset_rtl + create_bd_port -dir I -type clk clock_rtl + connect_bd_net [get_bd_pins sys_clk_0/clk_in1] [get_bd_ports clock_rtl] + set external_clock_port clock_rtl + + #Avoid IPI DRC, make clock port synchronous to reset + if { $external_clock_port ne "" && $external_reset_port ne "" } { + set_property CONFIG.ASSOCIATED_RESET $external_reset_port [get_bd_ports $external_clock_port] + } + + # Connect other sys_reset pins + connect_bd_net [get_bd_pins sys_reset_0/slowest_sync_clk] [get_bd_pins sys_clk_0/clk_out1] + connect_bd_net [get_bd_pins sys_clk_0/locked] [get_bd_pins sys_reset_0/dcm_locked] + + # Create instance: ip_fan_0, and set properties + set ip_fan_0 [ create_bd_cell -type ip -vlnv user.org:user:ip_fan:1.0 ip_fan_0 ] + + # Create instance: jtag_axi_0, and set properties + set jtag_axi_0 [ create_bd_cell -type ip -vlnv xilinx.com:ip:jtag_axi jtag_axi_0 ] + set_property -dict [list CONFIG.PROTOCOL {0}] [get_bd_cells jtag_axi_0] + connect_bd_net [get_bd_pins jtag_axi_0/aclk] [get_bd_pins sys_clk_0/clk_out1] + connect_bd_net [get_bd_pins jtag_axi_0/aresetn] [get_bd_pins sys_reset_0/peripheral_aresetn] + + # Create instance: axi_peri_interconnect, and set properties + set axi_peri_interconnect [ create_bd_cell -type ip -vlnv xilinx.com:ip:axi_interconnect axi_peri_interconnect ] + connect_bd_net [get_bd_pins axi_peri_interconnect/ACLK] [get_bd_pins sys_clk_0/clk_out1] + connect_bd_net [get_bd_pins axi_peri_interconnect/ARESETN] [get_bd_pins sys_reset_0/interconnect_aresetn] + set_property -dict [ list CONFIG.NUM_SI {1} ] $axi_peri_interconnect + connect_bd_net [get_bd_pins axi_peri_interconnect/S00_ACLK] [get_bd_pins sys_clk_0/clk_out1] + connect_bd_net [get_bd_pins axi_peri_interconnect/S00_ARESETN] [get_bd_pins sys_reset_0/peripheral_aresetn] + connect_bd_intf_net [get_bd_intf_pins jtag_axi_0/M_AXI] [get_bd_intf_pins axi_peri_interconnect/S00_AXI] + + set_property -dict [ list CONFIG.NUM_MI {1} ] $axi_peri_interconnect + connect_bd_net [get_bd_pins axi_peri_interconnect/M00_ACLK] [get_bd_pins sys_clk_0/clk_out1] + connect_bd_net [get_bd_pins axi_peri_interconnect/M00_ARESETN] [get_bd_pins sys_reset_0/peripheral_aresetn] + + # Connect all clock & reset of ip_fan_0 slave interfaces.. + connect_bd_intf_net [get_bd_intf_pins axi_peri_interconnect/M00_AXI] [get_bd_intf_pins ip_fan_0/S00_AXI] + connect_bd_net [get_bd_pins ip_fan_0/s00_axi_aclk] [get_bd_pins sys_clk_0/clk_out1] + connect_bd_net [get_bd_pins ip_fan_0/s00_axi_aresetn] [get_bd_pins sys_reset_0/peripheral_aresetn] + + + # Auto assign address + assign_bd_address + + # Copy all address to ip_fan_v1_0_include.tcl file + set bd_path [get_property DIRECTORY [current_project]]/[current_project].srcs/[current_fileset]/bd + upvar 1 $offsetfile offset_file + set offset_file "${bd_path}/ip_fan_v1_0_include.tcl" + set fp [open $offset_file "w"] + puts $fp "# Configuration address parameters" + + set offset [get_property OFFSET [get_bd_addr_segs /jtag_axi_0/Data/SEG_ip_fan_0_S00_AXI_* ]] + puts $fp "set s00_axi_addr ${offset}" + + close $fp +} + +# Set IP Repository and Update IP Catalogue +set ip_path [file dirname [file normalize [get_property XML_FILE_NAME [ipx::get_cores user.org:user:ip_fan:1.0]]]] +set hw_test_file ${ip_path}/example_designs/debug_hw_design/ip_fan_v1_0_hw_test.tcl + +set repo_paths [get_property ip_repo_paths [current_fileset]] +if { [lsearch -exact -nocase $repo_paths $ip_path ] == -1 } { + set_property ip_repo_paths "$ip_path [get_property ip_repo_paths [current_fileset]]" [current_fileset] + update_ip_catalog +} + +set design_name "" +set all_bd {} +set all_bd_files [get_files *.bd -quiet] +foreach file $all_bd_files { +set file_name [string range $file [expr {[string last "/" $file] + 1}] end] +set bd_name [string range $file_name 0 [expr {[string last "." $file_name] -1}]] +lappend all_bd $bd_name +} + +for { set i 1 } { 1 } { incr i } { + set design_name "ip_fan_v1_0_hw_${i}" + if { [lsearch -exact -nocase $all_bd $design_name ] == -1 } { + break + } +} + +set intf_address_include_file "" +create_ipi_design intf_address_include_file ${design_name} +save_bd_design +validate_bd_design + +set wrapper_file [make_wrapper -files [get_files ${design_name}.bd] -top -force] +import_files -force -norecurse $wrapper_file + +puts "-------------------------------------------------------------------------------------------------" +puts "INFO NEXT STEPS : Until this stage, debug hardware design has been created, " +puts " please perform following steps to test design in targeted board." +puts "1. Generate bitstream" +puts "2. Setup your targeted board, open hardware manager and open new(or existing) hardware target" +puts "3. Download generated bitstream" +puts "4. Run generated hardware test using below command, this invokes basic read/write operation" +puts " to every interface present in the peripheral : xilinx.com:user:myip:1.0" +puts " : source -notrace ${hw_test_file}" +puts "-------------------------------------------------------------------------------------------------" + diff --git a/hardware/pl_platform/ip_repo/ip_fan_1.0/example_designs/debug_hw_design/ip_fan_v1_0_hw_test.tcl b/hardware/pl_platform/ip_repo/ip_fan_1.0/example_designs/debug_hw_design/ip_fan_v1_0_hw_test.tcl new file mode 100644 index 0000000..6287e38 --- /dev/null +++ b/hardware/pl_platform/ip_repo/ip_fan_1.0/example_designs/debug_hw_design/ip_fan_v1_0_hw_test.tcl @@ -0,0 +1,45 @@ +# Runtime Tcl commands to interact with - ip_fan_v1_0 + +# Sourcing design address info tcl +set bd_path [get_property DIRECTORY [current_project]]/[current_project].srcs/[current_fileset]/bd +source ${bd_path}/ip_fan_v1_0_include.tcl + +# jtag axi master interface hardware name, change as per your design. +set jtag_axi_master hw_axi_1 +set ec 0 + +# hw test script +# Delete all previous axis transactions +if { [llength [get_hw_axi_txns -quiet]] } { + delete_hw_axi_txn [get_hw_axi_txns -quiet] +} + + +# Test all lite slaves. +set wdata_1 abcd1234 + +# Test: S00_AXI +# Create a write transaction at s00_axi_addr address +create_hw_axi_txn w_s00_axi_addr [get_hw_axis $jtag_axi_master] -type write -address $s00_axi_addr -data $wdata_1 +# Create a read transaction at s00_axi_addr address +create_hw_axi_txn r_s00_axi_addr [get_hw_axis $jtag_axi_master] -type read -address $s00_axi_addr +# Initiate transactions +run_hw_axi r_s00_axi_addr +run_hw_axi w_s00_axi_addr +run_hw_axi r_s00_axi_addr +set rdata_tmp [get_property DATA [get_hw_axi_txn r_s00_axi_addr]] +# Compare read data +if { $rdata_tmp == $wdata_1 } { + puts "Data comparison test pass for - S00_AXI" +} else { + puts "Data comparison test fail for - S00_AXI, expected-$wdata_1 actual-$rdata_tmp" + inc ec +} + +# Check error flag +if { $ec == 0 } { + puts "PTGEN_TEST: PASSED!" +} else { + puts "PTGEN_TEST: FAILED!" +} + diff --git a/hardware/pl_platform/ip_repo/ip_fan_1.0/hdl/ip_fan_v1_0.v b/hardware/pl_platform/ip_repo/ip_fan_1.0/hdl/ip_fan_v1_0.v new file mode 100644 index 0000000..96ee1e9 --- /dev/null +++ b/hardware/pl_platform/ip_repo/ip_fan_1.0/hdl/ip_fan_v1_0.v @@ -0,0 +1,82 @@ + +`timescale 1 ns / 1 ps + + module ip_fan_v1_0 # + ( + // Users to add parameters here + parameter FAN_PWM_FREQ = 10, + parameter SYS_CLK_FREQ = 200_000_000, + // User parameters ends + // Do not modify the parameters beyond this line + + + // Parameters of Axi Slave Bus Interface S00_AXI + parameter integer C_S00_AXI_DATA_WIDTH = 32, + parameter integer C_S00_AXI_ADDR_WIDTH = 4 + ) + ( + // Users to add ports here + output wire fan, + // User ports ends + // Do not modify the ports beyond this line + + + // Ports of Axi Slave Bus Interface S00_AXI + input wire s00_axi_aclk, + input wire s00_axi_aresetn, + input wire [C_S00_AXI_ADDR_WIDTH-1 : 0] s00_axi_awaddr, + input wire [2 : 0] s00_axi_awprot, + input wire s00_axi_awvalid, + output wire s00_axi_awready, + input wire [C_S00_AXI_DATA_WIDTH-1 : 0] s00_axi_wdata, + input wire [(C_S00_AXI_DATA_WIDTH/8)-1 : 0] s00_axi_wstrb, + input wire s00_axi_wvalid, + output wire s00_axi_wready, + output wire [1 : 0] s00_axi_bresp, + output wire s00_axi_bvalid, + input wire s00_axi_bready, + input wire [C_S00_AXI_ADDR_WIDTH-1 : 0] s00_axi_araddr, + input wire [2 : 0] s00_axi_arprot, + input wire s00_axi_arvalid, + output wire s00_axi_arready, + output wire [C_S00_AXI_DATA_WIDTH-1 : 0] s00_axi_rdata, + output wire [1 : 0] s00_axi_rresp, + output wire s00_axi_rvalid, + input wire s00_axi_rready + ); +// Instantiation of Axi Bus Interface S00_AXI + ip_fan_v1_0_S00_AXI # ( + .FAN_PWM_FREQ(FAN_PWM_FREQ), + .SYS_CLK_FREQ(SYS_CLK_FREQ), + .C_S_AXI_DATA_WIDTH(C_S00_AXI_DATA_WIDTH), + .C_S_AXI_ADDR_WIDTH(C_S00_AXI_ADDR_WIDTH) + ) ip_fan_v1_0_S00_AXI_inst ( + .fan(fan), + .S_AXI_ACLK(s00_axi_aclk), + .S_AXI_ARESETN(s00_axi_aresetn), + .S_AXI_AWADDR(s00_axi_awaddr), + .S_AXI_AWPROT(s00_axi_awprot), + .S_AXI_AWVALID(s00_axi_awvalid), + .S_AXI_AWREADY(s00_axi_awready), + .S_AXI_WDATA(s00_axi_wdata), + .S_AXI_WSTRB(s00_axi_wstrb), + .S_AXI_WVALID(s00_axi_wvalid), + .S_AXI_WREADY(s00_axi_wready), + .S_AXI_BRESP(s00_axi_bresp), + .S_AXI_BVALID(s00_axi_bvalid), + .S_AXI_BREADY(s00_axi_bready), + .S_AXI_ARADDR(s00_axi_araddr), + .S_AXI_ARPROT(s00_axi_arprot), + .S_AXI_ARVALID(s00_axi_arvalid), + .S_AXI_ARREADY(s00_axi_arready), + .S_AXI_RDATA(s00_axi_rdata), + .S_AXI_RRESP(s00_axi_rresp), + .S_AXI_RVALID(s00_axi_rvalid), + .S_AXI_RREADY(s00_axi_rready) + ); + + // Add user logic here + + // User logic ends + + endmodule diff --git a/hardware/pl_platform/ip_repo/ip_fan_1.0/hdl/ip_fan_v1_0_S00_AXI.v b/hardware/pl_platform/ip_repo/ip_fan_1.0/hdl/ip_fan_v1_0_S00_AXI.v new file mode 100644 index 0000000..560e2f1 --- /dev/null +++ b/hardware/pl_platform/ip_repo/ip_fan_1.0/hdl/ip_fan_v1_0_S00_AXI.v @@ -0,0 +1,457 @@ + +`timescale 1 ns / 1 ps + + module ip_fan_v1_0_S00_AXI # + ( + // Users to add parameters here + parameter FAN_PWM_FREQ = 200, + parameter SYS_CLK_FREQ = 20_000_000, + // User parameters ends + // Do not modify the parameters beyond this line + + // Width of S_AXI data bus + parameter integer C_S_AXI_DATA_WIDTH = 32, + // Width of S_AXI address bus + parameter integer C_S_AXI_ADDR_WIDTH = 4 + ) + ( + // Users to add ports here + + output reg fan, + + // User ports ends + // Do not modify the ports beyond this line + + // Global Clock Signal + input wire S_AXI_ACLK, + // Global Reset Signal. This Signal is Active LOW + input wire S_AXI_ARESETN, + // Write address (issued by master, acceped by Slave) + input wire [C_S_AXI_ADDR_WIDTH-1 : 0] S_AXI_AWADDR, + // Write channel Protection type. This signal indicates the + // privilege and security level of the transaction, and whether + // the transaction is a data access or an instruction access. + input wire [2 : 0] S_AXI_AWPROT, + // Write address valid. This signal indicates that the master signaling + // valid write address and control information. + input wire S_AXI_AWVALID, + // Write address ready. This signal indicates that the slave is ready + // to accept an address and associated control signals. + output wire S_AXI_AWREADY, + // Write data (issued by master, acceped by Slave) + input wire [C_S_AXI_DATA_WIDTH-1 : 0] S_AXI_WDATA, + // Write strobes. This signal indicates which byte lanes hold + // valid data. There is one write strobe bit for each eight + // bits of the write data bus. + input wire [(C_S_AXI_DATA_WIDTH/8)-1 : 0] S_AXI_WSTRB, + // Write valid. This signal indicates that valid write + // data and strobes are available. + input wire S_AXI_WVALID, + // Write ready. This signal indicates that the slave + // can accept the write data. + output wire S_AXI_WREADY, + // Write response. This signal indicates the status + // of the write transaction. + output wire [1 : 0] S_AXI_BRESP, + // Write response valid. This signal indicates that the channel + // is signaling a valid write response. + output wire S_AXI_BVALID, + // Response ready. This signal indicates that the master + // can accept a write response. + input wire S_AXI_BREADY, + // Read address (issued by master, acceped by Slave) + input wire [C_S_AXI_ADDR_WIDTH-1 : 0] S_AXI_ARADDR, + // Protection type. This signal indicates the privilege + // and security level of the transaction, and whether the + // transaction is a data access or an instruction access. + input wire [2 : 0] S_AXI_ARPROT, + // Read address valid. This signal indicates that the channel + // is signaling valid read address and control information. + input wire S_AXI_ARVALID, + // Read address ready. This signal indicates that the slave is + // ready to accept an address and associated control signals. + output wire S_AXI_ARREADY, + // Read data (issued by slave) + output wire [C_S_AXI_DATA_WIDTH-1 : 0] S_AXI_RDATA, + // Read response. This signal indicates the status of the + // read transfer. + output wire [1 : 0] S_AXI_RRESP, + // Read valid. This signal indicates that the channel is + // signaling the required read data. + output wire S_AXI_RVALID, + // Read ready. This signal indicates that the master can + // accept the read data and response information. + input wire S_AXI_RREADY + ); + + // AXI4LITE signals + reg [C_S_AXI_ADDR_WIDTH-1 : 0] axi_awaddr; + reg axi_awready; + reg axi_wready; + reg [1 : 0] axi_bresp; + reg axi_bvalid; + reg [C_S_AXI_ADDR_WIDTH-1 : 0] axi_araddr; + reg axi_arready; + reg [C_S_AXI_DATA_WIDTH-1 : 0] axi_rdata; + reg [1 : 0] axi_rresp; + reg axi_rvalid; + + // Example-specific design signals + // local parameter for addressing 32 bit / 64 bit C_S_AXI_DATA_WIDTH + // ADDR_LSB is used for addressing 32/64 bit registers/memories + // ADDR_LSB = 2 for 32 bits (n downto 2) + // ADDR_LSB = 3 for 64 bits (n downto 3) + localparam integer ADDR_LSB = (C_S_AXI_DATA_WIDTH/32) + 1; + localparam integer OPT_MEM_ADDR_BITS = 1; + //---------------------------------------------- + //-- Signals for user logic register space example + //------------------------------------------------ + //-- Number of Slave Registers 4 + reg [C_S_AXI_DATA_WIDTH-1:0] slv_reg0; + reg [C_S_AXI_DATA_WIDTH-1:0] slv_reg1; + reg [C_S_AXI_DATA_WIDTH-1:0] slv_reg2; + reg [C_S_AXI_DATA_WIDTH-1:0] slv_reg3; + wire slv_reg_rden; + wire slv_reg_wren; + reg [C_S_AXI_DATA_WIDTH-1:0] reg_data_out; + integer byte_index; + reg aw_en; + + // I/O Connections assignments + + assign S_AXI_AWREADY = axi_awready; + assign S_AXI_WREADY = axi_wready; + assign S_AXI_BRESP = axi_bresp; + assign S_AXI_BVALID = axi_bvalid; + assign S_AXI_ARREADY = axi_arready; + assign S_AXI_RDATA = axi_rdata; + assign S_AXI_RRESP = axi_rresp; + assign S_AXI_RVALID = axi_rvalid; + // Implement axi_awready generation + // axi_awready is asserted for one S_AXI_ACLK clock cycle when both + // S_AXI_AWVALID and S_AXI_WVALID are asserted. axi_awready is + // de-asserted when reset is low. + + always @( posedge S_AXI_ACLK ) + begin + if ( S_AXI_ARESETN == 1'b0 ) + begin + axi_awready <= 1'b0; + aw_en <= 1'b1; + end + else + begin + if (~axi_awready && S_AXI_AWVALID && S_AXI_WVALID && aw_en) + begin + // slave is ready to accept write address when + // there is a valid write address and write data + // on the write address and data bus. This design + // expects no outstanding transactions. + axi_awready <= 1'b1; + aw_en <= 1'b0; + end + else if (S_AXI_BREADY && axi_bvalid) + begin + aw_en <= 1'b1; + axi_awready <= 1'b0; + end + else + begin + axi_awready <= 1'b0; + end + end + end + + // Implement axi_awaddr latching + // This process is used to latch the address when both + // S_AXI_AWVALID and S_AXI_WVALID are valid. + + always @( posedge S_AXI_ACLK ) + begin + if ( S_AXI_ARESETN == 1'b0 ) + begin + axi_awaddr <= 0; + end + else + begin + if (~axi_awready && S_AXI_AWVALID && S_AXI_WVALID && aw_en) + begin + // Write Address latching + axi_awaddr <= S_AXI_AWADDR; + end + end + end + + // Implement axi_wready generation + // axi_wready is asserted for one S_AXI_ACLK clock cycle when both + // S_AXI_AWVALID and S_AXI_WVALID are asserted. axi_wready is + // de-asserted when reset is low. + + always @( posedge S_AXI_ACLK ) + begin + if ( S_AXI_ARESETN == 1'b0 ) + begin + axi_wready <= 1'b0; + end + else + begin + if (~axi_wready && S_AXI_WVALID && S_AXI_AWVALID && aw_en ) + begin + // slave is ready to accept write data when + // there is a valid write address and write data + // on the write address and data bus. This design + // expects no outstanding transactions. + axi_wready <= 1'b1; + end + else + begin + axi_wready <= 1'b0; + end + end + end + + // Implement memory mapped register select and write logic generation + // The write data is accepted and written to memory mapped registers when + // axi_awready, S_AXI_WVALID, axi_wready and S_AXI_WVALID are asserted. Write strobes are used to + // select byte enables of slave registers while writing. + // These registers are cleared when reset (active low) is applied. + // Slave register write enable is asserted when valid address and data are available + // and the slave is ready to accept the write address and write data. + assign slv_reg_wren = axi_wready && S_AXI_WVALID && axi_awready && S_AXI_AWVALID; + + always @( posedge S_AXI_ACLK ) + begin + if ( S_AXI_ARESETN == 1'b0 ) + begin + slv_reg0 <= 0; + slv_reg1 <= 0; + slv_reg2 <= 0; + slv_reg3 <= 0; + end + else begin + if (slv_reg_wren) begin + case ( axi_awaddr[ADDR_LSB+OPT_MEM_ADDR_BITS:ADDR_LSB] ) + 2'h0: + for ( byte_index = 0; byte_index <= (C_S_AXI_DATA_WIDTH/8)-1; byte_index = byte_index+1 ) + if ( S_AXI_WSTRB[byte_index] == 1 ) begin + // Respective byte enables are asserted as per write strobes + // Slave register 0 + slv_reg0[(byte_index*8) +: 8] <= S_AXI_WDATA[(byte_index*8) +: 8]; + end + 2'h1: + for ( byte_index = 0; byte_index <= (C_S_AXI_DATA_WIDTH/8)-1; byte_index = byte_index+1 ) + if ( S_AXI_WSTRB[byte_index] == 1 ) begin + // Respective byte enables are asserted as per write strobes + // Slave register 1 + slv_reg1[(byte_index*8) +: 8] <= S_AXI_WDATA[(byte_index*8) +: 8]; + end + 2'h2: + for ( byte_index = 0; byte_index <= (C_S_AXI_DATA_WIDTH/8)-1; byte_index = byte_index+1 ) + if ( S_AXI_WSTRB[byte_index] == 1 ) begin + // Respective byte enables are asserted as per write strobes + // Slave register 2 + slv_reg2[(byte_index*8) +: 8] <= S_AXI_WDATA[(byte_index*8) +: 8]; + end + 2'h3: + for ( byte_index = 0; byte_index <= (C_S_AXI_DATA_WIDTH/8)-1; byte_index = byte_index+1 ) + if ( S_AXI_WSTRB[byte_index] == 1 ) begin + // Respective byte enables are asserted as per write strobes + // Slave register 3 + slv_reg3[(byte_index*8) +: 8] <= S_AXI_WDATA[(byte_index*8) +: 8]; + end + default : begin + slv_reg0 <= slv_reg0; + slv_reg1 <= slv_reg1; + slv_reg2 <= slv_reg2; + slv_reg3 <= slv_reg3; + end + endcase + end + end + end + + // Implement write response logic generation + // The write response and response valid signals are asserted by the slave + // when axi_wready, S_AXI_WVALID, axi_wready and S_AXI_WVALID are asserted. + // This marks the acceptance of address and indicates the status of + // write transaction. + + always @( posedge S_AXI_ACLK ) + begin + if ( S_AXI_ARESETN == 1'b0 ) + begin + axi_bvalid <= 0; + axi_bresp <= 2'b0; + end + else + begin + if (axi_awready && S_AXI_AWVALID && ~axi_bvalid && axi_wready && S_AXI_WVALID) + begin + // indicates a valid write response is available + axi_bvalid <= 1'b1; + axi_bresp <= 2'b0; // 'OKAY' response + end // work error responses in future + else + begin + if (S_AXI_BREADY && axi_bvalid) + //check if bready is asserted while bvalid is high) + //(there is a possibility that bready is always asserted high) + begin + axi_bvalid <= 1'b0; + end + end + end + end + + // Implement axi_arready generation + // axi_arready is asserted for one S_AXI_ACLK clock cycle when + // S_AXI_ARVALID is asserted. axi_awready is + // de-asserted when reset (active low) is asserted. + // The read address is also latched when S_AXI_ARVALID is + // asserted. axi_araddr is reset to zero on reset assertion. + + always @( posedge S_AXI_ACLK ) + begin + if ( S_AXI_ARESETN == 1'b0 ) + begin + axi_arready <= 1'b0; + axi_araddr <= 32'b0; + end + else + begin + if (~axi_arready && S_AXI_ARVALID) + begin + // indicates that the slave has acceped the valid read address + axi_arready <= 1'b1; + // Read address latching + axi_araddr <= S_AXI_ARADDR; + end + else + begin + axi_arready <= 1'b0; + end + end + end + + // Implement axi_arvalid generation + // axi_rvalid is asserted for one S_AXI_ACLK clock cycle when both + // S_AXI_ARVALID and axi_arready are asserted. The slave registers + // data are available on the axi_rdata bus at this instance. The + // assertion of axi_rvalid marks the validity of read data on the + // bus and axi_rresp indicates the status of read transaction.axi_rvalid + // is deasserted on reset (active low). axi_rresp and axi_rdata are + // cleared to zero on reset (active low). + always @( posedge S_AXI_ACLK ) + begin + if ( S_AXI_ARESETN == 1'b0 ) + begin + axi_rvalid <= 0; + axi_rresp <= 0; + end + else + begin + if (axi_arready && S_AXI_ARVALID && ~axi_rvalid) + begin + // Valid read data is available at the read data bus + axi_rvalid <= 1'b1; + axi_rresp <= 2'b0; // 'OKAY' response + end + else if (axi_rvalid && S_AXI_RREADY) + begin + // Read data is accepted by the master + axi_rvalid <= 1'b0; + end + end + end + + // Implement memory mapped register select and read logic generation + // Slave register read enable is asserted when valid address is available + // and the slave is ready to accept the read address. + assign slv_reg_rden = axi_arready & S_AXI_ARVALID & ~axi_rvalid; + always @(*) + begin + // Address decoding for reading registers + case ( axi_araddr[ADDR_LSB+OPT_MEM_ADDR_BITS:ADDR_LSB] ) + 2'h0 : reg_data_out <= slv_reg0; + 2'h1 : reg_data_out <= slv_reg1; + 2'h2 : reg_data_out <= slv_reg2; + 2'h3 : reg_data_out <= slv_reg3; + default : reg_data_out <= 0; + endcase + end + + // slv_reg0[0]: + // 1 - turn on pwm, the fan is controlled by pwm + // 0 - turn off the fan + + // slv_reg1: + // 32bit register, an unsigned integer defining the dutycycle of pwm. dutycycle% = slv_reg1 / (2 ^ 32 - 1) * 100% + // + // Output register or memory read data + always @( posedge S_AXI_ACLK ) + begin + if ( S_AXI_ARESETN == 1'b0 ) + begin + axi_rdata <= 0; + end + else + begin + // When there is a valid read address (S_AXI_ARVALID) with + // acceptance of read address by the slave (axi_arready), + // output the read dada + if (slv_reg_rden) + begin + axi_rdata <= reg_data_out; // register read data + end + end + end + + // Add user logic here + reg S_AXI_BREADY_D0; + reg S_AXI_BREADY_D1; + wire S_AXI_BREADY_NEGEDGE = S_AXI_BREADY_D0 && !S_AXI_BREADY_D1; + parameter RELOAD_VALUE = SYS_CLK_FREQ / FAN_PWM_FREQ; + reg [31:0] counter; + + always @(posedge S_AXI_ACLK) begin + if (S_AXI_ARESETN == 1'b0) begin + S_AXI_BREADY_D0 <= 0; + S_AXI_BREADY_D1 <= 0; + end + else begin + S_AXI_BREADY_D0 <= S_AXI_BREADY; + S_AXI_BREADY_D1 <= S_AXI_BREADY_D0; + end + end + + always @(posedge S_AXI_ACLK) begin + if ( S_AXI_ARESETN == 1'b0 || S_AXI_BREADY_NEGEDGE == 1'b1) begin + fan <= 0; + end + else if (counter < slv_reg1) begin + fan <= 1'b1 & slv_reg0[0]; + end + else begin + fan <= 1'b0; + end + end + + always @(posedge S_AXI_ACLK) begin + if ( S_AXI_ARESETN == 1'b0 || S_AXI_BREADY_NEGEDGE == 1'b1) begin + counter <= 0; + end + else if (slv_reg0[0] == 1'b1)begin + if (counter >= RELOAD_VALUE) begin + counter <= 0; + end + else begin + counter <= counter + 32'd1; + end + end + else begin + counter <= 0; + end + end + // User logic ends + + endmodule diff --git a/hardware/pl_platform/ip_repo/ip_fan_1.0/ip_fan_0.xcix b/hardware/pl_platform/ip_repo/ip_fan_1.0/ip_fan_0.xcix new file mode 100644 index 0000000..2bc5da0 Binary files /dev/null and b/hardware/pl_platform/ip_repo/ip_fan_1.0/ip_fan_0.xcix differ diff --git a/hardware/pl_platform/ip_repo/ip_fan_1.0/xgui/ip_fan_v1_0.tcl b/hardware/pl_platform/ip_repo/ip_fan_1.0/xgui/ip_fan_v1_0.tcl new file mode 100644 index 0000000..80d5298 --- /dev/null +++ b/hardware/pl_platform/ip_repo/ip_fan_1.0/xgui/ip_fan_v1_0.tcl @@ -0,0 +1,81 @@ +# Definitional proc to organize widgets for parameters. +proc init_gui { IPINST } { + ipgui::add_param $IPINST -name "Component_Name" + +} + +proc update_PARAM_VALUE.FAN_PWM_FREQ { PARAM_VALUE.FAN_PWM_FREQ } { + # Procedure called to update FAN_PWM_FREQ when any of the dependent parameters in the arguments change +} + +proc validate_PARAM_VALUE.FAN_PWM_FREQ { PARAM_VALUE.FAN_PWM_FREQ } { + # Procedure called to validate FAN_PWM_FREQ + return true +} + +proc update_PARAM_VALUE.SYS_CLK_FREQ { PARAM_VALUE.SYS_CLK_FREQ } { + # Procedure called to update SYS_CLK_FREQ when any of the dependent parameters in the arguments change +} + +proc validate_PARAM_VALUE.SYS_CLK_FREQ { PARAM_VALUE.SYS_CLK_FREQ } { + # Procedure called to validate SYS_CLK_FREQ + return true +} + +proc update_PARAM_VALUE.C_S00_AXI_DATA_WIDTH { PARAM_VALUE.C_S00_AXI_DATA_WIDTH } { + # Procedure called to update C_S00_AXI_DATA_WIDTH when any of the dependent parameters in the arguments change +} + +proc validate_PARAM_VALUE.C_S00_AXI_DATA_WIDTH { PARAM_VALUE.C_S00_AXI_DATA_WIDTH } { + # Procedure called to validate C_S00_AXI_DATA_WIDTH + return true +} + +proc update_PARAM_VALUE.C_S00_AXI_ADDR_WIDTH { PARAM_VALUE.C_S00_AXI_ADDR_WIDTH } { + # Procedure called to update C_S00_AXI_ADDR_WIDTH when any of the dependent parameters in the arguments change +} + +proc validate_PARAM_VALUE.C_S00_AXI_ADDR_WIDTH { PARAM_VALUE.C_S00_AXI_ADDR_WIDTH } { + # Procedure called to validate C_S00_AXI_ADDR_WIDTH + return true +} + +proc update_PARAM_VALUE.C_S00_AXI_BASEADDR { PARAM_VALUE.C_S00_AXI_BASEADDR } { + # Procedure called to update C_S00_AXI_BASEADDR when any of the dependent parameters in the arguments change +} + +proc validate_PARAM_VALUE.C_S00_AXI_BASEADDR { PARAM_VALUE.C_S00_AXI_BASEADDR } { + # Procedure called to validate C_S00_AXI_BASEADDR + return true +} + +proc update_PARAM_VALUE.C_S00_AXI_HIGHADDR { PARAM_VALUE.C_S00_AXI_HIGHADDR } { + # Procedure called to update C_S00_AXI_HIGHADDR when any of the dependent parameters in the arguments change +} + +proc validate_PARAM_VALUE.C_S00_AXI_HIGHADDR { PARAM_VALUE.C_S00_AXI_HIGHADDR } { + # Procedure called to validate C_S00_AXI_HIGHADDR + return true +} + + +proc update_MODELPARAM_VALUE.C_S00_AXI_DATA_WIDTH { MODELPARAM_VALUE.C_S00_AXI_DATA_WIDTH PARAM_VALUE.C_S00_AXI_DATA_WIDTH } { + # Procedure called to set VHDL generic/Verilog parameter value(s) based on TCL parameter value + set_property value [get_property value ${PARAM_VALUE.C_S00_AXI_DATA_WIDTH}] ${MODELPARAM_VALUE.C_S00_AXI_DATA_WIDTH} +} + +proc update_MODELPARAM_VALUE.C_S00_AXI_ADDR_WIDTH { MODELPARAM_VALUE.C_S00_AXI_ADDR_WIDTH PARAM_VALUE.C_S00_AXI_ADDR_WIDTH } { + # Procedure called to set VHDL generic/Verilog parameter value(s) based on TCL parameter value + set_property value [get_property value ${PARAM_VALUE.C_S00_AXI_ADDR_WIDTH}] ${MODELPARAM_VALUE.C_S00_AXI_ADDR_WIDTH} +} + +proc update_MODELPARAM_VALUE.FAN_PWM_FREQ { MODELPARAM_VALUE.FAN_PWM_FREQ PARAM_VALUE.FAN_PWM_FREQ } { + # Procedure called to set VHDL generic/Verilog parameter value(s) based on TCL parameter value + set_property value [get_property value ${PARAM_VALUE.FAN_PWM_FREQ}] ${MODELPARAM_VALUE.FAN_PWM_FREQ} +} + +proc update_MODELPARAM_VALUE.SYS_CLK_FREQ { MODELPARAM_VALUE.SYS_CLK_FREQ PARAM_VALUE.SYS_CLK_FREQ } { + # Procedure called to set VHDL generic/Verilog parameter value(s) based on TCL parameter value + set_property value [get_property value ${PARAM_VALUE.SYS_CLK_FREQ}] ${MODELPARAM_VALUE.SYS_CLK_FREQ} +} + diff --git a/hardware/pl_platform/lower_machine.tcl b/hardware/pl_platform/lower_machine.tcl new file mode 100644 index 0000000..43db30e --- /dev/null +++ b/hardware/pl_platform/lower_machine.tcl @@ -0,0 +1,568 @@ +#***************************************************************************************** +# Vivado (TM) v2022.1 (64-bit) +# +# lower_machine.tcl: Tcl script for re-creating project 'lower_machine' +# +# Generated by Vivado on Fri Apr 28 09:33:21 PDT 2023 +# IP Build 3524634 on Mon Apr 18 20:55:01 MDT 2022 +# +# This file contains the Vivado Tcl commands for re-creating the project to the state* +# when this script was generated. In order to re-create the project, please source this +# file in the Vivado Tcl Shell. +# +# * Note that the runs in the created project will be configured the same way as the +# original project, however they will not be launched automatically. To regenerate the +# run results please launch the synthesis/implementation runs as needed. +# +#***************************************************************************************** +# NOTE: In order to use this script for source control purposes, please make sure that the +# following files are added to the source control system:- +# +# 1. This project restoration tcl script (lower_machine.tcl) that was generated. +# +# 2. The following source(s) files that were local or imported into the original project. +# (Please see the '$orig_proj_dir' and '$origin_dir' variable setting below at the start of the script) +# +# "$origin_dir/bd/system.tcl" +# +# 3. The following remote source files that were added to the original project:- +# +# "$origin_dir/cstr/lower_machine.xdc" +# +#***************************************************************************************** + +# Check file required for this script exists +proc checkRequiredFiles { origin_dir} { + set status true + set files [list \ + "[file normalize "$origin_dir/bd/system.tcl"]"\ + ] + foreach ifile $files { + if { ![file isfile $ifile] } { + puts " Could not find local file $ifile " + set status false + } + } + + set files [list \ + "[file normalize "$origin_dir/cstr/lower_machine.xdc"]"\ + ] + foreach ifile $files { + if { ![file isfile $ifile] } { + puts " Could not find remote file $ifile " + set status false + } + } + + set paths [list \ + "[file normalize "$origin_dir/../[file normalize "$origin_dir/ip_repo"]"]"\ + ] + foreach ipath $paths { + if { ![file isdirectory $ipath] } { + puts " Could not access $ipath " + set status false + } + } + + return $status +} +# Set the reference directory for source file relative paths (by default the value is script directory path) +set origin_dir [file dirname [info script]] + +# Use origin directory path location variable, if specified in the tcl shell +if { [info exists ::origin_dir_loc] } { + set origin_dir $::origin_dir_loc +} + +# Set the project name +set _xil_proj_name_ "lower_machine" + +# Use project name variable, if specified in the tcl shell +if { [info exists ::user_project_name] } { + set _xil_proj_name_ $::user_project_name +} + +variable script_file +set script_file "lower_machine.tcl" + +# Help information for this script +proc print_help {} { + variable script_file + puts "\nDescription:" + puts "Recreate a Vivado project from this script. The created project will be" + puts "functionally equivalent to the original project for which this script was" + puts "generated. The script contains commands for creating a project, filesets," + puts "runs, adding/importing sources and setting properties on various objects.\n" + puts "Syntax:" + puts "$script_file" + puts "$script_file -tclargs \[--origin_dir \]" + puts "$script_file -tclargs \[--project_name \]" + puts "$script_file -tclargs \[--help\]\n" + puts "Usage:" + puts "Name Description" + puts "-------------------------------------------------------------------------" + puts "\[--origin_dir \] Determine source file paths wrt this path. Default" + puts " origin_dir path value is \".\", otherwise, the value" + puts " that was set with the \"-paths_relative_to\" switch" + puts " when this script was generated.\n" + puts "\[--project_name \] Create project with the specified name. Default" + puts " name is the name of the project from where this" + puts " script was generated.\n" + puts "\[--help\] Print help information for this script" + puts "-------------------------------------------------------------------------\n" + exit 0 +} + +if { $::argc > 0 } { + for {set i 0} {$i < $::argc} {incr i} { + set option [string trim [lindex $::argv $i]] + switch -regexp -- $option { + "--origin_dir" { incr i; set origin_dir [lindex $::argv $i] } + "--project_name" { incr i; set _xil_proj_name_ [lindex $::argv $i] } + "--help" { print_help } + default { + if { [regexp {^-} $option] } { + puts "ERROR: Unknown option '$option' specified, please type '$script_file -tclargs --help' for usage info.\n" + return 1 + } + } + } + } +} + +# Set the directory path for the original project from where this script was exported +set orig_proj_dir "[file normalize "$origin_dir/lower_machine"]" + +# Check for paths and files needed for project creation +set validate_required 0 +if { $validate_required } { + if { [checkRequiredFiles $origin_dir] } { + puts "Tcl file $script_file is valid. All files required for project creation is accesable. " + } else { + puts "Tcl file $script_file is not valid. Not all files required for project creation is accesable. " + return + } +} + +# Create project +create_project ${_xil_proj_name_} $origin_dir/${_xil_proj_name_} -part xc7z010clg400-1 + +# Set the directory path for the new project +set proj_dir [get_property directory [current_project]] + +# Set project properties +set obj [current_project] +set_property -name "default_lib" -value "xil_defaultlib" -objects $obj +set_property -name "enable_resource_estimation" -value "0" -objects $obj +set_property -name "enable_vhdl_2008" -value "1" -objects $obj +set_property -name "ip_cache_permissions" -value "read write" -objects $obj +set_property -name "ip_output_repo" -value "$proj_dir/${_xil_proj_name_}.cache/ip" -objects $obj +set_property -name "mem.enable_memory_map_generation" -value "1" -objects $obj +set_property -name "part" -value "xc7z010clg400-1" -objects $obj +set_property -name "revised_directory_structure" -value "1" -objects $obj +set_property -name "sim.central_dir" -value "$proj_dir/${_xil_proj_name_}.ip_user_files" -objects $obj +set_property -name "sim.ip.auto_export_scripts" -value "1" -objects $obj +set_property -name "simulator_language" -value "Mixed" -objects $obj +set_property -name "webtalk.activehdl_export_sim" -value "1" -objects $obj +set_property -name "webtalk.modelsim_export_sim" -value "1" -objects $obj +set_property -name "webtalk.questa_export_sim" -value "1" -objects $obj +set_property -name "webtalk.riviera_export_sim" -value "1" -objects $obj +set_property -name "webtalk.vcs_export_sim" -value "1" -objects $obj +set_property -name "webtalk.xcelium_export_sim" -value "1" -objects $obj +set_property -name "webtalk.xsim_export_sim" -value "1" -objects $obj +set_property -name "xpm_libraries" -value "XPM_CDC XPM_MEMORY" -objects $obj + +# Create 'sources_1' fileset (if not found) +if {[string equal [get_filesets -quiet sources_1] ""]} { + create_fileset -srcset sources_1 +} + +# Set IP repository paths +set obj [get_filesets sources_1] +if { $obj != {} } { + set_property "ip_repo_paths" "[file normalize "$origin_dir/ip_repo"]" $obj + + # Rebuild user ip_repo's index before adding any source files + update_ip_catalog -rebuild +} + +# Create block design +source $origin_dir/bd/system.tcl + +# Generate the wrapper +make_wrapper -files [get_files system.bd] -top -import + + +# Set 'sources_1' fileset file properties for local files +set file "system/system.bd" +set file_obj [get_files -of_objects [get_filesets sources_1] [list "*$file"]] +set_property -name "registered_with_manager" -value "1" -objects $file_obj + + +# Set 'sources_1' fileset properties +set obj [get_filesets sources_1] +set_property -name "top" -value "system_wrapper" -objects $obj + +# Create 'constrs_1' fileset (if not found) +if {[string equal [get_filesets -quiet constrs_1] ""]} { + create_fileset -constrset constrs_1 +} + +# Set 'constrs_1' fileset object +set obj [get_filesets constrs_1] + +# Add/Import constrs file and set constrs file properties +set file "[file normalize "$origin_dir/cstr/lower_machine.xdc"]" +set file_added [add_files -norecurse -fileset $obj [list $file]] +set file "$origin_dir/cstr/lower_machine.xdc" +set file [file normalize $file] +set file_obj [get_files -of_objects [get_filesets constrs_1] [list "*$file"]] +set_property -name "file_type" -value "XDC" -objects $file_obj + +# Set 'constrs_1' fileset properties +set obj [get_filesets constrs_1] +set_property -name "target_part" -value "xc7z010clg400-1" -objects $obj + +# Create 'sim_1' fileset (if not found) +if {[string equal [get_filesets -quiet sim_1] ""]} { + create_fileset -simset sim_1 +} + +# Set 'sim_1' fileset object +set obj [get_filesets sim_1] +# Empty (no sources present) + +# Set 'sim_1' fileset properties +set obj [get_filesets sim_1] +set_property -name "incremental" -value "0" -objects $obj +set_property -name "top" -value "system_wrapper" -objects $obj +set_property -name "top_lib" -value "xil_defaultlib" -objects $obj + +# Set 'utils_1' fileset object +set obj [get_filesets utils_1] +# Empty (no sources present) + +# Set 'utils_1' fileset properties +set obj [get_filesets utils_1] + +set idrFlowPropertiesConstraints "" +catch { + set idrFlowPropertiesConstraints [get_param runs.disableIDRFlowPropertyConstraints] + set_param runs.disableIDRFlowPropertyConstraints 1 +} + +# Create 'synth_1' run (if not found) +if {[string equal [get_runs -quiet synth_1] ""]} { + create_run -name synth_1 -part xc7z010clg400-1 -flow {Vivado Synthesis 2022} -strategy "Flow_PerfOptimized_high" -report_strategy {No Reports} -constrset constrs_1 +} else { + set_property strategy "Flow_PerfOptimized_high" [get_runs synth_1] + set_property flow "Vivado Synthesis 2022" [get_runs synth_1] +} +set obj [get_runs synth_1] +set_property set_report_strategy_name 1 $obj +set_property report_strategy {Vivado Synthesis Default Reports} $obj +set_property set_report_strategy_name 0 $obj +# Create 'synth_1_synth_report_utilization_0' report (if not found) +if { [ string equal [get_report_configs -of_objects [get_runs synth_1] synth_1_synth_report_utilization_0] "" ] } { + create_report_config -report_name synth_1_synth_report_utilization_0 -report_type report_utilization:1.0 -steps synth_design -runs synth_1 +} +set obj [get_report_configs -of_objects [get_runs synth_1] synth_1_synth_report_utilization_0] +if { $obj != "" } { + +} +set obj [get_runs synth_1] +set_property -name "part" -value "xc7z010clg400-1" -objects $obj +set_property -name "strategy" -value "Flow_PerfOptimized_high" -objects $obj +set_property -name "steps.synth_design.args.directive" -value "PerformanceOptimized" -objects $obj +set_property -name "steps.synth_design.args.fsm_extraction" -value "one_hot" -objects $obj +set_property -name "steps.synth_design.args.keep_equivalent_registers" -value "1" -objects $obj +set_property -name "steps.synth_design.args.resource_sharing" -value "off" -objects $obj +set_property -name "steps.synth_design.args.no_lc" -value "1" -objects $obj +set_property -name "steps.synth_design.args.shreg_min_size" -value "5" -objects $obj + +# set the current synth run +current_run -synthesis [get_runs synth_1] + +# Create 'impl_1' run (if not found) +if {[string equal [get_runs -quiet impl_1] ""]} { + create_run -name impl_1 -part xc7z010clg400-1 -flow {Vivado Implementation 2022} -strategy "Performance_ExtraTimingOpt" -report_strategy {No Reports} -constrset constrs_1 -parent_run synth_1 +} else { + set_property strategy "Performance_ExtraTimingOpt" [get_runs impl_1] + set_property flow "Vivado Implementation 2022" [get_runs impl_1] +} +set obj [get_runs impl_1] +set_property set_report_strategy_name 1 $obj +set_property report_strategy {Vivado Implementation Default Reports} $obj +set_property set_report_strategy_name 0 $obj +# Create 'impl_1_init_report_timing_summary_0' report (if not found) +if { [ string equal [get_report_configs -of_objects [get_runs impl_1] impl_1_init_report_timing_summary_0] "" ] } { + create_report_config -report_name impl_1_init_report_timing_summary_0 -report_type report_timing_summary:1.0 -steps init_design -runs impl_1 +} +set obj [get_report_configs -of_objects [get_runs impl_1] impl_1_init_report_timing_summary_0] +if { $obj != "" } { +set_property -name "is_enabled" -value "0" -objects $obj +set_property -name "options.max_paths" -value "10" -objects $obj +set_property -name "options.report_unconstrained" -value "1" -objects $obj + +} +# Create 'impl_1_opt_report_drc_0' report (if not found) +if { [ string equal [get_report_configs -of_objects [get_runs impl_1] impl_1_opt_report_drc_0] "" ] } { + create_report_config -report_name impl_1_opt_report_drc_0 -report_type report_drc:1.0 -steps opt_design -runs impl_1 +} +set obj [get_report_configs -of_objects [get_runs impl_1] impl_1_opt_report_drc_0] +if { $obj != "" } { + +} +# Create 'impl_1_opt_report_timing_summary_0' report (if not found) +if { [ string equal [get_report_configs -of_objects [get_runs impl_1] impl_1_opt_report_timing_summary_0] "" ] } { + create_report_config -report_name impl_1_opt_report_timing_summary_0 -report_type report_timing_summary:1.0 -steps opt_design -runs impl_1 +} +set obj [get_report_configs -of_objects [get_runs impl_1] impl_1_opt_report_timing_summary_0] +if { $obj != "" } { +set_property -name "is_enabled" -value "0" -objects $obj +set_property -name "options.max_paths" -value "10" -objects $obj +set_property -name "options.report_unconstrained" -value "1" -objects $obj + +} +# Create 'impl_1_power_opt_report_timing_summary_0' report (if not found) +if { [ string equal [get_report_configs -of_objects [get_runs impl_1] impl_1_power_opt_report_timing_summary_0] "" ] } { + create_report_config -report_name impl_1_power_opt_report_timing_summary_0 -report_type report_timing_summary:1.0 -steps power_opt_design -runs impl_1 +} +set obj [get_report_configs -of_objects [get_runs impl_1] impl_1_power_opt_report_timing_summary_0] +if { $obj != "" } { +set_property -name "is_enabled" -value "0" -objects $obj +set_property -name "options.max_paths" -value "10" -objects $obj +set_property -name "options.report_unconstrained" -value "1" -objects $obj + +} +# Create 'impl_1_place_report_io_0' report (if not found) +if { [ string equal [get_report_configs -of_objects [get_runs impl_1] impl_1_place_report_io_0] "" ] } { + create_report_config -report_name impl_1_place_report_io_0 -report_type report_io:1.0 -steps place_design -runs impl_1 +} +set obj [get_report_configs -of_objects [get_runs impl_1] impl_1_place_report_io_0] +if { $obj != "" } { + +} +# Create 'impl_1_place_report_utilization_0' report (if not found) +if { [ string equal [get_report_configs -of_objects [get_runs impl_1] impl_1_place_report_utilization_0] "" ] } { + create_report_config -report_name impl_1_place_report_utilization_0 -report_type report_utilization:1.0 -steps place_design -runs impl_1 +} +set obj [get_report_configs -of_objects [get_runs impl_1] impl_1_place_report_utilization_0] +if { $obj != "" } { + +} +# Create 'impl_1_place_report_control_sets_0' report (if not found) +if { [ string equal [get_report_configs -of_objects [get_runs impl_1] impl_1_place_report_control_sets_0] "" ] } { + create_report_config -report_name impl_1_place_report_control_sets_0 -report_type report_control_sets:1.0 -steps place_design -runs impl_1 +} +set obj [get_report_configs -of_objects [get_runs impl_1] impl_1_place_report_control_sets_0] +if { $obj != "" } { +set_property -name "options.verbose" -value "1" -objects $obj + +} +# Create 'impl_1_place_report_incremental_reuse_0' report (if not found) +if { [ string equal [get_report_configs -of_objects [get_runs impl_1] impl_1_place_report_incremental_reuse_0] "" ] } { + create_report_config -report_name impl_1_place_report_incremental_reuse_0 -report_type report_incremental_reuse:1.0 -steps place_design -runs impl_1 +} +set obj [get_report_configs -of_objects [get_runs impl_1] impl_1_place_report_incremental_reuse_0] +if { $obj != "" } { +set_property -name "is_enabled" -value "0" -objects $obj + +} +# Create 'impl_1_place_report_incremental_reuse_1' report (if not found) +if { [ string equal [get_report_configs -of_objects [get_runs impl_1] impl_1_place_report_incremental_reuse_1] "" ] } { + create_report_config -report_name impl_1_place_report_incremental_reuse_1 -report_type report_incremental_reuse:1.0 -steps place_design -runs impl_1 +} +set obj [get_report_configs -of_objects [get_runs impl_1] impl_1_place_report_incremental_reuse_1] +if { $obj != "" } { +set_property -name "is_enabled" -value "0" -objects $obj + +} +# Create 'impl_1_place_report_timing_summary_0' report (if not found) +if { [ string equal [get_report_configs -of_objects [get_runs impl_1] impl_1_place_report_timing_summary_0] "" ] } { + create_report_config -report_name impl_1_place_report_timing_summary_0 -report_type report_timing_summary:1.0 -steps place_design -runs impl_1 +} +set obj [get_report_configs -of_objects [get_runs impl_1] impl_1_place_report_timing_summary_0] +if { $obj != "" } { +set_property -name "is_enabled" -value "0" -objects $obj +set_property -name "options.max_paths" -value "10" -objects $obj +set_property -name "options.report_unconstrained" -value "1" -objects $obj + +} +# Create 'impl_1_post_place_power_opt_report_timing_summary_0' report (if not found) +if { [ string equal [get_report_configs -of_objects [get_runs impl_1] impl_1_post_place_power_opt_report_timing_summary_0] "" ] } { + create_report_config -report_name impl_1_post_place_power_opt_report_timing_summary_0 -report_type report_timing_summary:1.0 -steps post_place_power_opt_design -runs impl_1 +} +set obj [get_report_configs -of_objects [get_runs impl_1] impl_1_post_place_power_opt_report_timing_summary_0] +if { $obj != "" } { +set_property -name "is_enabled" -value "0" -objects $obj +set_property -name "options.max_paths" -value "10" -objects $obj +set_property -name "options.report_unconstrained" -value "1" -objects $obj + +} +# Create 'impl_1_phys_opt_report_timing_summary_0' report (if not found) +if { [ string equal [get_report_configs -of_objects [get_runs impl_1] impl_1_phys_opt_report_timing_summary_0] "" ] } { + create_report_config -report_name impl_1_phys_opt_report_timing_summary_0 -report_type report_timing_summary:1.0 -steps phys_opt_design -runs impl_1 +} +set obj [get_report_configs -of_objects [get_runs impl_1] impl_1_phys_opt_report_timing_summary_0] +if { $obj != "" } { +set_property -name "is_enabled" -value "0" -objects $obj +set_property -name "options.max_paths" -value "10" -objects $obj +set_property -name "options.report_unconstrained" -value "1" -objects $obj + +} +# Create 'impl_1_route_report_drc_0' report (if not found) +if { [ string equal [get_report_configs -of_objects [get_runs impl_1] impl_1_route_report_drc_0] "" ] } { + create_report_config -report_name impl_1_route_report_drc_0 -report_type report_drc:1.0 -steps route_design -runs impl_1 +} +set obj [get_report_configs -of_objects [get_runs impl_1] impl_1_route_report_drc_0] +if { $obj != "" } { + +} +# Create 'impl_1_route_report_methodology_0' report (if not found) +if { [ string equal [get_report_configs -of_objects [get_runs impl_1] impl_1_route_report_methodology_0] "" ] } { + create_report_config -report_name impl_1_route_report_methodology_0 -report_type report_methodology:1.0 -steps route_design -runs impl_1 +} +set obj [get_report_configs -of_objects [get_runs impl_1] impl_1_route_report_methodology_0] +if { $obj != "" } { + +} +# Create 'impl_1_route_report_power_0' report (if not found) +if { [ string equal [get_report_configs -of_objects [get_runs impl_1] impl_1_route_report_power_0] "" ] } { + create_report_config -report_name impl_1_route_report_power_0 -report_type report_power:1.0 -steps route_design -runs impl_1 +} +set obj [get_report_configs -of_objects [get_runs impl_1] impl_1_route_report_power_0] +if { $obj != "" } { + +} +# Create 'impl_1_route_report_route_status_0' report (if not found) +if { [ string equal [get_report_configs -of_objects [get_runs impl_1] impl_1_route_report_route_status_0] "" ] } { + create_report_config -report_name impl_1_route_report_route_status_0 -report_type report_route_status:1.0 -steps route_design -runs impl_1 +} +set obj [get_report_configs -of_objects [get_runs impl_1] impl_1_route_report_route_status_0] +if { $obj != "" } { + +} +# Create 'impl_1_route_report_timing_summary_0' report (if not found) +if { [ string equal [get_report_configs -of_objects [get_runs impl_1] impl_1_route_report_timing_summary_0] "" ] } { + create_report_config -report_name impl_1_route_report_timing_summary_0 -report_type report_timing_summary:1.0 -steps route_design -runs impl_1 +} +set obj [get_report_configs -of_objects [get_runs impl_1] impl_1_route_report_timing_summary_0] +if { $obj != "" } { +set_property -name "options.max_paths" -value "10" -objects $obj +set_property -name "options.report_unconstrained" -value "1" -objects $obj + +} +# Create 'impl_1_route_report_incremental_reuse_0' report (if not found) +if { [ string equal [get_report_configs -of_objects [get_runs impl_1] impl_1_route_report_incremental_reuse_0] "" ] } { + create_report_config -report_name impl_1_route_report_incremental_reuse_0 -report_type report_incremental_reuse:1.0 -steps route_design -runs impl_1 +} +set obj [get_report_configs -of_objects [get_runs impl_1] impl_1_route_report_incremental_reuse_0] +if { $obj != "" } { + +} +# Create 'impl_1_route_report_clock_utilization_0' report (if not found) +if { [ string equal [get_report_configs -of_objects [get_runs impl_1] impl_1_route_report_clock_utilization_0] "" ] } { + create_report_config -report_name impl_1_route_report_clock_utilization_0 -report_type report_clock_utilization:1.0 -steps route_design -runs impl_1 +} +set obj [get_report_configs -of_objects [get_runs impl_1] impl_1_route_report_clock_utilization_0] +if { $obj != "" } { + +} +# Create 'impl_1_route_report_bus_skew_0' report (if not found) +if { [ string equal [get_report_configs -of_objects [get_runs impl_1] impl_1_route_report_bus_skew_0] "" ] } { + create_report_config -report_name impl_1_route_report_bus_skew_0 -report_type report_bus_skew:1.1 -steps route_design -runs impl_1 +} +set obj [get_report_configs -of_objects [get_runs impl_1] impl_1_route_report_bus_skew_0] +if { $obj != "" } { +set_property -name "options.warn_on_violation" -value "1" -objects $obj + +} +# Create 'impl_1_post_route_phys_opt_report_timing_summary_0' report (if not found) +if { [ string equal [get_report_configs -of_objects [get_runs impl_1] impl_1_post_route_phys_opt_report_timing_summary_0] "" ] } { + create_report_config -report_name impl_1_post_route_phys_opt_report_timing_summary_0 -report_type report_timing_summary:1.0 -steps post_route_phys_opt_design -runs impl_1 +} +set obj [get_report_configs -of_objects [get_runs impl_1] impl_1_post_route_phys_opt_report_timing_summary_0] +if { $obj != "" } { +set_property -name "options.max_paths" -value "10" -objects $obj +set_property -name "options.report_unconstrained" -value "1" -objects $obj +set_property -name "options.warn_on_violation" -value "1" -objects $obj + +} +# Create 'impl_1_post_route_phys_opt_report_bus_skew_0' report (if not found) +if { [ string equal [get_report_configs -of_objects [get_runs impl_1] impl_1_post_route_phys_opt_report_bus_skew_0] "" ] } { + create_report_config -report_name impl_1_post_route_phys_opt_report_bus_skew_0 -report_type report_bus_skew:1.1 -steps post_route_phys_opt_design -runs impl_1 +} +set obj [get_report_configs -of_objects [get_runs impl_1] impl_1_post_route_phys_opt_report_bus_skew_0] +if { $obj != "" } { +set_property -name "options.warn_on_violation" -value "1" -objects $obj + +} +set obj [get_runs impl_1] +set_property -name "part" -value "xc7z010clg400-1" -objects $obj +set_property -name "strategy" -value "Performance_ExtraTimingOpt" -objects $obj +set_property -name "steps.place_design.args.directive" -value "ExtraTimingOpt" -objects $obj +set_property -name "steps.phys_opt_design.args.directive" -value "Explore" -objects $obj +set_property -name "steps.route_design.args.directive" -value "NoTimingRelaxation" -objects $obj +set_property -name "steps.write_bitstream.args.readback_file" -value "0" -objects $obj +set_property -name "steps.write_bitstream.args.verbose" -value "0" -objects $obj + +# set the current impl run +current_run -implementation [get_runs impl_1] +catch { + if { $idrFlowPropertiesConstraints != {} } { + set_param runs.disableIDRFlowPropertyConstraints $idrFlowPropertiesConstraints + } +} + +puts "INFO: Project created:${_xil_proj_name_}" +# Create 'drc_1' gadget (if not found) +if {[string equal [get_dashboard_gadgets [ list "drc_1" ] ] ""]} { +create_dashboard_gadget -name {drc_1} -type drc +} +set obj [get_dashboard_gadgets [ list "drc_1" ] ] +set_property -name "reports" -value "impl_1#impl_1_route_report_drc_0" -objects $obj + +# Create 'methodology_1' gadget (if not found) +if {[string equal [get_dashboard_gadgets [ list "methodology_1" ] ] ""]} { +create_dashboard_gadget -name {methodology_1} -type methodology +} +set obj [get_dashboard_gadgets [ list "methodology_1" ] ] +set_property -name "reports" -value "impl_1#impl_1_route_report_methodology_0" -objects $obj + +# Create 'power_1' gadget (if not found) +if {[string equal [get_dashboard_gadgets [ list "power_1" ] ] ""]} { +create_dashboard_gadget -name {power_1} -type power +} +set obj [get_dashboard_gadgets [ list "power_1" ] ] +set_property -name "reports" -value "impl_1#impl_1_route_report_power_0" -objects $obj + +# Create 'timing_1' gadget (if not found) +if {[string equal [get_dashboard_gadgets [ list "timing_1" ] ] ""]} { +create_dashboard_gadget -name {timing_1} -type timing +} +set obj [get_dashboard_gadgets [ list "timing_1" ] ] +set_property -name "reports" -value "impl_1#impl_1_route_report_timing_summary_0" -objects $obj + +# Create 'utilization_1' gadget (if not found) +if {[string equal [get_dashboard_gadgets [ list "utilization_1" ] ] ""]} { +create_dashboard_gadget -name {utilization_1} -type utilization +} +set obj [get_dashboard_gadgets [ list "utilization_1" ] ] +set_property -name "reports" -value "synth_1#synth_1_synth_report_utilization_0" -objects $obj +set_property -name "run.step" -value "synth_design" -objects $obj +set_property -name "run.type" -value "synthesis" -objects $obj + +# Create 'utilization_2' gadget (if not found) +if {[string equal [get_dashboard_gadgets [ list "utilization_2" ] ] ""]} { +create_dashboard_gadget -name {utilization_2} -type utilization +} +set obj [get_dashboard_gadgets [ list "utilization_2" ] ] +set_property -name "reports" -value "impl_1#impl_1_place_report_utilization_0" -objects $obj + +move_dashboard_gadget -name {utilization_1} -row 0 -col 0 +move_dashboard_gadget -name {power_1} -row 1 -col 0 +move_dashboard_gadget -name {drc_1} -row 2 -col 0 +move_dashboard_gadget -name {timing_1} -row 0 -col 1 +move_dashboard_gadget -name {utilization_2} -row 1 -col 1 +move_dashboard_gadget -name {methodology_1} -row 2 -col 1 diff --git a/hardware/pl_platform/version b/hardware/pl_platform/version index b123147..ea710ab 100644 --- a/hardware/pl_platform/version +++ b/hardware/pl_platform/version @@ -1 +1 @@ -1.1 \ No newline at end of file +1.2 \ No newline at end of file diff --git a/script/loadfifo.sh b/script/loadfifo.sh deleted file mode 100644 index cb77206..0000000 --- a/script/loadfifo.sh +++ /dev/null @@ -1,3 +0,0 @@ -#!/bin/sh - -modprobe fifo \ No newline at end of file diff --git a/script/version b/script/version index 9f8e9b6..b123147 100644 --- a/script/version +++ b/script/version @@ -1 +1 @@ -1.0 \ No newline at end of file +1.1 \ No newline at end of file diff --git a/source/linux_driver/fifo.c b/source/linux_driver/fifo.c deleted file mode 100644 index 703219d..0000000 --- a/source/linux_driver/fifo.c +++ /dev/null @@ -1,354 +0,0 @@ -#include -#include -#include -#include -#include -#include -#include -#include -#include -#include -#include - -#define FIFO_CNT 1 /* 设备号个数 */ -#define FIFO_NAME "fifo" /* 名字 */ -#define FIFO_CMD_FUNCTION_CLEAR 1 -#define FIFO_CMD_FUNCTION_PADDING 2 -#define FIFO_CMD_GET_EMPTYCOUNT 3 - -/* - * 相关寄存器地址定义 - */ -#define FIFO_REG_BASE 0x43C00000 -#define FIFO_REG_0_OFFSET 0x00000000 -#define FIFO_REG_1_OFFSET 0x00000004 -#define FIFO_REG_2_OFFSET 0x00000008 -#define FIFO_REG_3_OFFSET 0x0000000C -#define FIFO_REG_4_OFFSET 0x00000010 -#define FIFO_REG_5_OFFSET 0x00000014 -#define FIFO_REG_6_OFFSET 0x00000018 -#define FIFO_REG_7_OFFSET 0x0000001C -#define FIFO_REG_8_OFFSET 0x00000020 -#define FIFO_REG_9_OFFSET 0x00000024 -#define FIFO_REG_10_OFFSET 0x00000028 -#define FIFO_REG_11_OFFSET 0x0000002C -#define FIFO_REG_12_OFFSET 0x00000030 // {16'b0, almost_empty, empty, almost_full, full, data_count[11:0]}; -#define FIFO_REG_13_OFFSET 0x00000034 -#define FIFO_REG_14_OFFSET 0x00000038 - -#define FIFO_CR_CLR_MASK ((u32)(1 << 1)) // 清空队列 (Clear) 对该位写入1,队列将清空,同时队列输出为全0。注意:不要写入除1以外的任何值。 -#define FIFO_CR_WS_MASK ((u32)(1 << 0)) // 写入同步 (Write Synchronization) 对该位写入1,FIFO_DATx的数据按字节小端序进入队列。 注意:不要写入除1以外的任何值。 - -#define FIFO_SR_VLD_MASK ((u32)(1 << 16)) // 数据输出有效标志 (Valid) 0: 当前无有效输出,输出保持上一状态 1: 当前队列正在输出有效数据 -#define FIFO_SR_AMEM_MASK ((u32)(1 << 15)) // 队列将空标志 (Almost Empty) 0: 队列没有被读空 1: 队列在一个读时钟周期后会被读空 -#define FIFO_SR_EM_MASK ((u32)(1 << 14)) // 队列空标志 (Empty) 0: 队列中存在有效数据,没有被读空 1: 队列中已经没有有效数据 -#define FIFO_SR_AMFU_MASK ((u32)(1 << 13)) // 队列将满标志 (Almost Full) 0: 队列没有被写满 1: 队列在一个写时钟周期后会被写满 -#define FIFO_SR_FU_MASK ((u32)(1 << 12)) // 队列满标志 (Almost Full) 0: 队列中的有效数据小于FIFO数据深度 1: 队列中的有效数据达到FIFO数据深度 -#define FIFO_SR_CNT_MASK ((u32)(0xFFF << 0)) // 队列数据数量 (Data Count) 该值指示队列中的数据数量 注意:一个数据为384位宽 - -#define FIFO_ECR_CNT_MASK ((u32)0xFFFFFFFF) // 队列空读取累计次数 - -/* 映射后的寄存器虚拟地址指针 */ -static void __iomem *fifo_dat0_addr; -static void __iomem *fifo_dat1_addr; -static void __iomem *fifo_dat2_addr; -static void __iomem *fifo_dat3_addr; -static void __iomem *fifo_dat4_addr; -static void __iomem *fifo_dat5_addr; -static void __iomem *fifo_dat6_addr; -static void __iomem *fifo_dat7_addr; -static void __iomem *fifo_dat8_addr; -static void __iomem *fifo_dat9_addr; -static void __iomem *fifo_dat10_addr; -static void __iomem *fifo_dat11_addr; -static void __iomem *fifo_sr_addr; -static void __iomem *fifo_ecr_addr; -static void __iomem *fifo_cr_addr; - -/* fifo设备结构体 */ -struct fifo_dev -{ - dev_t devid; /* 设备号 */ - struct cdev cdev; /* cdev */ - struct class *class; /* 类 */ - struct device *device; /* 设备 */ - int major; /* 主设备号 */ - int minor; /* 次设备号 */ -}; - -static struct fifo_dev fifo; /* led设备 */ - -/* - * @description : 打开设备 - * @param – inode : 传递给驱动的inode - * @param - filp : 设备文件,file结构体有个叫做private_data的成员变量 - * 一般在open的时候将private_data指向设备结构体。 - * @return : 0 成功;其他 失败 - */ -static int fifo_open(struct inode *inode, struct file *filp) -{ - return 0; -} - -/* - * @description : 从设备读取数据 - * @param - filp : 要打开的设备文件(文件描述符) - * @param - buf : 返回给用户空间的数据缓冲区 - * @param - cnt : 要读取的数据长度 - * @param - offt : 相对于文件首地址的偏移 - * @return : 读取的字节数,如果为负值,表示读取失败 - */ -static ssize_t fifo_read(struct file *filp, char __user *buf, size_t cnt, loff_t *offt) -{ - u32 data = readl(fifo_sr_addr) & FIFO_SR_CNT_MASK; - copy_to_user(buf, &data, 4); - return cnt; -} - -static u32 kern_buf_u32[8 * 4096]; - -/* - * @description : 向设备写数据 - * @param - filp : 设备文件,表示打开的文件描述符 - * @param - buf : 要写给设备写入的数据 - * @param - cnt : 要写入的数据长度 - * @param - offt : 相对于文件首地址的偏移 - * @return : 写入的字节数,如果为负值,表示写入失败 - */ -static ssize_t fifo_write(struct file *filp, const char __user *buf, size_t cnt, loff_t *offt) -{ - int ret; - int i; - - if (cnt % 32 != 0 || cnt > sizeof(kern_buf_u32)) - { - printk(KERN_ERR "cnt error, cnt=%d, sizeof=%d\r\n", cnt, (u32)sizeof(kern_buf_u32)); - return -1; - } - - ret = copy_from_user(kern_buf_u32, buf, cnt); // 得到应用层传递过来的数据 - if (ret < 0) - { - printk(KERN_ERR "kernel write failed!\r\n"); - return -EFAULT; - } - - for (i = 0; i < (cnt / sizeof(u32)); i += 8) - { - writel(kern_buf_u32[i], fifo_dat0_addr); - writel(kern_buf_u32[i + 1], fifo_dat1_addr); - writel(kern_buf_u32[i + 2], fifo_dat2_addr); - writel(kern_buf_u32[i + 3], fifo_dat3_addr); - writel(kern_buf_u32[i + 4], fifo_dat4_addr); - writel(kern_buf_u32[i + 5], fifo_dat5_addr); - writel(kern_buf_u32[i + 6], fifo_dat6_addr); - writel(kern_buf_u32[i + 7], fifo_dat7_addr); - writel(0, fifo_dat8_addr); - writel(0, fifo_dat9_addr); - writel(0, fifo_dat10_addr); - writel(0, fifo_dat11_addr); - writel(FIFO_CR_WS_MASK, fifo_cr_addr); - } - - return cnt; -} - -/* - * @description : 关闭/释放设备 - * @param – filp : 要关闭的设备文件(文件描述符) - * @return : 0 成功;其他 失败 - */ -static int fifo_release(struct inode *inode, struct file *filp) -{ - return 0; -} - -static long fifo_ioctl(struct file *fp, unsigned int cmd, unsigned long tmp) -{ - if (_IOC_TYPE(cmd) != 'D') - { - printk(KERN_ERR "IOC_TYPE or IOC_WRITE error: IOC_TYPE=%c, IOC_WRITE=%d\r\n", _IOC_TYPE(cmd), _IOC_DIR(cmd)); - return -EINVAL; - } - if (_IOC_NR(cmd) == FIFO_CMD_GET_EMPTYCOUNT) - { - u32 empty_count = readl(fifo_ecr_addr) & FIFO_ECR_CNT_MASK; - printk("%d\r\n", empty_count); - if (copy_to_user((u32 *)tmp, &empty_count, 4) < 0) - { - printk(KERN_ERR "get empty count error\r\n"); - return -EINVAL; - } - } - else if (_IOC_NR(cmd) == FIFO_CMD_FUNCTION_CLEAR) - { - // 清空队列 - writel(FIFO_CR_CLR_MASK, fifo_cr_addr); - } - else if (_IOC_NR(cmd) == FIFO_CMD_FUNCTION_PADDING) - { - // 对队列中添加tmp个数的0元素 - int i; - for (i = 0; i < tmp; i ++) - { - writel((u32)0, fifo_dat0_addr); - writel((u32)0, fifo_dat1_addr); - writel((u32)0, fifo_dat2_addr); - writel((u32)0, fifo_dat3_addr); - writel((u32)0, fifo_dat4_addr); - writel((u32)0, fifo_dat5_addr); - writel((u32)0, fifo_dat6_addr); - writel((u32)0, fifo_dat7_addr); - writel((u32)0, fifo_dat8_addr); - writel((u32)0, fifo_dat9_addr); - writel((u32)0, fifo_dat10_addr); - writel((u32)0, fifo_dat11_addr); - writel(FIFO_CR_WS_MASK, fifo_cr_addr); - } - } - return 0; -} - -/* 设备操作函数 */ -static struct file_operations fifo_fops = { - .owner = THIS_MODULE, - .open = fifo_open, - .read = fifo_read, - .write = fifo_write, - .release = fifo_release, - .unlocked_ioctl = fifo_ioctl, -}; - -static int __init fifo_init(void) -{ - int ret; - /* 寄存器地址映射 */ - fifo_dat0_addr = ioremap(FIFO_REG_BASE + FIFO_REG_0_OFFSET, 4); - fifo_dat1_addr = ioremap(FIFO_REG_BASE + FIFO_REG_1_OFFSET, 4); - fifo_dat2_addr = ioremap(FIFO_REG_BASE + FIFO_REG_2_OFFSET, 4); - fifo_dat3_addr = ioremap(FIFO_REG_BASE + FIFO_REG_3_OFFSET, 4); - fifo_dat4_addr = ioremap(FIFO_REG_BASE + FIFO_REG_4_OFFSET, 4); - fifo_dat5_addr = ioremap(FIFO_REG_BASE + FIFO_REG_5_OFFSET, 4); - fifo_dat6_addr = ioremap(FIFO_REG_BASE + FIFO_REG_6_OFFSET, 4); - fifo_dat7_addr = ioremap(FIFO_REG_BASE + FIFO_REG_7_OFFSET, 4); - fifo_dat8_addr = ioremap(FIFO_REG_BASE + FIFO_REG_8_OFFSET, 4); - fifo_dat9_addr = ioremap(FIFO_REG_BASE + FIFO_REG_9_OFFSET, 4); - fifo_dat10_addr = ioremap(FIFO_REG_BASE + FIFO_REG_10_OFFSET, 4); - fifo_dat11_addr = ioremap(FIFO_REG_BASE + FIFO_REG_11_OFFSET, 4); - fifo_sr_addr = ioremap(FIFO_REG_BASE + FIFO_REG_12_OFFSET, 4); - fifo_ecr_addr = ioremap(FIFO_REG_BASE + FIFO_REG_13_OFFSET, 4); - fifo_cr_addr = ioremap(FIFO_REG_BASE + FIFO_REG_14_OFFSET, 4); - - /* 注册字符设备驱动 */ - //(1)创建设备号 - if (fifo.major) - { - fifo.devid = MKDEV(fifo.major, 0); - ret = register_chrdev_region(fifo.devid, FIFO_CNT, FIFO_NAME); - if (ret) - goto FAIL_REGISTER_CHR_DEV; - } - else - { - ret = alloc_chrdev_region(&fifo.devid, 0, FIFO_CNT, FIFO_NAME); - if (ret) - goto FAIL_REGISTER_CHR_DEV; - fifo.major = MAJOR(fifo.devid); - fifo.minor = MINOR(fifo.devid); - } - - //(2)初始化cdev - fifo.cdev.owner = THIS_MODULE; - cdev_init(&fifo.cdev, &fifo_fops); - - //(3)添加cdev - ret = cdev_add(&fifo.cdev, fifo.devid, FIFO_CNT); - if (ret) - goto FAIL_ADD_CDEV; - - //(4)创建类 - fifo.class = class_create(THIS_MODULE, FIFO_NAME); - if (IS_ERR(fifo.class)) - { - ret = PTR_ERR(fifo.class); - goto FAIL_CREATE_CLASS; - } - - //(5)创建设备 - fifo.device = device_create(fifo.class, NULL, fifo.devid, NULL, FIFO_NAME); - if (IS_ERR(fifo.device)) - { - ret = PTR_ERR(fifo.device); - goto FAIL_CREATE_DEV; - } - - return 0; - -FAIL_CREATE_DEV: - class_destroy(fifo.class); - -FAIL_CREATE_CLASS: - cdev_del(&fifo.cdev); - -FAIL_ADD_CDEV: - unregister_chrdev_region(fifo.devid, FIFO_CNT); - -FAIL_REGISTER_CHR_DEV: - iounmap(fifo_dat0_addr); - iounmap(fifo_dat1_addr); - iounmap(fifo_dat2_addr); - iounmap(fifo_dat3_addr); - iounmap(fifo_dat4_addr); - iounmap(fifo_dat5_addr); - iounmap(fifo_dat6_addr); - iounmap(fifo_dat7_addr); - iounmap(fifo_dat8_addr); - iounmap(fifo_dat9_addr); - iounmap(fifo_dat10_addr); - iounmap(fifo_dat11_addr); - iounmap(fifo_sr_addr); - iounmap(fifo_ecr_addr); - iounmap(fifo_cr_addr); - - return ret; -} - -static void __exit fifo_exit(void) -{ - - //(1)注销设备 - device_destroy(fifo.class, fifo.devid); - - //(2)注销类 - class_destroy(fifo.class); - - //(3)删除cdev - cdev_del(&fifo.cdev); - - //(4)注销设备号 - unregister_chrdev_region(fifo.devid, FIFO_CNT); - - //(5)取消内存映射 - iounmap(fifo_dat0_addr); - iounmap(fifo_dat1_addr); - iounmap(fifo_dat2_addr); - iounmap(fifo_dat3_addr); - iounmap(fifo_dat4_addr); - iounmap(fifo_dat5_addr); - iounmap(fifo_dat6_addr); - iounmap(fifo_dat7_addr); - iounmap(fifo_dat8_addr); - iounmap(fifo_dat9_addr); - iounmap(fifo_dat10_addr); - iounmap(fifo_dat11_addr); - iounmap(fifo_sr_addr); - iounmap(fifo_ecr_addr); - iounmap(fifo_cr_addr); -} - -/* 驱动模块入口和出口函数注册 */ -module_init(fifo_init); -module_exit(fifo_exit); -MODULE_AUTHOR("Dingkun"); -MODULE_DESCRIPTION("driver for hardware fifo in the platform"); -MODULE_LICENSE("GPL"); diff --git a/source/linux_driver/version b/source/linux_driver/version index 840ca8c..400122e 100644 --- a/source/linux_driver/version +++ b/source/linux_driver/version @@ -1 +1 @@ -1.4 \ No newline at end of file +1.5 \ No newline at end of file