Hardware components | ||||||
| × | 1 | ||||
Software apps and online services | ||||||
| ||||||
| ||||||
| ||||||
|
Inference at the edge
Existing solution for machine learning on edge device seems to rely on :
- the capturing of enough data from the edge device,
- a training performed on a powerful computer or in the cloud,
- an optimization phase of the resulting network and weights so it can perform well on the edge device,
- the necessity to transfer the neural network and weights to the edge device,
- and then the use of the device for inference.
If there is a change in the edge device or in its environment, a new training must be done and new weights loaded. This can be costly or impossible if no more high bandwidth transmission is available with the edge device.
Training at the edge
The idea for this project is to implement what is required to train the neural network directly on the device, with limited external bandwidth consumption.
Existing solution seems to not perform training directly on the edge.
A training on the edge allows to easily perform a new training of a device that have limited communication bandwidth available.
It also allows to deploy a device and perform its training in the fields, in the case when it is not possible to gather real environment data for training before the device is deployed.
How and what ?
Thanks to the PYNQ framework, we will be able to use a Jupyter Notebook to run PyTorch code directly on the Ultra96-V2 board.
We will implement the "Hello World" of machine learning, aka MNIST digit recognition.
The project will also show how to extend PyTorch to define a new Linear layer that will use the Zynq Ultrascale+ FPGA part to compute the neural network floating point matrix multiplication.
Executive summary
No time to loose ? Just want to try it yourself ? Ok, let's go :
- download the Ultra96-PYNQ image and flash it
- power the board and connect to it
- open a terminal and install PyTorch
- add the files of this project on your board, and play with the provided jupyter notebook
On this page :https://github.com/Avnet/Ultra96-PYNQ/releases/tag/v2.6.0
You will find :
- the link to download the image (ultra96v2_v2.6.0.zip) that must be written on the SD card (>= 16 GB) of the Ultra96-V2,
- and the explanations to do it (spoiler : use Etcher).
On this page :https://ultra96-pynq.readthedocs.io/en/latest/getting_started.html
You will find :
- this short video that explains what to connect where (this is for the Ultra96 board, for the Ultra96-V2, the power on button is SW4)
- The link to use to open a Jupyter Notebook on the device :http://192.168.3.1:9090 (if you have connected the board to your PC with an USB cable, password is xilinx)
- The link to access to the files on the device. On a linux PC, with an USB connection to the board, the link to type in your file explorer is :smb://192.168.3.1/xilinx/ (login is xilinx, password is xilinx, domain is XLNX)
- The fact that the Jupyter Notebook allow you to open a terminal as root on the device :New > Terminal
- Explanations for network configuration, but the easy path is to use an USB-Ethernet adapter, and to connect the board to your network through this ethernet connection.Type "ip addr" in the terminal to know the ip address of the board on your network. This way you can connect to the board with this address (and the USB cable to your PC is no more needed).
If you have an USB fan, use it below the board to keep it cool.
3. Install PyTorchOn this page :https://mathinf.eu/pytorch/arm64/
You will learn that you just have to use the information from the official PyTorch site.
For the configuration, just use : build nightly, os linux, package pip, language python, cuda none.
You will get the command that must be executed in a terminal window of the Ultra96-V2 board.
4. Add this project filesYou need to put the files of the project at the following place :
/home/xilinx/pynq/overlays/multaccum/multaccum.bit/home/xilinx/pynq/overlays/multaccum/multaccum.hwh/home/xilinx/jupyter_notebooks/myfolder/nn_training_accel.ipynb
This is the block design of the Vivado project used to create the PYNQ 'multaccum' overlay.
This is all there is for now. This is your turn to experiment with this now. Open the "nn_training_accel.ipynb" jupyter notebook and try all this by yourself.
With this design, I have measured a training speed of 11 ms per image. This is 11 minutes for one epoch on the 60 000 images of the training data set.
ConclusionThe computation is faster with the CPU, but this suppose the CPU has nothing else to do. The use of the FPGA is a way to allow the CPU to more easily perform other tasks during a training that will probably be continuous on an edge device monitoring and adapting to the evolution on its environment.
Next ?Complements that are not included by lack of time or because they are not finalized yet are :
- explanation of the 'multaccum' architecture
- presentation of another notebook with an autoencoder model
- presentation of another notebook with training done from the bottleneck of the autoencoder to obtain a certain accuracy with a training on less labeled data
- application of this on live webcam image
nn_training_accel.ipynb
Python{
"cells": [
{
"cell_type": "code",
"execution_count": 1,
"metadata": {},
"outputs": [],
"source": [
"import torch\n",
"import torch.nn as nn\n",
"import torch.nn.functional as F\n",
"import torchvision\n",
"\n",
"import matplotlib.pyplot as plt\n",
"import numpy as np"
]
},
{
"cell_type": "markdown",
"metadata": {},
"source": [
"# MNIST dataset"
]
},
{
"cell_type": "markdown",
"metadata": {},
"source": [
"The dataset is created as a way to access the data we will use for training.\n",
"\n",
"We define a transformation that will be applied on each of the image of the dataset when we query them. \n",
"This will ease the learning.\n",
"\n",
"This transformation will :\n",
"* convert the pixel to float values (instead of value between 0 and 255)\n",
"* normalize the value of the pixels (mean of 0, standard deviation of 1)"
]
},
{
"cell_type": "code",
"execution_count": 2,
"metadata": {},
"outputs": [],
"source": [
"transform = torchvision.transforms.Compose([\n",
" torchvision.transforms.ToTensor(),\n",
" torchvision.transforms.Normalize((0.1307,), (0.3081,))\n",
" ])"
]
},
{
"cell_type": "markdown",
"metadata": {},
"source": [
"We create a train and a test dataset."
]
},
{
"cell_type": "code",
"execution_count": 3,
"metadata": {},
"outputs": [],
"source": [
"train_dataset = torchvision.datasets.MNIST(\n",
" root=\"./torch_datasets\",\n",
" train=True,\n",
" transform=transform,\n",
" download=True\n",
")\n",
"\n",
"test_dataset = torchvision.datasets.MNIST(\n",
" root=\"./torch_datasets\",\n",
" train=False,\n",
" transform=transform,\n",
" download=True\n",
")"
]
},
{
"cell_type": "markdown",
"metadata": {},
"source": [
"# Data"
]
},
{
"cell_type": "markdown",
"metadata": {},
"source": [
"Let's play a bit with the content of these datasets."
]
},
{
"cell_type": "code",
"execution_count": 4,
"metadata": {},
"outputs": [
{
"data": {
"text/plain": [
"Dataset MNIST\n",
" Number of datapoints: 60000\n",
" Root location: ./torch_datasets\n",
" Split: Train\n",
" StandardTransform\n",
"Transform: Compose(\n",
" ToTensor()\n",
" Normalize(mean=(0.1307,), std=(0.3081,))\n",
" )"
]
},
"execution_count": 4,
"metadata": {},
"output_type": "execute_result"
}
],
"source": [
"train_dataset"
]
},
{
"cell_type": "code",
"execution_count": 5,
"metadata": {},
"outputs": [
{
"name": "stdout",
"output_type": "stream",
"text": [
"torch.Size([1, 28, 28]) 5\n"
]
},
{
"data": {
"text/plain": [
"<matplotlib.image.AxesImage at 0x7f5bd8fc88>"
]
},
"execution_count": 5,
"metadata": {},
"output_type": "execute_result"
},
{
"data": {
"image/png": "iVBORw0KGgoAAAANSUhEUgAAAP8AAAD8CAYAAAC4nHJkAAAABHNCSVQICAgIfAhkiAAAAAlwSFlzAAALEgAACxIB0t1+/AAAADl0RVh0U29mdHdhcmUAbWF0cGxvdGxpYiB2ZXJzaW9uIDIuMS4xLCBodHRwOi8vbWF0cGxvdGxpYi5vcmcvAOZPmwAADmtJREFUeJzt3W+sVPWdx/HPFwT/UFQIV3ulKF00ZgmJYEbYhI2iRLSbKvCgBmIQTQM+ANkmEBfhATxwE6PbdlVMk4slQFJpGyorJGYtGo1L3BgGJQiLbNVc6V0QLqFYqw9Q+O6De2hu8c5vhpkzc+byfb8ScmfO9/zmfDPczz0z85uZn7m7AMQzpOgGABSD8ANBEX4gKMIPBEX4gaAIPxAU4QeCIvxAUIQfCOqSVh5szJgxPn78+FYeEgilu7tbJ06csFr2bSj8ZnavpGclDZX0ors/ldp//PjxKpfLjRwSQEKpVKp537of9pvZUEkvSPqBpImS5pvZxHpvD0BrNfKcf6qkj9z9E3c/LenXkmbn0xaAZmsk/GMl/bHf9Z5s298ws8VmVjazcm9vbwOHA5CnRsI/0IsK3/p8sLt3uXvJ3UsdHR0NHA5AnhoJf4+kcf2uf0/SkcbaAdAqjYR/t6SbzOz7ZjZc0jxJ2/NpC0Cz1T3V5+7fmNlSSa+pb6pvg7sfyK0zAE3V0Dy/u78q6dWcegHQQry9FwiK8ANBEX4gKMIPBEX4gaAIPxAU4QeCIvxAUIQfCIrwA0ERfiAowg8ERfiBoAg/EBThB4Ii/EBQhB8IivADQRF+ICjCDwRF+IGgCD8QFOEHgiL8QFCEHwiK8ANBEX4gKMIPBEX4gaAaWqXXzLolfSHpjKRv3L2UR1PIz5kzZ5L1zz//vKnHX7duXcXaV199lRx76NChZP2FF15I1lesWFGxtmXLluTYyy67LFlfuXJlsr5mzZpkvR00FP7Mne5+IofbAdBCPOwHgmo0/C7p92a2x8wW59EQgNZo9GH/dHc/YmbXSNppZh+6+9v9d8j+KCyWpOuvv77BwwHIS0Nnfnc/kv08LmmbpKkD7NPl7iV3L3V0dDRyOAA5qjv8ZjbCzEaeuyxplqT9eTUGoLkaedh/raRtZnbudl5y9//MpSsATVd3+N39E0m35NjLRevw4cPJ+unTp5P1d955J1nftWtXxdqpU6eSY7du3ZqsF2ncuHHJ+mOPPZasb9u2rWJt5MiRybG33JL+1b7jjjuS9cGAqT4gKMIPBEX4gaAIPxAU4QeCIvxAUHl8qi+8999/P1m/6667kvVmf6y2XQ0dOjRZf/LJJ5P1ESNGJOsPPvhgxdp1112XHDtq1Khk/eabb07WBwPO/EBQhB8IivADQRF+ICjCDwRF+IGgCD8QFPP8ObjhhhuS9TFjxiTr7TzPP23atGS92nz4m2++WbE2fPjw5NgFCxYk62gMZ34gKMIPBEX4gaAIPxAU4QeCIvxAUIQfCIp5/hyMHj06WX/mmWeS9R07diTrU6ZMSdaXLVuWrKdMnjw5WX/99deT9Wqfqd+/v/I6Ls8991xyLJqLMz8QFOEHgiL8QFCEHwiK8ANBEX4gKMIPBFV1nt/MNkj6oaTj7j4p2zZa0m8kjZfULekBd/9T89oc3ObMmZOsV/te/2rLSe/bt69i7cUXX0yOXbFiRbJebR6/mkmTJlWsdXV1NXTbaEwtZ/6Nku49b9tKSW+4+02S3siuAxhEqobf3d+WdPK8zbMlbcoub5KUPrUBaDv1Pue/1t2PSlL285r8WgLQCk1/wc/MFptZ2czKvb29zT4cgBrVG/5jZtYpSdnP45V2dPcudy+5e6mjo6POwwHIW73h3y5pYXZ5oaRX8mkHQKtUDb+ZbZH035JuNrMeM/uxpKck3W1mf5B0d3YdwCBSdZ7f3edXKM3MuZewrrzyyobGX3XVVXWPrfY+gHnz5iXrQ4bwPrHBiv85ICjCDwRF+IGgCD8QFOEHgiL8QFB8dfdFYO3atRVre/bsSY596623kvVqX909a9asZB3tizM/EBThB4Ii/EBQhB8IivADQRF+ICjCDwTFPP9FIPX12uvXr0+OvfXWW5P1RYsWJet33nlnsl4qlSrWlixZkhxrZsk6GsOZHwiK8ANBEX4gKMIPBEX4gaAIPxAU4QeCYp7/IjdhwoRkfePGjcn6I488kqxv3ry57vqXX36ZHPvQQw8l652dnck60jjzA0ERfiAowg8ERfiBoAg/EBThB4Ii/EBQVef5zWyDpB9KOu7uk7JtayUtktSb7bbK3V9tVpNonrlz5ybrN954Y7K+fPnyZD31vf9PPPFEcuynn36arK9evTpZHzt2bLIeXS1n/o2S7h1g+8/dfXL2j+ADg0zV8Lv725JOtqAXAC3UyHP+pWa2z8w2mNmo3DoC0BL1hv8XkiZImizpqKSfVtrRzBabWdnMyr29vZV2A9BidYXf3Y+5+xl3PytpvaSpiX273L3k7qWOjo56+wSQs7rCb2b9P041V9L+fNoB0Cq1TPVtkTRD0hgz65G0RtIMM5ssySV1S3q0iT0CaAJz95YdrFQqeblcbtnx0HynTp1K1nfs2FGx9vDDDyfHVvvdnDlzZrK+c+fOZP1iVCqVVC6Xa1rwgHf4AUERfiAowg8ERfiBoAg/EBThB4Jiqg+FufTSS5P1r7/+OlkfNmxYsv7aa69VrM2YMSM5drBiqg9AVYQfCIrwA0ERfiAowg8ERfiBoAg/EBRLdCNp3759yfrWrVuT9d27d1esVZvHr2bixInJ+u23397Q7V/sOPMDQRF+ICjCDwRF+IGgCD8QFOEHgiL8QFDM81/kDh06lKw///zzyfrLL7+crH/22WcX3FOtLrkk/evZ2dmZrA8ZwrkthXsHCIrwA0ERfiAowg8ERfiBoAg/EBThB4KqOs9vZuMkbZb0XUlnJXW5+7NmNlrSbySNl9Qt6QF3/1PzWo2r2lz6Sy+9VLG2bt265Nju7u56WsrFbbfdlqyvXr06Wb///vvzbCecWs7830ha7u5/L+kfJC0xs4mSVkp6w91vkvRGdh3AIFE1/O5+1N3fyy5/IemgpLGSZkvalO22SdKcZjUJIH8X9JzfzMZLmiLpXUnXuvtRqe8PhKRr8m4OQPPUHH4z+46k30n6ibv/+QLGLTazspmVe3t76+kRQBPUFH4zG6a+4P/K3c990uOYmXVm9U5Jxwca6+5d7l5y91JHR0cePQPIQdXwm5lJ+qWkg+7+s36l7ZIWZpcXSnol//YANEstH+mdLmmBpA/MbG+2bZWkpyT91sx+LOmwpB81p8XB79ixY8n6gQMHkvWlS5cm6x9++OEF95SXadOmJeuPP/54xdrs2bOTY/lIbnNVDb+775JUab3vmfm2A6BV+NMKBEX4gaAIPxAU4QeCIvxAUIQfCIqv7q7RyZMnK9YeffTR5Ni9e/cm6x9//HFdPeVh+vTpyfry5cuT9XvuuSdZv/zyyy+4J7QGZ34gKMIPBEX4gaAIPxAU4QeCIvxAUIQfCCrMPP+7776brD/99NPJ+u7duyvWenp66uopL1dccUXF2rJly5Jjq3099ogRI+rqCe2PMz8QFOEHgiL8QFCEHwiK8ANBEX4gKMIPBBVmnn/btm0N1RsxceLEZP2+++5L1ocOHZqsr1ixomLt6quvTo5FXJz5gaAIPxAU4QeCIvxAUIQfCIrwA0ERfiAoc/f0DmbjJG2W9F1JZyV1ufuzZrZW0iJJvdmuq9z91dRtlUolL5fLDTcNYGClUknlctlq2beWN/l8I2m5u79nZiMl7TGznVnt5+7+b/U2CqA4VcPv7kclHc0uf2FmByWNbXZjAJrrgp7zm9l4SVMknftOrKVmts/MNpjZqApjFptZ2czKvb29A+0CoAA1h9/MviPpd5J+4u5/lvQLSRMkTVbfI4OfDjTO3bvcveTupY6OjhxaBpCHmsJvZsPUF/xfufvLkuTux9z9jLuflbRe0tTmtQkgb1XDb2Ym6ZeSDrr7z/pt7+y321xJ+/NvD0Cz1PJq/3RJCyR9YGbn1ppeJWm+mU2W5JK6JaXXqQbQVmp5tX+XpIHmDZNz+gDaG+/wA4Ii/EBQhB8IivADQRF+ICjCDwRF+IGgCD8QFOEHgiL8QFCEHwiK8ANBEX4gKMIPBFX1q7tzPZhZr6RP+20aI+lEyxq4MO3aW7v2JdFbvfLs7QZ3r+n78loa/m8d3Kzs7qXCGkho197atS+J3upVVG887AeCIvxAUEWHv6vg46e0a2/t2pdEb/UqpLdCn/MDKE7RZ34ABSkk/GZ2r5kdMrOPzGxlET1UYmbdZvaBme01s0KXFM6WQTtuZvv7bRttZjvN7A/ZzwGXSSuot7Vm9n/ZfbfXzP6poN7GmdmbZnbQzA6Y2T9n2wu97xJ9FXK/tfxhv5kNlfS/ku6W1CNpt6T57v4/LW2kAjPrllRy98LnhM3sdkl/kbTZ3Sdl256WdNLdn8r+cI5y939pk97WSvpL0Ss3ZwvKdPZfWVrSHEkPq8D7LtHXAyrgfivizD9V0kfu/om7n5b0a0mzC+ij7bn725JOnrd5tqRN2eVN6vvlabkKvbUFdz/q7u9ll7+QdG5l6ULvu0RfhSgi/GMl/bHf9R6115LfLun3ZrbHzBYX3cwArs2WTT+3fPo1BfdzvqorN7fSeStLt819V8+K13krIvwDrf7TTlMO0939Vkk/kLQke3iL2tS0cnOrDLCydFuod8XrvBUR/h5J4/pd/56kIwX0MSB3P5L9PC5pm9pv9eFj5xZJzX4eL7ifv2qnlZsHWllabXDftdOK10WEf7ekm8zs+2Y2XNI8SdsL6ONbzGxE9kKMzGyEpFlqv9WHt0tamF1eKOmVAnv5G+2ycnOllaVV8H3XbiteF/Imn2wq498lDZW0wd3/teVNDMDM/k59Z3upbxHTl4rszcy2SJqhvk99HZO0RtJ/SPqtpOslHZb0I3dv+QtvFXqbob6Hrn9dufncc+wW9/aPkv5L0geSzmabV6nv+XVh912ir/kq4H7jHX5AULzDDwiK8ANBEX4gKMIPBEX4gaAIPxAU4QeCIvxAUP8Pt/ALPExulGgAAAAASUVORK5CYII=\n",
"text/plain": [
"<matplotlib.figure.Figure at 0x7f5f308fd0>"
]
},
"metadata": {},
"output_type": "display_data"
}
],
"source": [
"timg, c = train_dataset[0]\n",
"print(timg.shape, c)\n",
"plt.imshow(timg.squeeze(0), cmap='gray_r')"
]
},
{
"cell_type": "code",
"execution_count": 6,
"metadata": {},
"outputs": [
{
"data": {
"text/plain": [
"Dataset MNIST\n",
" Number of datapoints: 10000\n",
" Root location: ./torch_datasets\n",
" Split: Test\n",
" StandardTransform\n",
"Transform: Compose(\n",
" ToTensor()\n",
" Normalize(mean=(0.1307,), std=(0.3081,))\n",
" )"
]
},
"execution_count": 6,
"metadata": {},
"output_type": "execute_result"
}
],
"source": [
"test_dataset"
]
},
{
"cell_type": "code",
"execution_count": 7,
"metadata": {},
"outputs": [
{
"name": "stdout",
"output_type": "stream",
"text": [
"torch.Size([1, 28, 28]) 7\n"
]
},
{
"data": {
"text/plain": [
"<matplotlib.image.AxesImage at 0x7f5bd21ba8>"
]
},
"execution_count": 7,
"metadata": {},
"output_type": "execute_result"
},
{
"data": {
"image/png": "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\n",
"text/plain": [
"<matplotlib.figure.Figure at 0x7f88355da0>"
]
},
"metadata": {},
"output_type": "display_data"
}
],
"source": [
"timg, c = test_dataset[0]\n",
"print(timg.shape, c)\n",
"plt.imshow(timg.squeeze(0), cmap='gray_r')"
]
},
{
"cell_type": "markdown",
"metadata": {},
"source": [
"# DataLoader"
]
},
{
"cell_type": "markdown",
"metadata": {},
"source": [
"We will now define the size of the batch we want to use. And we will create a dataloader that will allow us to get data from the dataset by batch of the given size (this will be easier than creating a loop ourselves)."
]
},
{
"cell_type": "code",
"execution_count": 8,
"metadata": {},
"outputs": [],
"source": [
"batchsize = 4"
]
},
{
"cell_type": "code",
"execution_count": 9,
"metadata": {},
"outputs": [],
"source": [
"train_loader = torch.utils.data.DataLoader(train_dataset, batchsize)\n",
"test_loader = torch.utils.data.DataLoader(test_dataset, batchsize)"
]
},
{
"cell_type": "markdown",
"metadata": {},
"source": [
"#PYNQ Overlay"
]
},
{
"cell_type": "markdown",
"metadata": {},
"source": [
"We will load the PYNQ overlay, and define handler for the AXI GPIO and DMA that are present in this overlay."
]
},
{
"cell_type": "code",
"execution_count": 10,
"metadata": {},
"outputs": [
{
"data": {
"application/javascript": [
"\n",
"try {\n",
"require(['notebook/js/codecell'], function(codecell) {\n",
" codecell.CodeCell.options_default.highlight_modes[\n",
" 'magic_text/x-csrc'] = {'reg':[/^%%microblaze/]};\n",
" Jupyter.notebook.events.one('kernel_ready.Kernel', function(){\n",
" Jupyter.notebook.get_cells().map(function(cell){\n",
" if (cell.cell_type == 'code'){ cell.auto_highlight(); } }) ;\n",
" });\n",
"});\n",
"} catch (e) {};\n"
]
},
"metadata": {},
"output_type": "display_data"
},
{
"data": {
"application/javascript": [
"\n",
"try {\n",
"require(['notebook/js/codecell'], function(codecell) {\n",
" codecell.CodeCell.options_default.highlight_modes[\n",
" 'magic_text/x-csrc'] = {'reg':[/^%%pybind11/]};\n",
" Jupyter.notebook.events.one('kernel_ready.Kernel', function(){\n",
" Jupyter.notebook.get_cells().map(function(cell){\n",
" if (cell.cell_type == 'code'){ cell.auto_highlight(); } }) ;\n",
" });\n",
"});\n",
"} catch (e) {};\n"
]
},
"metadata": {},
"output_type": "display_data"
}
],
"source": [
"from pynq import Overlay\n",
"from pynq import allocate\n",
"import pynq.lib.dma"
]
},
{
"cell_type": "code",
"execution_count": 11,
"metadata": {},
"outputs": [],
"source": [
"# Load the overlay\n",
"overlay = Overlay(\"/home/xilinx/pynq/overlays/multaccum/multaccum.bit\")"
]
},
{
"cell_type": "code",
"execution_count": 12,
"metadata": {},
"outputs": [],
"source": [
"# Load the AXI GPIO and DMAs\n",
"axigpio_size = overlay.multaccum.din_size\n",
"dma_in_a = overlay.multaccum.in_a_dma\n",
"dma_in_b = overlay.multaccum.in_b_dma\n",
"dma_out = overlay.multaccum.out_dma"
]
},
{
"cell_type": "markdown",
"metadata": {},
"source": [
"The DMAs require contiguous memory buffer. Let's allocate them."
]
},
{
"cell_type": "code",
"execution_count": 13,
"metadata": {},
"outputs": [],
"source": [
"n = 2**21\n",
"in_a_buffer = allocate(shape=(n,), dtype=np.float32)\n",
"in_b_buffer = allocate(shape=(n,), dtype=np.float32)\n",
"\n",
"out_buffer = allocate(shape=(2**16,), dtype=np.float32)"
]
},
{
"cell_type": "markdown",
"metadata": {},
"source": [
"# Overlay driver function"
]
},
{
"cell_type": "markdown",
"metadata": {},
"source": [
"We will now define the 'multaccumx' function that will use the FPGA to perform the following computation :\n",
"\n",
" output = inputs @ weights.t() + bias"
]
},
{
"cell_type": "code",
"execution_count": 14,
"metadata": {},
"outputs": [],
"source": [
"def multaccumx(inputs, weights, bias):\n",
"\n",
" # Check that the arguments are corretly shaped\n",
" if inputs.dim() != 2:\n",
" print(\"ERROR : 'inputs' dim is not 2 !\", inputs.dim())\n",
" print(inputs.shape)\n",
" return 0\n",
" if weights.dim() != 2:\n",
" print(\"ERROR : 'weights' dim is not 2 !\", weights.dim())\n",
" return 0\n",
" if bias.dim() != 1:\n",
" print(\"ERROR : 'bias' dim is not 1 !\", bias.dim())\n",
" return 0\n",
"\n",
" #Store the sizes\n",
" nb_din, sz_din = inputs.shape\n",
" nb_neuron, sz_neuron = weights.shape\n",
" sz_bias = bias.shape[0]\n",
"\n",
" # Check that the size match\n",
" if sz_din != sz_neuron:\n",
" print(\"ERROR : 'inputs' and 'weights' size is not equal !\", sz_din, sz_neuron)\n",
" return 0\n",
" if nb_neuron != sz_bias:\n",
" print(\"ERROR : 'weights' and 'bias' size is not equal !\", nb_neuron, sz_bias)\n",
" return 0\n",
"\n",
" # Configure the 'multaccum' FPGA IP with din size minus 1\n",
" # (this is used in the IP to generate internal AXI Stream tlast) \n",
" axigpio_size.register_map.GPIO_DATA = sz_din-1 \n",
"\n",
" # Store the weigths in the continuous buffer that will be transfered by the DMA\n",
" in_b_buffer[:nb_neuron*sz_neuron] = weights.flatten()\n",
"\n",
" # Loop on all din\n",
" for i in range(nb_din):\n",
"\n",
" # Store the inputs data in the continuous buffer that will be transfered by the DMA\n",
" # (the inputs data are repetaed as many times as the number of neuron in the layer)\n",
" in_a_buffer[:nb_neuron*sz_din] = inputs[i].unsqueeze(0).expand(nb_neuron, -1).flatten()\n",
"\n",
" # Launch the DMA transferts\n",
" dma_out.recvchannel.transfer(out_buffer[i*nb_neuron:])\n",
" dma_in_b.sendchannel.transfer(in_b_buffer[:nb_neuron*sz_neuron])\n",
" dma_in_a.sendchannel.transfer(in_a_buffer[:nb_neuron*sz_din])\n",
"\n",
" # Wait the end of result reception\n",
" dma_out.recvchannel.wait()\n",
"\n",
" # Copy the result from the continuous buffer as a tensor of the correct shape\n",
" dout = torch.tensor(out_buffer[:nb_din*nb_neuron]).view(nb_din, nb_neuron) + bias\n",
" return dout\n"
]
},
{
"cell_type": "code",
"execution_count": null,
"metadata": {},
"outputs": [],
"source": []
},
{
"cell_type": "markdown",
"metadata": {},
"source": [
"# Custom autograd function"
]
},
{
"cell_type": "markdown",
"metadata": {},
"source": [
"The 'multaccumx' function is just performing a computation.\n",
"\n",
"To be able to use it in a layer of a neural network, we need to wrap it to associate the corresponding gradient computation that will be required during the backward pass of the training."
]
},
{
"cell_type": "code",
"execution_count": 15,
"metadata": {},
"outputs": [],
"source": [
"class MyLinx(torch.autograd.Function):\n",
" \"\"\"\n",
" We can implement our own custom autograd Functions by subclassing\n",
" torch.autograd.Function and implementing the forward and backward passes\n",
" which operate on Tensors.\n",
" \"\"\"\n",
"\n",
" @staticmethod\n",
" def forward(ctx, input, weight, bias=None):\n",
" \"\"\"\n",
" In the forward pass we receive a context object and a Tensor containing the\n",
" input; we must return a Tensor containing the output, and we can use the\n",
" context object to cache objects for use in the backward pass.\n",
" \"\"\"\n",
" ctx.save_for_backward(input, weight, bias)\n",
" output = multaccumx(input, weight, bias)\n",
" # if bias is not None:\n",
" # output += bias.unsqueeze(0).expand_as(output)\n",
" return output\n",
"\n",
" # This function has only a single output, so it gets only one gradient\n",
" @staticmethod\n",
" def backward(ctx, grad_output):\n",
" \"\"\"\n",
" In the backward pass we receive the context object and a Tensor containing\n",
" the gradient of the loss with respect to the output produced during the\n",
" forward pass. We can retrieve cached data from the context object, and must\n",
" compute and return the gradient of the loss with respect to the input to the\n",
" forward function.\n",
" \"\"\"\n",
" input, weight, bias = ctx.saved_tensors\n",
" grad_input = grad_weight = grad_bias = None\n",
"\n",
" if ctx.needs_input_grad[0]:\n",
" grad_input = grad_output.mm(weight)\n",
" if ctx.needs_input_grad[1]:\n",
" grad_weight = grad_output.t().mm(input)\n",
" if bias is not None and ctx.needs_input_grad[2]:\n",
" grad_bias = grad_output.sum(0).squeeze(0)\n",
"\n",
" return grad_input, grad_weight, grad_bias\n",
"\n",
"\n",
"mylinx = MyLinx.apply\n"
]
},
{
"cell_type": "code",
"execution_count": null,
"metadata": {},
"outputs": [],
"source": []
},
{
"cell_type": "markdown",
"metadata": {},
"source": [
"# Custom nn.Linear"
]
},
{
"cell_type": "markdown",
"metadata": {},
"source": [
"PyTorch contains object that can easily be used to build a neural network.\n",
"\n",
"We don't want to recreate completely such an object, as we just want to change\n",
"the way the forward computation of a linear layer is computed (to use the FPGA to compute it).\n",
"\n",
"We can do this by simply overiding the forward part of the existing 'nn.Linear' object."
]
},
{
"cell_type": "code",
"execution_count": 16,
"metadata": {},
"outputs": [],
"source": [
"class myLinearX(nn.Linear):\n",
" \n",
" def forward(self, input):\n",
" #output = input @ self.weight.t() + self.bias\n",
" output = mylinx(input.flatten(1), self.weight, self.bias)\n",
" return output"
]
},
{
"cell_type": "markdown",
"metadata": {},
"source": [
"# Neural Network Model"
]
},
{
"cell_type": "markdown",
"metadata": {},
"source": [
"We have now all the pieces we needed. We can define the neural network model we want, and use our new 'myLinearX' linear layer in it."
]
},
{
"cell_type": "code",
"execution_count": 17,
"metadata": {},
"outputs": [],
"source": [
"mymodelx = nn.Sequential(\n",
" nn.Flatten(),\n",
" myLinearX(784,128),\n",
" nn.ReLU(),\n",
" myLinearX(128,32),\n",
" nn.ReLU(),\n",
" myLinearX(32, 10),\n",
" nn.LogSoftmax(dim=1)\n",
")"
]
},
{
"cell_type": "markdown",
"metadata": {},
"source": [
"This model defines :\n",
"* the architecture of the network,\n",
"* the parameters of the network,\n",
"* the initilization of these parameters,\n",
"* and the gradient that will be computed.\n",
"\n",
"We also need to define the way we will upgrade the parameters with the computed gradient, and the associated learning rate. "
]
},
{
"cell_type": "code",
"execution_count": 18,
"metadata": {},
"outputs": [],
"source": [
"myoptimizerx = torch.optim.SGD(mymodelx.parameters(), lr=1e-3)"
]
},
{
"cell_type": "markdown",
"metadata": {},
"source": [
"# Training time"
]
},
{
"cell_type": "markdown",
"metadata": {},
"source": [
"To train our network we need to :\n",
"* reinitialize all the gradients to 0\n",
"* perform a forward pass on a batch of data to compute the output of the model\n",
"* compute a loss to evaluate how far our output is from the required output\n",
"* use the computed loss to perform the backward pass that will define all the gradients\n",
"* update the parameters with the computed gradient as defined in our optimizer\n",
"* repeat until the end of the train dataset\n",
"\n",
"We will gather all theses steps in a 'train' function."
]
},
{
"cell_type": "code",
"execution_count": 19,
"metadata": {},
"outputs": [],
"source": [
"def train(model, train_loader, optimizer, epoch):\n",
" model.train()\n",
" for batch_idx, (data, target) in enumerate(train_loader):\n",
" optimizer.zero_grad()\n",
" output = model(data)\n",
" loss = F.nll_loss(output, target)\n",
" loss.backward()\n",
" optimizer.step()\n",
" if batch_idx % 1000 == 0:\n",
" print('Train Epoch: {} [{}/{} ({:.0f}%)]\\tLoss: {:.6f}'.format(\n",
" epoch, batch_idx * len(data), len(train_loader.dataset),\n",
" 100. * batch_idx / len(train_loader), loss.item()))"
]
},
{
"cell_type": "markdown",
"metadata": {},
"source": [
"We need to evaluate how good our training is.\n",
"\n",
"For this, the output of the model is used to perform a prediction that is supposed to match with the target output. We will use the test dataset to check how many time the prediciotn is correct for data our model have not used for its training.\n",
"\n",
"As this is for evaluation only, we will only perform the forward pass, and no gradient computation will be required.\n",
"\n",
"Let's define a 'test' fucntion that will perform this evaluation on the test dataset."
]
},
{
"cell_type": "code",
"execution_count": 23,
"metadata": {},
"outputs": [],
"source": [
"def test(model, test_loader):\n",
" model.eval()\n",
" test_loss = 0\n",
" correct = 0\n",
" with torch.no_grad():\n",
" for batch_idx, (data, target) in enumerate(test_loader):\n",
" output = model(data)\n",
" test_loss += F.nll_loss(output, target, reduction='sum').item() # sum up batch loss\n",
" pred = output.argmax(dim=1, keepdim=True) # get the index of the max log-probability\n",
" correct += pred.eq(target.view_as(pred)).sum().item()\n",
" if batch_idx % 1000 == 0:\n",
" print(\"Test batch index:\", batch_idx)\n",
"\n",
" test_loss /= len(test_loader.dataset)\n",
"\n",
" print('\\nTest set: Average loss: {:.4f}, Accuracy: {}/{} ({:.2f}%)\\n'.format(\n",
" test_loss, correct, len(test_loader.dataset),\n",
" 100. * correct / len(test_loader.dataset)))"
]
},
{
"cell_type": "markdown",
"metadata": {},
"source": [
"We can now launch the training. As this training is slow, we will do only one epoch."
]
},
{
"cell_type": "code",
"execution_count": 21,
"metadata": {},
"outputs": [
{
"name": "stdout",
"output_type": "stream",
"text": [
"Train Epoch: 0 [0/60000 (0%)]\tLoss: 2.406540\n",
"Train Epoch: 0 [4000/60000 (7%)]\tLoss: 1.743816\n",
"Train Epoch: 0 [8000/60000 (13%)]\tLoss: 0.602789\n",
"Train Epoch: 0 [12000/60000 (20%)]\tLoss: 0.708294\n",
"Train Epoch: 0 [16000/60000 (27%)]\tLoss: 0.649807\n",
"Train Epoch: 0 [20000/60000 (33%)]\tLoss: 0.687648\n",
"Train Epoch: 0 [24000/60000 (40%)]\tLoss: 0.352677\n",
"Train Epoch: 0 [28000/60000 (47%)]\tLoss: 0.047605\n",
"Train Epoch: 0 [32000/60000 (53%)]\tLoss: 0.208460\n",
"Train Epoch: 0 [36000/60000 (60%)]\tLoss: 0.310835\n",
"Train Epoch: 0 [40000/60000 (67%)]\tLoss: 0.026316\n",
"Train Epoch: 0 [44000/60000 (73%)]\tLoss: 0.335622\n",
"Train Epoch: 0 [48000/60000 (80%)]\tLoss: 0.087380\n",
"Train Epoch: 0 [52000/60000 (87%)]\tLoss: 0.023506\n",
"Train Epoch: 0 [56000/60000 (93%)]\tLoss: 0.228996\n"
]
},
{
"ename": "NameError",
"evalue": "name 'device' is not defined",
"output_type": "error",
"traceback": [
"\u001b[0;31m---------------------------------------------------------------------------\u001b[0m",
"\u001b[0;31mNameError\u001b[0m Traceback (most recent call last)",
"\u001b[0;32m<ipython-input-21-b75fede2fb66>\u001b[0m in \u001b[0;36m<module>\u001b[0;34m()\u001b[0m\n\u001b[1;32m 1\u001b[0m \u001b[0;32mfor\u001b[0m \u001b[0mepoch\u001b[0m \u001b[0;32min\u001b[0m \u001b[0mrange\u001b[0m\u001b[0;34m(\u001b[0m\u001b[0;36m1\u001b[0m\u001b[0;34m)\u001b[0m\u001b[0;34m:\u001b[0m\u001b[0;34m\u001b[0m\u001b[0m\n\u001b[1;32m 2\u001b[0m \u001b[0mtrain\u001b[0m\u001b[0;34m(\u001b[0m\u001b[0mmymodelx\u001b[0m\u001b[0;34m,\u001b[0m \u001b[0mtrain_loader\u001b[0m\u001b[0;34m,\u001b[0m \u001b[0mmyoptimizerx\u001b[0m\u001b[0;34m,\u001b[0m \u001b[0mepoch\u001b[0m\u001b[0;34m)\u001b[0m\u001b[0;34m\u001b[0m\u001b[0m\n\u001b[0;32m----> 3\u001b[0;31m \u001b[0mtest\u001b[0m\u001b[0;34m(\u001b[0m\u001b[0mmymodelx\u001b[0m\u001b[0;34m,\u001b[0m \u001b[0mtest_loader\u001b[0m\u001b[0;34m)\u001b[0m\u001b[0;34m\u001b[0m\u001b[0m\n\u001b[0m",
"\u001b[0;32m<ipython-input-20-dc8d1d609526>\u001b[0m in \u001b[0;36mtest\u001b[0;34m(model, test_loader)\u001b[0m\n\u001b[1;32m 5\u001b[0m \u001b[0;32mwith\u001b[0m \u001b[0mtorch\u001b[0m\u001b[0;34m.\u001b[0m\u001b[0mno_grad\u001b[0m\u001b[0;34m(\u001b[0m\u001b[0;34m)\u001b[0m\u001b[0;34m:\u001b[0m\u001b[0;34m\u001b[0m\u001b[0m\n\u001b[1;32m 6\u001b[0m \u001b[0;32mfor\u001b[0m \u001b[0mbatch_idx\u001b[0m\u001b[0;34m,\u001b[0m \u001b[0;34m(\u001b[0m\u001b[0mdata\u001b[0m\u001b[0;34m,\u001b[0m \u001b[0mtarget\u001b[0m\u001b[0;34m)\u001b[0m \u001b[0;32min\u001b[0m \u001b[0menumerate\u001b[0m\u001b[0;34m(\u001b[0m\u001b[0mtest_loader\u001b[0m\u001b[0;34m)\u001b[0m\u001b[0;34m:\u001b[0m\u001b[0;34m\u001b[0m\u001b[0m\n\u001b[0;32m----> 7\u001b[0;31m \u001b[0mdata\u001b[0m\u001b[0;34m,\u001b[0m \u001b[0mtarget\u001b[0m \u001b[0;34m=\u001b[0m \u001b[0mdata\u001b[0m\u001b[0;34m.\u001b[0m\u001b[0mto\u001b[0m\u001b[0;34m(\u001b[0m\u001b[0mdevice\u001b[0m\u001b[0;34m)\u001b[0m\u001b[0;34m,\u001b[0m \u001b[0mtarget\u001b[0m\u001b[0;34m.\u001b[0m\u001b[0mto\u001b[0m\u001b[0;34m(\u001b[0m\u001b[0mdevice\u001b[0m\u001b[0;34m)\u001b[0m\u001b[0;34m\u001b[0m\u001b[0m\n\u001b[0m\u001b[1;32m 8\u001b[0m \u001b[0moutput\u001b[0m \u001b[0;34m=\u001b[0m \u001b[0mmodel\u001b[0m\u001b[0;34m(\u001b[0m\u001b[0mdata\u001b[0m\u001b[0;34m)\u001b[0m\u001b[0;34m\u001b[0m\u001b[0m\n\u001b[1;32m 9\u001b[0m \u001b[0mtest_loss\u001b[0m \u001b[0;34m+=\u001b[0m \u001b[0mF\u001b[0m\u001b[0;34m.\u001b[0m\u001b[0mnll_loss\u001b[0m\u001b[0;34m(\u001b[0m\u001b[0moutput\u001b[0m\u001b[0;34m,\u001b[0m \u001b[0mtarget\u001b[0m\u001b[0;34m,\u001b[0m \u001b[0mreduction\u001b[0m\u001b[0;34m=\u001b[0m\u001b[0;34m'sum'\u001b[0m\u001b[0;34m)\u001b[0m\u001b[0;34m.\u001b[0m\u001b[0mitem\u001b[0m\u001b[0;34m(\u001b[0m\u001b[0;34m)\u001b[0m \u001b[0;31m# sum up batch loss\u001b[0m\u001b[0;34m\u001b[0m\u001b[0m\n",
"\u001b[0;31mNameError\u001b[0m: name 'device' is not defined"
]
}
],
"source": [
"for epoch in range(1):\n",
" train(mymodelx, train_loader, myoptimizerx, epoch)\n",
" test(mymodelx, test_loader)"
]
},
{
"cell_type": "code",
"execution_count": 24,
"metadata": {},
"outputs": [
{
"name": "stdout",
"output_type": "stream",
"text": [
"Test batch index: 0\n",
"Test batch index: 1000\n",
"Test batch index: 2000\n",
"\n",
"Test set: Average loss: 0.3096, Accuracy: 9058/10000 (90.58%)\n",
"\n"
]
}
],
"source": [
"test(mymodelx, test_loader)"
]
},
{
"cell_type": "code",
"execution_count": null,
"metadata": {},
"outputs": [],
"source": []
}
],
"metadata": {
"kernelspec": {
"display_name": "Python 3",
"language": "python",
"name": "python3"
}
},
"nbformat": 4,
"nbformat_minor": 2
}
design_multaccum.tcl
Tcl################################################################
# This is a generated script based on design: design_1
#
# 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 2020.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 design_1_script.tcl
# The design that will be created by this Tcl script contains the following
# module references:
# gentlast
# Please add the sources of those modules before sourcing this Tcl script.
# 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 xczu3eg-sbva484-1-i
set_property BOARD_PART avnet.com:ultra96v2:part0:1.1 [current_project]
}
# CHANGE DESIGN NAME HERE
variable design_name
set design_name design_1
# 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 <design_name> 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 <design_name> 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 <design_name> 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 <design_name> 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 <design_name> 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 "\
xilinx.com:ip:smartconnect:1.0\
xilinx.com:ip:clk_wiz:6.0\
xilinx.com:ip:proc_sys_reset:5.0\
xilinx.com:ip:zynq_ultra_ps_e:3.3\
xilinx.com:ip:axis_broadcaster:1.1\
xilinx.com:ip:axis_subset_converter:1.1\
xilinx.com:ip:axi_gpio:2.0\
xilinx.com:ip:floating_point:7.1\
xilinx.com:ip:c_shift_ram:12.0\
xilinx.com:ip:axi_dma:7.1\
xilinx.com:ip:util_vector_logic:2.0\
xilinx.com:ip:xlconstant:1.1\
"
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
}
}
##################################################################
# CHECK Modules
##################################################################
set bCheckModules 1
if { $bCheckModules == 1 } {
set list_check_mods "\
gentlast\
"
set list_mods_missing ""
common::send_gid_msg -ssname BD::TCL -id 2020 -severity "INFO" "Checking if the following modules exist in the project's sources: $list_check_mods ."
foreach mod_vlnv $list_check_mods {
if { [can_resolve_reference $mod_vlnv] == 0 } {
lappend list_mods_missing $mod_vlnv
}
}
if { $list_mods_missing ne "" } {
catch {common::send_gid_msg -ssname BD::TCL -id 2021 -severity "ERROR" "The following module(s) are not found in the project: $list_mods_missing" }
common::send_gid_msg -ssname BD::TCL -id 2022 -severity "INFO" "Please add source files for the missing module(s) above."
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
##################################################################
# Hierarchical cell: multaccum
proc create_hier_cell_multaccum { parentCell nameHier } {
variable script_folder
if { $parentCell eq "" || $nameHier eq "" } {
catch {common::send_gid_msg -ssname BD::TCL -id 2092 -severity "ERROR" "create_hier_cell_multaccum() - Empty argument(s)!"}
return
}
# 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 <hier>."}
return
}
# Save current instance; Restore later
set oldCurInst [current_bd_instance .]
# Set parent object as current
current_bd_instance $parentObj
# Create cell and set as current instance
set hier_obj [create_bd_cell -type hier $nameHier]
current_bd_instance $hier_obj
# Create interface pins
create_bd_intf_pin -mode Master -vlnv xilinx.com:interface:aximm_rtl:1.0 M_AXI_MM2S
create_bd_intf_pin -mode Master -vlnv xilinx.com:interface:aximm_rtl:1.0 M_AXI_MM2S1
create_bd_intf_pin -mode Master -vlnv xilinx.com:interface:aximm_rtl:1.0 M_AXI_S2MM
create_bd_intf_pin -mode Slave -vlnv xilinx.com:interface:aximm_rtl:1.0 S_AXI
create_bd_intf_pin -mode Slave -vlnv xilinx.com:interface:aximm_rtl:1.0 S_AXI_LITE
create_bd_intf_pin -mode Slave -vlnv xilinx.com:interface:aximm_rtl:1.0 S_AXI_LITE1
create_bd_intf_pin -mode Slave -vlnv xilinx.com:interface:aximm_rtl:1.0 S_AXI_LITE2
# Create pins
create_bd_pin -dir I -type clk aclk
create_bd_pin -dir I -type rst aresetn
create_bd_pin -dir I -type rst axi_resetn
create_bd_pin -dir I -type clk m_axi_s2mm_aclk
# Create instance: axis_broadcaster_0, and set properties
set axis_broadcaster_0 [ create_bd_cell -type ip -vlnv xilinx.com:ip:axis_broadcaster:1.1 axis_broadcaster_0 ]
set_property -dict [ list \
CONFIG.M00_TDATA_REMAP {tdata[31:0]} \
CONFIG.M01_TDATA_REMAP {tdata[31:0]} \
CONFIG.M_TDATA_NUM_BYTES {4} \
CONFIG.S_TDATA_NUM_BYTES {4} \
] $axis_broadcaster_0
# Create instance: axis_subset_converter_0, and set properties
set axis_subset_converter_0 [ create_bd_cell -type ip -vlnv xilinx.com:ip:axis_subset_converter:1.1 axis_subset_converter_0 ]
set_property -dict [ list \
CONFIG.M_HAS_TLAST {1} \
CONFIG.M_HAS_TREADY {1} \
CONFIG.M_TDATA_NUM_BYTES {4} \
CONFIG.S_HAS_TLAST {1} \
CONFIG.S_TDATA_NUM_BYTES {4} \
CONFIG.TDATA_REMAP {tdata[31:0]} \
CONFIG.TLAST_REMAP {tlast[0]} \
] $axis_subset_converter_0
# Create instance: din_size, and set properties
set din_size [ create_bd_cell -type ip -vlnv xilinx.com:ip:axi_gpio:2.0 din_size ]
set_property -dict [ list \
CONFIG.C_ALL_OUTPUTS {1} \
CONFIG.C_DOUT_DEFAULT {0x00000000} \
CONFIG.C_GPIO_WIDTH {16} \
CONFIG.C_IS_DUAL {0} \
] $din_size
# Create instance: faccum, and set properties
set faccum [ create_bd_cell -type ip -vlnv xilinx.com:ip:floating_point:7.1 faccum ]
set_property -dict [ list \
CONFIG.Add_Sub_Value {Add} \
CONFIG.Axi_Optimize_Goal {Performance} \
CONFIG.C_Accum_Input_Msb {32} \
CONFIG.C_Accum_Lsb {-149} \
CONFIG.C_Accum_Msb {127} \
CONFIG.C_Latency {39} \
CONFIG.C_Mult_Usage {Medium_Usage} \
CONFIG.C_Rate {1} \
CONFIG.C_Result_Exponent_Width {8} \
CONFIG.C_Result_Fraction_Width {24} \
CONFIG.Has_A_TLAST {true} \
CONFIG.Operation_Type {Accumulator} \
CONFIG.RESULT_TLAST_Behv {Pass_A_TLAST} \
CONFIG.Result_Precision_Type {Single} \
] $faccum
# Create instance: faccum_shreg, and set properties
set faccum_shreg [ create_bd_cell -type ip -vlnv xilinx.com:ip:c_shift_ram:12.0 faccum_shreg ]
set_property -dict [ list \
CONFIG.AsyncInitVal {0} \
CONFIG.DefaultData {0} \
CONFIG.Depth {39} \
CONFIG.SyncInitVal {0} \
CONFIG.Width {1} \
] $faccum_shreg
# Create instance: fmult, and set properties
set fmult [ create_bd_cell -type ip -vlnv xilinx.com:ip:floating_point:7.1 fmult ]
set_property -dict [ list \
CONFIG.Add_Sub_Value {Both} \
CONFIG.Axi_Optimize_Goal {Performance} \
CONFIG.C_Latency {11} \
CONFIG.C_Mult_Usage {Full_Usage} \
CONFIG.C_Rate {1} \
CONFIG.C_Result_Exponent_Width {8} \
CONFIG.C_Result_Fraction_Width {24} \
CONFIG.Has_A_TLAST {true} \
CONFIG.Operation_Type {Multiply} \
CONFIG.RESULT_TLAST_Behv {Pass_A_TLAST} \
CONFIG.Result_Precision_Type {Single} \
] $fmult
# Create instance: fmult_shreg, and set properties
set fmult_shreg [ create_bd_cell -type ip -vlnv xilinx.com:ip:c_shift_ram:12.0 fmult_shreg ]
set_property -dict [ list \
CONFIG.AsyncInitVal {0} \
CONFIG.DefaultData {0} \
CONFIG.Depth {11} \
CONFIG.SyncInitVal {0} \
CONFIG.Width {1} \
] $fmult_shreg
# Create instance: gentlast_din, and set properties
set block_name gentlast
set block_cell_name gentlast_din
if { [catch {set gentlast_din [create_bd_cell -type module -reference $block_name $block_cell_name] } errmsg] } {
catch {common::send_gid_msg -ssname BD::TCL -id 2095 -severity "ERROR" "Unable to add referenced block <$block_name>. Please add the files for ${block_name}'s definition into the project."}
return 1
} elseif { $gentlast_din eq "" } {
catch {common::send_gid_msg -ssname BD::TCL -id 2096 -severity "ERROR" "Unable to referenced block <$block_name>. Please add the files for ${block_name}'s definition into the project."}
return 1
}
# Create instance: in_a_dma, and set properties
set in_a_dma [ create_bd_cell -type ip -vlnv xilinx.com:ip:axi_dma:7.1 in_a_dma ]
set_property -dict [ list \
CONFIG.c_include_s2mm {0} \
CONFIG.c_include_sg {0} \
CONFIG.c_sg_include_stscntrl_strm {0} \
CONFIG.c_sg_length_width {26} \
] $in_a_dma
# Create instance: in_b_dma, and set properties
set in_b_dma [ create_bd_cell -type ip -vlnv xilinx.com:ip:axi_dma:7.1 in_b_dma ]
set_property -dict [ list \
CONFIG.c_include_s2mm {0} \
CONFIG.c_include_sg {0} \
CONFIG.c_sg_include_stscntrl_strm {0} \
CONFIG.c_sg_length_width {26} \
] $in_b_dma
# Create instance: out_dma, and set properties
set out_dma [ create_bd_cell -type ip -vlnv xilinx.com:ip:axi_dma:7.1 out_dma ]
set_property -dict [ list \
CONFIG.c_include_mm2s {0} \
CONFIG.c_include_sg {0} \
CONFIG.c_sg_include_stscntrl_strm {0} \
CONFIG.c_sg_length_width {26} \
] $out_dma
# Create instance: util_vector_logic_0, and set properties
set util_vector_logic_0 [ create_bd_cell -type ip -vlnv xilinx.com:ip:util_vector_logic:2.0 util_vector_logic_0 ]
set_property -dict [ list \
CONFIG.C_SIZE {1} \
] $util_vector_logic_0
# Create instance: util_vector_logic_1, and set properties
set util_vector_logic_1 [ create_bd_cell -type ip -vlnv xilinx.com:ip:util_vector_logic:2.0 util_vector_logic_1 ]
set_property -dict [ list \
CONFIG.C_SIZE {1} \
] $util_vector_logic_1
# Create instance: xlconstant_1, and set properties
set xlconstant_1 [ create_bd_cell -type ip -vlnv xilinx.com:ip:xlconstant:1.1 xlconstant_1 ]
# Create interface connections
connect_bd_intf_net -intf_net Conn1 [get_bd_intf_pins M_AXI_MM2S] [get_bd_intf_pins in_a_dma/M_AXI_MM2S]
connect_bd_intf_net -intf_net Conn2 [get_bd_intf_pins M_AXI_S2MM] [get_bd_intf_pins out_dma/M_AXI_S2MM]
connect_bd_intf_net -intf_net Conn3 [get_bd_intf_pins S_AXI_LITE] [get_bd_intf_pins out_dma/S_AXI_LITE]
connect_bd_intf_net -intf_net Conn4 [get_bd_intf_pins S_AXI_LITE1] [get_bd_intf_pins in_b_dma/S_AXI_LITE]
connect_bd_intf_net -intf_net Conn5 [get_bd_intf_pins M_AXI_MM2S1] [get_bd_intf_pins in_b_dma/M_AXI_MM2S]
connect_bd_intf_net -intf_net Conn6 [get_bd_intf_pins S_AXI_LITE2] [get_bd_intf_pins in_a_dma/S_AXI_LITE]
connect_bd_intf_net -intf_net Conn7 [get_bd_intf_pins S_AXI] [get_bd_intf_pins din_size/S_AXI]
connect_bd_intf_net -intf_net axis_broadcaster_0_M00_AXIS [get_bd_intf_pins axis_broadcaster_0/M00_AXIS] [get_bd_intf_pins fmult/S_AXIS_B]
connect_bd_intf_net -intf_net axis_broadcaster_0_M01_AXIS [get_bd_intf_pins axis_broadcaster_0/M01_AXIS] [get_bd_intf_pins axis_subset_converter_0/S_AXIS]
connect_bd_intf_net -intf_net in_a_dma_M_AXIS_MM2S [get_bd_intf_pins fmult/S_AXIS_A] [get_bd_intf_pins in_a_dma/M_AXIS_MM2S]
connect_bd_intf_net -intf_net in_b_dma_M_AXIS_MM2S [get_bd_intf_pins axis_broadcaster_0/S_AXIS] [get_bd_intf_pins in_b_dma/M_AXIS_MM2S]
# Create port connections
connect_bd_net -net aclk_1 [get_bd_pins aclk] [get_bd_pins axis_broadcaster_0/aclk] [get_bd_pins axis_subset_converter_0/aclk] [get_bd_pins faccum/aclk] [get_bd_pins faccum_shreg/CLK] [get_bd_pins fmult/aclk] [get_bd_pins fmult_shreg/CLK] [get_bd_pins gentlast_din/clk] [get_bd_pins in_a_dma/m_axi_mm2s_aclk] [get_bd_pins in_b_dma/m_axi_mm2s_aclk] [get_bd_pins out_dma/m_axi_s2mm_aclk]
connect_bd_net -net aresetn_1 [get_bd_pins aresetn] [get_bd_pins axis_broadcaster_0/aresetn] [get_bd_pins axis_subset_converter_0/aresetn] [get_bd_pins gentlast_din/rstn]
connect_bd_net -net axi_resetn_1 [get_bd_pins axi_resetn] [get_bd_pins din_size/s_axi_aresetn] [get_bd_pins in_a_dma/axi_resetn] [get_bd_pins in_b_dma/axi_resetn] [get_bd_pins out_dma/axi_resetn]
connect_bd_net -net axis_subset_converter_0_m_axis_tlast [get_bd_pins axis_subset_converter_0/m_axis_tlast] [get_bd_pins util_vector_logic_1/Op1]
connect_bd_net -net axis_subset_converter_0_m_axis_tvalid [get_bd_pins axis_subset_converter_0/m_axis_tvalid] [get_bd_pins util_vector_logic_1/Op2]
connect_bd_net -net din_size_gpio_io_o [get_bd_pins din_size/gpio_io_o] [get_bd_pins gentlast_din/i_size_m1]
connect_bd_net -net faccum_m_axis_result_tdata [get_bd_pins faccum/m_axis_result_tdata] [get_bd_pins out_dma/s_axis_s2mm_tdata]
connect_bd_net -net faccum_m_axis_result_tlast [get_bd_pins faccum/m_axis_result_tlast] [get_bd_pins util_vector_logic_0/Op1]
connect_bd_net -net faccum_m_axis_result_tvalid [get_bd_pins faccum/m_axis_result_tvalid] [get_bd_pins util_vector_logic_0/Op2]
connect_bd_net -net faccum_s_axis_a_tready [get_bd_pins faccum/s_axis_a_tready] [get_bd_pins fmult/m_axis_result_tready] [get_bd_pins gentlast_din/i_ready]
connect_bd_net -net faccum_shreg_Q [get_bd_pins faccum_shreg/Q] [get_bd_pins out_dma/s_axis_s2mm_tlast]
connect_bd_net -net fmult_m_axis_result_tdata [get_bd_pins faccum/s_axis_a_tdata] [get_bd_pins fmult/m_axis_result_tdata]
connect_bd_net -net fmult_m_axis_result_tvalid [get_bd_pins faccum/s_axis_a_tvalid] [get_bd_pins fmult/m_axis_result_tvalid] [get_bd_pins gentlast_din/i_valid]
connect_bd_net -net fmult_shreg_Q [get_bd_pins faccum_shreg/D] [get_bd_pins fmult_shreg/Q]
connect_bd_net -net gentlast_din_o_last [get_bd_pins faccum/s_axis_a_tlast] [get_bd_pins gentlast_din/o_last]
connect_bd_net -net m_axi_s2mm_aclk_1 [get_bd_pins m_axi_s2mm_aclk] [get_bd_pins din_size/s_axi_aclk] [get_bd_pins in_a_dma/s_axi_lite_aclk] [get_bd_pins in_b_dma/s_axi_lite_aclk] [get_bd_pins out_dma/s_axi_lite_aclk]
connect_bd_net -net out_dma_s_axis_s2mm_tready [get_bd_pins faccum/m_axis_result_tready] [get_bd_pins out_dma/s_axis_s2mm_tready]
connect_bd_net -net util_vector_logic_0_Res [get_bd_pins out_dma/s_axis_s2mm_tvalid] [get_bd_pins util_vector_logic_0/Res]
connect_bd_net -net util_vector_logic_1_Res [get_bd_pins fmult_shreg/D] [get_bd_pins util_vector_logic_1/Res]
connect_bd_net -net xlconstant_1_dout [get_bd_pins axis_subset_converter_0/m_axis_tready] [get_bd_pins xlconstant_1/dout]
# Restore current instance
current_bd_instance $oldCurInst
}
# 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 <hier>."}
return
}
# Save current instance; Restore later
set oldCurInst [current_bd_instance .]
# Set parent object as current
current_bd_instance $parentObj
# Create interface ports
# Create ports
# Create instance: axi_smc, and set properties
set axi_smc [ create_bd_cell -type ip -vlnv xilinx.com:ip:smartconnect:1.0 axi_smc ]
set_property -dict [ list \
CONFIG.NUM_SI {3} \
] $axi_smc
# Create instance: clk_wiz_0, and set properties
set clk_wiz_0 [ create_bd_cell -type ip -vlnv xilinx.com:ip:clk_wiz:6.0 clk_wiz_0 ]
set_property -dict [ list \
CONFIG.CLKOUT1_JITTER {94.862} \
CONFIG.CLKOUT1_REQUESTED_OUT_FREQ {300.000} \
CONFIG.MMCM_CLKOUT0_DIVIDE_F {4.000} \
CONFIG.USE_LOCKED {true} \
CONFIG.USE_RESET {false} \
] $clk_wiz_0
# Create instance: multaccum
create_hier_cell_multaccum [current_bd_instance .] multaccum
# Create instance: ps8_0_axi_periph, and set properties
set ps8_0_axi_periph [ create_bd_cell -type ip -vlnv xilinx.com:ip:axi_interconnect:2.1 ps8_0_axi_periph ]
set_property -dict [ list \
CONFIG.NUM_MI {4} \
CONFIG.NUM_SI {2} \
] $ps8_0_axi_periph
# Create instance: rst_ps8_0_100M, and set properties
set rst_ps8_0_100M [ create_bd_cell -type ip -vlnv xilinx.com:ip:proc_sys_reset:5.0 rst_ps8_0_100M ]
# Create instance: rst_ps8_0_300M, and set properties
set rst_ps8_0_300M [ create_bd_cell -type ip -vlnv xilinx.com:ip:proc_sys_reset:5.0 rst_ps8_0_300M ]
# Create instance: zynq_ultra_ps_e_0, and set properties
set zynq_ultra_ps_e_0 [ create_bd_cell -type ip -vlnv xilinx.com:ip:zynq_ultra_ps_e:3.3 zynq_ultra_ps_e_0 ]
set_property -dict [ list \
CONFIG.PSU_BANK_0_IO_STANDARD {LVCMOS18} \
CONFIG.PSU_BANK_1_IO_STANDARD {LVCMOS18} \
CONFIG.PSU_BANK_2_IO_STANDARD {LVCMOS18} \
CONFIG.PSU_BANK_3_IO_STANDARD {LVCMOS18} \
CONFIG.PSU_DDR_RAM_HIGHADDR {0x7FFFFFFF} \
CONFIG.PSU_DDR_RAM_HIGHADDR_OFFSET {0x00000002} \
CONFIG.PSU_DDR_RAM_LOWADDR_OFFSET {0x80000000} \
CONFIG.PSU_DYNAMIC_DDR_CONFIG_EN {0} \
CONFIG.PSU_MIO_0_DIRECTION {out} \
CONFIG.PSU_MIO_0_INPUT_TYPE {cmos} \
CONFIG.PSU_MIO_0_POLARITY {Default} \
CONFIG.PSU_MIO_10_DIRECTION {inout} \
CONFIG.PSU_MIO_10_POLARITY {Default} \
CONFIG.PSU_MIO_11_DIRECTION {inout} \
CONFIG.PSU_MIO_11_POLARITY {Default} \
CONFIG.PSU_MIO_12_DIRECTION {inout} \
CONFIG.PSU_MIO_12_POLARITY {Default} \
CONFIG.PSU_MIO_13_DIRECTION {inout} \
CONFIG.PSU_MIO_13_DRIVE_STRENGTH {4} \
CONFIG.PSU_MIO_13_POLARITY {Default} \
CONFIG.PSU_MIO_14_DIRECTION {inout} \
CONFIG.PSU_MIO_14_DRIVE_STRENGTH {4} \
CONFIG.PSU_MIO_14_POLARITY {Default} \
CONFIG.PSU_MIO_15_DIRECTION {inout} \
CONFIG.PSU_MIO_15_DRIVE_STRENGTH {4} \
CONFIG.PSU_MIO_15_POLARITY {Default} \
CONFIG.PSU_MIO_16_DIRECTION {inout} \
CONFIG.PSU_MIO_16_DRIVE_STRENGTH {4} \
CONFIG.PSU_MIO_16_POLARITY {Default} \
CONFIG.PSU_MIO_17_DIRECTION {inout} \
CONFIG.PSU_MIO_17_POLARITY {Default} \
CONFIG.PSU_MIO_18_DIRECTION {inout} \
CONFIG.PSU_MIO_18_POLARITY {Default} \
CONFIG.PSU_MIO_19_DIRECTION {inout} \
CONFIG.PSU_MIO_19_POLARITY {Default} \
CONFIG.PSU_MIO_1_DIRECTION {in} \
CONFIG.PSU_MIO_1_DRIVE_STRENGTH {12} \
CONFIG.PSU_MIO_1_POLARITY {Default} \
CONFIG.PSU_MIO_1_SLEW {fast} \
CONFIG.PSU_MIO_20_DIRECTION {inout} \
CONFIG.PSU_MIO_20_POLARITY {Default} \
CONFIG.PSU_MIO_21_DIRECTION {inout} \
CONFIG.PSU_MIO_21_DRIVE_STRENGTH {4} \
CONFIG.PSU_MIO_21_POLARITY {Default} \
CONFIG.PSU_MIO_22_DIRECTION {out} \
CONFIG.PSU_MIO_22_DRIVE_STRENGTH {4} \
CONFIG.PSU_MIO_22_INPUT_TYPE {cmos} \
CONFIG.PSU_MIO_22_POLARITY {Default} \
CONFIG.PSU_MIO_23_DIRECTION {inout} \
CONFIG.PSU_MIO_23_POLARITY {Default} \
CONFIG.PSU_MIO_24_DIRECTION {in} \
CONFIG.PSU_MIO_24_DRIVE_STRENGTH {12} \
CONFIG.PSU_MIO_24_POLARITY {Default} \
CONFIG.PSU_MIO_24_SLEW {fast} \
CONFIG.PSU_MIO_25_DIRECTION {inout} \
CONFIG.PSU_MIO_25_POLARITY {Default} \
CONFIG.PSU_MIO_26_DIRECTION {in} \
CONFIG.PSU_MIO_26_DRIVE_STRENGTH {12} \
CONFIG.PSU_MIO_26_POLARITY {Default} \
CONFIG.PSU_MIO_26_SLEW {fast} \
CONFIG.PSU_MIO_27_DIRECTION {out} \
CONFIG.PSU_MIO_27_INPUT_TYPE {cmos} \
CONFIG.PSU_MIO_27_POLARITY {Default} \
CONFIG.PSU_MIO_28_DIRECTION {in} \
CONFIG.PSU_MIO_28_DRIVE_STRENGTH {12} \
CONFIG.PSU_MIO_28_POLARITY {Default} \
CONFIG.PSU_MIO_28_SLEW {fast} \
CONFIG.PSU_MIO_29_DIRECTION {out} \
CONFIG.PSU_MIO_29_INPUT_TYPE {cmos} \
CONFIG.PSU_MIO_29_POLARITY {Default} \
CONFIG.PSU_MIO_2_DIRECTION {in} \
CONFIG.PSU_MIO_2_DRIVE_STRENGTH {12} \
CONFIG.PSU_MIO_2_POLARITY {Default} \
CONFIG.PSU_MIO_2_SLEW {fast} \
CONFIG.PSU_MIO_30_DIRECTION {in} \
CONFIG.PSU_MIO_30_DRIVE_STRENGTH {12} \
CONFIG.PSU_MIO_30_POLARITY {Default} \
CONFIG.PSU_MIO_30_SLEW {fast} \
CONFIG.PSU_MIO_31_DIRECTION {inout} \
CONFIG.PSU_MIO_31_POLARITY {Default} \
CONFIG.PSU_MIO_32_DIRECTION {out} \
CONFIG.PSU_MIO_32_INPUT_TYPE {cmos} \
CONFIG.PSU_MIO_32_POLARITY {Default} \
CONFIG.PSU_MIO_33_DIRECTION {out} \
CONFIG.PSU_MIO_33_INPUT_TYPE {cmos} \
CONFIG.PSU_MIO_33_POLARITY {Default} \
CONFIG.PSU_MIO_34_DIRECTION {out} \
CONFIG.PSU_MIO_34_INPUT_TYPE {cmos} \
CONFIG.PSU_MIO_34_POLARITY {Default} \
CONFIG.PSU_MIO_35_DIRECTION {inout} \
CONFIG.PSU_MIO_35_POLARITY {Default} \
CONFIG.PSU_MIO_36_DIRECTION {inout} \
CONFIG.PSU_MIO_36_POLARITY {Default} \
CONFIG.PSU_MIO_37_DIRECTION {inout} \
CONFIG.PSU_MIO_37_POLARITY {Default} \
CONFIG.PSU_MIO_38_DIRECTION {inout} \
CONFIG.PSU_MIO_38_POLARITY {Default} \
CONFIG.PSU_MIO_39_DIRECTION {inout} \
CONFIG.PSU_MIO_39_DRIVE_STRENGTH {12} \
CONFIG.PSU_MIO_39_POLARITY {Default} \
CONFIG.PSU_MIO_39_SLEW {fast} \
CONFIG.PSU_MIO_3_DIRECTION {out} \
CONFIG.PSU_MIO_3_INPUT_TYPE {cmos} \
CONFIG.PSU_MIO_3_POLARITY {Default} \
CONFIG.PSU_MIO_40_DIRECTION {inout} \
CONFIG.PSU_MIO_40_POLARITY {Default} \
CONFIG.PSU_MIO_41_DIRECTION {inout} \
CONFIG.PSU_MIO_41_POLARITY {Default} \
CONFIG.PSU_MIO_42_DIRECTION {inout} \
CONFIG.PSU_MIO_42_POLARITY {Default} \
CONFIG.PSU_MIO_43_DIRECTION {inout} \
CONFIG.PSU_MIO_43_POLARITY {Default} \
CONFIG.PSU_MIO_44_DIRECTION {inout} \
CONFIG.PSU_MIO_44_POLARITY {Default} \
CONFIG.PSU_MIO_45_DIRECTION {inout} \
CONFIG.PSU_MIO_45_POLARITY {Default} \
CONFIG.PSU_MIO_46_DIRECTION {inout} \
CONFIG.PSU_MIO_46_POLARITY {Default} \
CONFIG.PSU_MIO_47_DIRECTION {inout} \
CONFIG.PSU_MIO_47_POLARITY {Default} \
CONFIG.PSU_MIO_48_DIRECTION {inout} \
CONFIG.PSU_MIO_48_POLARITY {Default} \
CONFIG.PSU_MIO_49_DIRECTION {inout} \
CONFIG.PSU_MIO_49_POLARITY {Default} \
CONFIG.PSU_MIO_4_DIRECTION {inout} \
CONFIG.PSU_MIO_4_POLARITY {Default} \
CONFIG.PSU_MIO_50_DIRECTION {inout} \
CONFIG.PSU_MIO_50_POLARITY {Default} \
CONFIG.PSU_MIO_51_DIRECTION {out} \
CONFIG.PSU_MIO_51_INPUT_TYPE {cmos} \
CONFIG.PSU_MIO_51_POLARITY {Default} \
CONFIG.PSU_MIO_52_DIRECTION {in} \
CONFIG.PSU_MIO_52_DRIVE_STRENGTH {12} \
CONFIG.PSU_MIO_52_POLARITY {Default} \
CONFIG.PSU_MIO_52_SLEW {fast} \
CONFIG.PSU_MIO_53_DIRECTION {in} \
CONFIG.PSU_MIO_53_DRIVE_STRENGTH {12} \
CONFIG.PSU_MIO_53_POLARITY {Default} \
CONFIG.PSU_MIO_53_SLEW {fast} \
CONFIG.PSU_MIO_54_DIRECTION {inout} \
CONFIG.PSU_MIO_54_POLARITY {Default} \
CONFIG.PSU_MIO_55_DIRECTION {in} \
CONFIG.PSU_MIO_55_DRIVE_STRENGTH {12} \
CONFIG.PSU_MIO_55_POLARITY {Default} \
CONFIG.PSU_MIO_55_SLEW {fast} \
CONFIG.PSU_MIO_56_DIRECTION {inout} \
CONFIG.PSU_MIO_56_POLARITY {Default} \
CONFIG.PSU_MIO_57_DIRECTION {inout} \
CONFIG.PSU_MIO_57_POLARITY {Default} \
CONFIG.PSU_MIO_58_DIRECTION {out} \
CONFIG.PSU_MIO_58_INPUT_TYPE {cmos} \
CONFIG.PSU_MIO_58_POLARITY {Default} \
CONFIG.PSU_MIO_59_DIRECTION {inout} \
CONFIG.PSU_MIO_59_POLARITY {Default} \
CONFIG.PSU_MIO_5_DIRECTION {inout} \
CONFIG.PSU_MIO_5_POLARITY {Default} \
CONFIG.PSU_MIO_60_DIRECTION {inout} \
CONFIG.PSU_MIO_60_POLARITY {Default} \
CONFIG.PSU_MIO_61_DIRECTION {inout} \
CONFIG.PSU_MIO_61_POLARITY {Default} \
CONFIG.PSU_MIO_62_DIRECTION {inout} \
CONFIG.PSU_MIO_62_POLARITY {Default} \
CONFIG.PSU_MIO_63_DIRECTION {inout} \
CONFIG.PSU_MIO_63_POLARITY {Default} \
CONFIG.PSU_MIO_64_DIRECTION {in} \
CONFIG.PSU_MIO_64_DRIVE_STRENGTH {12} \
CONFIG.PSU_MIO_64_POLARITY {Default} \
CONFIG.PSU_MIO_64_SLEW {fast} \
CONFIG.PSU_MIO_65_DIRECTION {in} \
CONFIG.PSU_MIO_65_DRIVE_STRENGTH {12} \
CONFIG.PSU_MIO_65_POLARITY {Default} \
CONFIG.PSU_MIO_65_SLEW {fast} \
CONFIG.PSU_MIO_66_DIRECTION {inout} \
CONFIG.PSU_MIO_66_POLARITY {Default} \
CONFIG.PSU_MIO_67_DIRECTION {in} \
CONFIG.PSU_MIO_67_DRIVE_STRENGTH {12} \
CONFIG.PSU_MIO_67_POLARITY {Default} \
CONFIG.PSU_MIO_67_SLEW {fast} \
CONFIG.PSU_MIO_68_DIRECTION {inout} \
CONFIG.PSU_MIO_68_POLARITY {Default} \
CONFIG.PSU_MIO_69_DIRECTION {inout} \
CONFIG.PSU_MIO_69_POLARITY {Default} \
CONFIG.PSU_MIO_6_DIRECTION {inout} \
CONFIG.PSU_MIO_6_POLARITY {Default} \
CONFIG.PSU_MIO_70_DIRECTION {out} \
CONFIG.PSU_MIO_70_INPUT_TYPE {cmos} \
CONFIG.PSU_MIO_70_POLARITY {Default} \
CONFIG.PSU_MIO_71_DIRECTION {inout} \
CONFIG.PSU_MIO_71_POLARITY {Default} \
CONFIG.PSU_MIO_72_DIRECTION {inout} \
CONFIG.PSU_MIO_72_POLARITY {Default} \
CONFIG.PSU_MIO_73_DIRECTION {inout} \
CONFIG.PSU_MIO_73_POLARITY {Default} \
CONFIG.PSU_MIO_74_DIRECTION {inout} \
CONFIG.PSU_MIO_74_POLARITY {Default} \
CONFIG.PSU_MIO_75_DIRECTION {inout} \
CONFIG.PSU_MIO_75_POLARITY {Default} \
CONFIG.PSU_MIO_76_DIRECTION {inout} \
CONFIG.PSU_MIO_76_POLARITY {Default} \
CONFIG.PSU_MIO_77_DIRECTION {inout} \
CONFIG.PSU_MIO_77_POLARITY {Default} \
CONFIG.PSU_MIO_7_DIRECTION {inout} \
CONFIG.PSU_MIO_7_POLARITY {Default} \
CONFIG.PSU_MIO_8_DIRECTION {inout} \
CONFIG.PSU_MIO_8_POLARITY {Default} \
CONFIG.PSU_MIO_9_DIRECTION {inout} \
CONFIG.PSU_MIO_9_POLARITY {Default} \
CONFIG.PSU_MIO_TREE_PERIPHERALS {UART 1#UART 1#UART 0#UART 0#I2C 1#I2C 1#SPI 1#GPIO0 MIO#GPIO0 MIO#SPI 1#SPI 1#SPI 1#GPIO0 MIO#SD 0#SD 0#SD 0#SD 0#GPIO0 MIO#GPIO0 MIO#GPIO0 MIO#GPIO0 MIO#SD 0#SD 0#GPIO0 MIO#SD 0#GPIO0 MIO#PMU GPI 0#DPAUX#DPAUX#DPAUX#DPAUX#GPIO1 MIO#PMU GPO 0#PMU GPO 1#PMU GPO 2#GPIO1 MIO#GPIO1 MIO#GPIO1 MIO#SPI 0#GPIO1 MIO#GPIO1 MIO#SPI 0#SPI 0#SPI 0#GPIO1 MIO#GPIO1 MIO#SD 1#SD 1#SD 1#SD 1#SD 1#SD 1#USB 0#USB 0#USB 0#USB 0#USB 0#USB 0#USB 0#USB 0#USB 0#USB 0#USB 0#USB 0#USB 1#USB 1#USB 1#USB 1#USB 1#USB 1#USB 1#USB 1#USB 1#USB 1#USB 1#USB 1#GPIO2 MIO#GPIO2 MIO} \
CONFIG.PSU_MIO_TREE_SIGNALS {txd#rxd#rxd#txd#scl_out#sda_out#sclk_out#gpio0[7]#gpio0[8]#n_ss_out[0]#miso#mosi#gpio0[12]#sdio0_data_out[0]#sdio0_data_out[1]#sdio0_data_out[2]#sdio0_data_out[3]#gpio0[17]#gpio0[18]#gpio0[19]#gpio0[20]#sdio0_cmd_out#sdio0_clk_out#gpio0[23]#sdio0_cd_n#gpio0[25]#gpi[0]#dp_aux_data_out#dp_hot_plug_detect#dp_aux_data_oe#dp_aux_data_in#gpio1[31]#gpo[0]#gpo[1]#gpo[2]#gpio1[35]#gpio1[36]#gpio1[37]#sclk_out#gpio1[39]#gpio1[40]#n_ss_out[0]#miso#mosi#gpio1[44]#gpio1[45]#sdio1_data_out[0]#sdio1_data_out[1]#sdio1_data_out[2]#sdio1_data_out[3]#sdio1_cmd_out#sdio1_clk_out#ulpi_clk_in#ulpi_dir#ulpi_tx_data[2]#ulpi_nxt#ulpi_tx_data[0]#ulpi_tx_data[1]#ulpi_stp#ulpi_tx_data[3]#ulpi_tx_data[4]#ulpi_tx_data[5]#ulpi_tx_data[6]#ulpi_tx_data[7]#ulpi_clk_in#ulpi_dir#ulpi_tx_data[2]#ulpi_nxt#ulpi_tx_data[0]#ulpi_tx_data[1]#ulpi_stp#ulpi_tx_data[3]#ulpi_tx_data[4]#ulpi_tx_data[5]#ulpi_tx_data[6]#ulpi_tx_data[7]#gpio2[76]#gpio2[77]} \
CONFIG.PSU_SD0_INTERNAL_BUS_WIDTH {4} \
CONFIG.PSU_SD1_INTERNAL_BUS_WIDTH {4} \
CONFIG.PSU_USB3__DUAL_CLOCK_ENABLE {1} \
CONFIG.PSU__ACT_DDR_FREQ_MHZ {533.333313} \
CONFIG.PSU__CAN1__GRP_CLK__ENABLE {0} \
CONFIG.PSU__CAN1__PERIPHERAL__ENABLE {0} \
CONFIG.PSU__CRF_APB__ACPU_CTRL__ACT_FREQMHZ {1200.000000} \
CONFIG.PSU__CRF_APB__ACPU_CTRL__DIVISOR0 {1} \
CONFIG.PSU__CRF_APB__ACPU_CTRL__SRCSEL {APLL} \
CONFIG.PSU__CRF_APB__APLL_CTRL__DIV2 {1} \
CONFIG.PSU__CRF_APB__APLL_CTRL__FBDIV {72} \
CONFIG.PSU__CRF_APB__APLL_CTRL__FRACDATA {0} \
CONFIG.PSU__CRF_APB__APLL_CTRL__SRCSEL {PSS_REF_CLK} \
CONFIG.PSU__CRF_APB__APLL_FRAC_CFG__ENABLED {0} \
CONFIG.PSU__CRF_APB__APLL_TO_LPD_CTRL__DIVISOR0 {3} \
CONFIG.PSU__CRF_APB__DBG_FPD_CTRL__ACT_FREQMHZ {250.000000} \
CONFIG.PSU__CRF_APB__DBG_FPD_CTRL__DIVISOR0 {2} \
CONFIG.PSU__CRF_APB__DBG_FPD_CTRL__SRCSEL {IOPLL} \
CONFIG.PSU__CRF_APB__DBG_TRACE_CTRL__DIVISOR0 {2} \
CONFIG.PSU__CRF_APB__DBG_TRACE_CTRL__SRCSEL {IOPLL} \
CONFIG.PSU__CRF_APB__DBG_TSTMP_CTRL__ACT_FREQMHZ {250.000000} \
CONFIG.PSU__CRF_APB__DBG_TSTMP_CTRL__DIVISOR0 {2} \
CONFIG.PSU__CRF_APB__DBG_TSTMP_CTRL__SRCSEL {IOPLL} \
CONFIG.PSU__CRF_APB__DDR_CTRL__ACT_FREQMHZ {266.666656} \
CONFIG.PSU__CRF_APB__DDR_CTRL__DIVISOR0 {4} \
CONFIG.PSU__CRF_APB__DDR_CTRL__FREQMHZ {533} \
CONFIG.PSU__CRF_APB__DDR_CTRL__SRCSEL {DPLL} \
CONFIG.PSU__CRF_APB__DPDMA_REF_CTRL__ACT_FREQMHZ {600.000000} \
CONFIG.PSU__CRF_APB__DPDMA_REF_CTRL__DIVISOR0 {2} \
CONFIG.PSU__CRF_APB__DPDMA_REF_CTRL__SRCSEL {APLL} \
CONFIG.PSU__CRF_APB__DPLL_CTRL__DIV2 {1} \
CONFIG.PSU__CRF_APB__DPLL_CTRL__FBDIV {64} \
CONFIG.PSU__CRF_APB__DPLL_CTRL__FRACDATA {0} \
CONFIG.PSU__CRF_APB__DPLL_CTRL__SRCSEL {PSS_REF_CLK} \
CONFIG.PSU__CRF_APB__DPLL_FRAC_CFG__ENABLED {0} \
CONFIG.PSU__CRF_APB__DPLL_TO_LPD_CTRL__DIVISOR0 {3} \
CONFIG.PSU__CRF_APB__DP_AUDIO_REF_CTRL__ACT_FREQMHZ {24.576040} \
CONFIG.PSU__CRF_APB__DP_AUDIO_REF_CTRL__DIVISOR0 {16} \
CONFIG.PSU__CRF_APB__DP_AUDIO_REF_CTRL__DIVISOR1 {1} \
CONFIG.PSU__CRF_APB__DP_AUDIO_REF_CTRL__SRCSEL {RPLL} \
CONFIG.PSU__CRF_APB__DP_AUDIO__FRAC_ENABLED {1} \
CONFIG.PSU__CRF_APB__DP_STC_REF_CTRL__ACT_FREQMHZ {26.214443} \
CONFIG.PSU__CRF_APB__DP_STC_REF_CTRL__DIVISOR0 {15} \
CONFIG.PSU__CRF_APB__DP_STC_REF_CTRL__DIVISOR1 {1} \
CONFIG.PSU__CRF_APB__DP_STC_REF_CTRL__SRCSEL {RPLL} \
CONFIG.PSU__CRF_APB__DP_VIDEO_REF_CTRL__ACT_FREQMHZ {297.029572} \
CONFIG.PSU__CRF_APB__DP_VIDEO_REF_CTRL__DIVISOR0 {4} \
CONFIG.PSU__CRF_APB__DP_VIDEO_REF_CTRL__DIVISOR1 {1} \
CONFIG.PSU__CRF_APB__DP_VIDEO_REF_CTRL__SRCSEL {VPLL} \
CONFIG.PSU__CRF_APB__DP_VIDEO__FRAC_ENABLED {1} \
CONFIG.PSU__CRF_APB__GDMA_REF_CTRL__ACT_FREQMHZ {600.000000} \
CONFIG.PSU__CRF_APB__GDMA_REF_CTRL__DIVISOR0 {2} \
CONFIG.PSU__CRF_APB__GDMA_REF_CTRL__SRCSEL {APLL} \
CONFIG.PSU__CRF_APB__GPU_REF_CTRL__ACT_FREQMHZ {500.000000} \
CONFIG.PSU__CRF_APB__GPU_REF_CTRL__DIVISOR0 {1} \
CONFIG.PSU__CRF_APB__GPU_REF_CTRL__SRCSEL {IOPLL} \
CONFIG.PSU__CRF_APB__PCIE_REF_CTRL__DIVISOR0 {2} \
CONFIG.PSU__CRF_APB__PCIE_REF_CTRL__SRCSEL {IOPLL} \
CONFIG.PSU__CRF_APB__SATA_REF_CTRL__DIVISOR0 {2} \
CONFIG.PSU__CRF_APB__SATA_REF_CTRL__FREQMHZ {250} \
CONFIG.PSU__CRF_APB__SATA_REF_CTRL__SRCSEL {IOPLL} \
CONFIG.PSU__CRF_APB__TOPSW_LSBUS_CTRL__ACT_FREQMHZ {100.000000} \
CONFIG.PSU__CRF_APB__TOPSW_LSBUS_CTRL__DIVISOR0 {5} \
CONFIG.PSU__CRF_APB__TOPSW_LSBUS_CTRL__SRCSEL {IOPLL} \
CONFIG.PSU__CRF_APB__TOPSW_MAIN_CTRL__ACT_FREQMHZ {533.333313} \
CONFIG.PSU__CRF_APB__TOPSW_MAIN_CTRL__DIVISOR0 {2} \
CONFIG.PSU__CRF_APB__TOPSW_MAIN_CTRL__SRCSEL {DPLL} \
CONFIG.PSU__CRF_APB__VPLL_CTRL__DIV2 {1} \
CONFIG.PSU__CRF_APB__VPLL_CTRL__FBDIV {71} \
CONFIG.PSU__CRF_APB__VPLL_CTRL__FRACDATA {0.2871} \
CONFIG.PSU__CRF_APB__VPLL_CTRL__FRACFREQ {300} \
CONFIG.PSU__CRF_APB__VPLL_CTRL__SRCSEL {PSS_REF_CLK} \
CONFIG.PSU__CRF_APB__VPLL_FRAC_CFG__ENABLED {1} \
CONFIG.PSU__CRF_APB__VPLL_TO_LPD_CTRL__DIVISOR0 {3} \
CONFIG.PSU__CRL_APB__ADMA_REF_CTRL__ACT_FREQMHZ {500.000000} \
CONFIG.PSU__CRL_APB__ADMA_REF_CTRL__DIVISOR0 {3} \
CONFIG.PSU__CRL_APB__ADMA_REF_CTRL__SRCSEL {IOPLL} \
CONFIG.PSU__CRL_APB__AFI6_REF_CTRL__DIVISOR0 {3} \
CONFIG.PSU__CRL_APB__AMS_REF_CTRL__ACT_FREQMHZ {51.724136} \
CONFIG.PSU__CRL_APB__AMS_REF_CTRL__DIVISOR0 {29} \
CONFIG.PSU__CRL_APB__AMS_REF_CTRL__DIVISOR1 {1} \
CONFIG.PSU__CRL_APB__AMS_REF_CTRL__SRCSEL {IOPLL} \
CONFIG.PSU__CRL_APB__CAN0_REF_CTRL__DIVISOR0 {15} \
CONFIG.PSU__CRL_APB__CAN0_REF_CTRL__DIVISOR1 {1} \
CONFIG.PSU__CRL_APB__CAN0_REF_CTRL__SRCSEL {IOPLL} \
CONFIG.PSU__CRL_APB__CAN1_REF_CTRL__DIVISOR0 {15} \
CONFIG.PSU__CRL_APB__CAN1_REF_CTRL__DIVISOR1 {1} \
CONFIG.PSU__CRL_APB__CAN1_REF_CTRL__SRCSEL {IOPLL} \
CONFIG.PSU__CRL_APB__CPU_R5_CTRL__ACT_FREQMHZ {500.000000} \
CONFIG.PSU__CRL_APB__CPU_R5_CTRL__DIVISOR0 {3} \
CONFIG.PSU__CRL_APB__CPU_R5_CTRL__SRCSEL {IOPLL} \
CONFIG.PSU__CRL_APB__CSU_PLL_CTRL__ACT_FREQMHZ {500} \
CONFIG.PSU__CRL_APB__CSU_PLL_CTRL__DIVISOR0 {4} \
CONFIG.PSU__CRL_APB__CSU_PLL_CTRL__FREQMHZ {400} \
CONFIG.PSU__CRL_APB__CSU_PLL_CTRL__SRCSEL {IOPLL} \
CONFIG.PSU__CRL_APB__DBG_LPD_CTRL__ACT_FREQMHZ {250.000000} \
CONFIG.PSU__CRL_APB__DBG_LPD_CTRL__DIVISOR0 {6} \
CONFIG.PSU__CRL_APB__DBG_LPD_CTRL__SRCSEL {IOPLL} \
CONFIG.PSU__CRL_APB__DLL_REF_CTRL__ACT_FREQMHZ {1500.000000} \
CONFIG.PSU__CRL_APB__GEM0_REF_CTRL__DIVISOR0 {12} \
CONFIG.PSU__CRL_APB__GEM0_REF_CTRL__DIVISOR1 {1} \
CONFIG.PSU__CRL_APB__GEM0_REF_CTRL__SRCSEL {IOPLL} \
CONFIG.PSU__CRL_APB__GEM1_REF_CTRL__DIVISOR0 {12} \
CONFIG.PSU__CRL_APB__GEM1_REF_CTRL__DIVISOR1 {1} \
CONFIG.PSU__CRL_APB__GEM1_REF_CTRL__SRCSEL {IOPLL} \
CONFIG.PSU__CRL_APB__GEM2_REF_CTRL__DIVISOR0 {12} \
CONFIG.PSU__CRL_APB__GEM2_REF_CTRL__DIVISOR1 {1} \
CONFIG.PSU__CRL_APB__GEM2_REF_CTRL__SRCSEL {IOPLL} \
CONFIG.PSU__CRL_APB__GEM3_REF_CTRL__DIVISOR0 {12} \
CONFIG.PSU__CRL_APB__GEM3_REF_CTRL__DIVISOR1 {1} \
CONFIG.PSU__CRL_APB__GEM3_REF_CTRL__SRCSEL {IOPLL} \
CONFIG.PSU__CRL_APB__GEM_TSU_REF_CTRL__DIVISOR0 {6} \
CONFIG.PSU__CRL_APB__GEM_TSU_REF_CTRL__DIVISOR1 {1} \
CONFIG.PSU__CRL_APB__GEM_TSU_REF_CTRL__SRCSEL {IOPLL} \
CONFIG.PSU__CRL_APB__I2C0_REF_CTRL__DIVISOR0 {15} \
CONFIG.PSU__CRL_APB__I2C0_REF_CTRL__DIVISOR1 {1} \
CONFIG.PSU__CRL_APB__I2C0_REF_CTRL__SRCSEL {IOPLL} \
CONFIG.PSU__CRL_APB__I2C1_REF_CTRL__ACT_FREQMHZ {100.000000} \
CONFIG.PSU__CRL_APB__I2C1_REF_CTRL__DIVISOR0 {15} \
CONFIG.PSU__CRL_APB__I2C1_REF_CTRL__DIVISOR1 {1} \
CONFIG.PSU__CRL_APB__I2C1_REF_CTRL__SRCSEL {IOPLL} \
CONFIG.PSU__CRL_APB__IOPLL_CTRL__DIV2 {0} \
CONFIG.PSU__CRL_APB__IOPLL_CTRL__FBDIV {45} \
CONFIG.PSU__CRL_APB__IOPLL_CTRL__FRACDATA {0} \
CONFIG.PSU__CRL_APB__IOPLL_CTRL__SRCSEL {PSS_REF_CLK} \
CONFIG.PSU__CRL_APB__IOPLL_FRAC_CFG__ENABLED {0} \
CONFIG.PSU__CRL_APB__IOPLL_TO_FPD_CTRL__DIVISOR0 {3} \
CONFIG.PSU__CRL_APB__IOU_SWITCH_CTRL__ACT_FREQMHZ {250.000000} \
CONFIG.PSU__CRL_APB__IOU_SWITCH_CTRL__DIVISOR0 {6} \
CONFIG.PSU__CRL_APB__IOU_SWITCH_CTRL__SRCSEL {IOPLL} \
CONFIG.PSU__CRL_APB__LPD_LSBUS_CTRL__ACT_FREQMHZ {100.000000} \
CONFIG.PSU__CRL_APB__LPD_LSBUS_CTRL__DIVISOR0 {15} \
CONFIG.PSU__CRL_APB__LPD_LSBUS_CTRL__SRCSEL {IOPLL} \
CONFIG.PSU__CRL_APB__LPD_SWITCH_CTRL__ACT_FREQMHZ {500.000000} \
CONFIG.PSU__CRL_APB__LPD_SWITCH_CTRL__DIVISOR0 {3} \
CONFIG.PSU__CRL_APB__LPD_SWITCH_CTRL__SRCSEL {IOPLL} \
CONFIG.PSU__CRL_APB__NAND_REF_CTRL__DIVISOR0 {15} \
CONFIG.PSU__CRL_APB__NAND_REF_CTRL__DIVISOR1 {1} \
CONFIG.PSU__CRL_APB__NAND_REF_CTRL__SRCSEL {IOPLL} \
CONFIG.PSU__CRL_APB__PCAP_CTRL__ACT_FREQMHZ {187.500000} \
CONFIG.PSU__CRL_APB__PCAP_CTRL__DIVISOR0 {8} \
CONFIG.PSU__CRL_APB__PCAP_CTRL__SRCSEL {IOPLL} \
CONFIG.PSU__CRL_APB__PL0_REF_CTRL__ACT_FREQMHZ {100.000000} \
CONFIG.PSU__CRL_APB__PL0_REF_CTRL__DIVISOR0 {15} \
CONFIG.PSU__CRL_APB__PL0_REF_CTRL__DIVISOR1 {1} \
CONFIG.PSU__CRL_APB__PL0_REF_CTRL__SRCSEL {IOPLL} \
CONFIG.PSU__CRL_APB__PL1_REF_CTRL__ACT_FREQMHZ {24.999975} \
CONFIG.PSU__CRL_APB__PL1_REF_CTRL__DIVISOR0 {15} \
CONFIG.PSU__CRL_APB__PL1_REF_CTRL__DIVISOR1 {4} \
CONFIG.PSU__CRL_APB__PL1_REF_CTRL__FREQMHZ {100} \
CONFIG.PSU__CRL_APB__PL1_REF_CTRL__SRCSEL {RPLL} \
CONFIG.PSU__CRL_APB__PL2_REF_CTRL__ACT_FREQMHZ {299.999700} \
CONFIG.PSU__CRL_APB__PL2_REF_CTRL__DIVISOR0 {5} \
CONFIG.PSU__CRL_APB__PL2_REF_CTRL__DIVISOR1 {1} \
CONFIG.PSU__CRL_APB__PL2_REF_CTRL__FREQMHZ {100} \
CONFIG.PSU__CRL_APB__PL2_REF_CTRL__SRCSEL {RPLL} \
CONFIG.PSU__CRL_APB__PL3_REF_CTRL__ACT_FREQMHZ {374.999625} \
CONFIG.PSU__CRL_APB__PL3_REF_CTRL__DIVISOR0 {4} \
CONFIG.PSU__CRL_APB__PL3_REF_CTRL__DIVISOR1 {1} \
CONFIG.PSU__CRL_APB__PL3_REF_CTRL__FREQMHZ {100} \
CONFIG.PSU__CRL_APB__PL3_REF_CTRL__SRCSEL {RPLL} \
CONFIG.PSU__CRL_APB__QSPI_REF_CTRL__DIVISOR0 {12} \
CONFIG.PSU__CRL_APB__QSPI_REF_CTRL__DIVISOR1 {1} \
CONFIG.PSU__CRL_APB__QSPI_REF_CTRL__SRCSEL {IOPLL} \
CONFIG.PSU__CRL_APB__RPLL_CTRL__DIV2 {1} \
CONFIG.PSU__CRL_APB__RPLL_CTRL__FBDIV {70} \
CONFIG.PSU__CRL_APB__RPLL_CTRL__FRACDATA {0.779} \
CONFIG.PSU__CRL_APB__RPLL_CTRL__FRACFREQ {25} \
CONFIG.PSU__CRL_APB__RPLL_CTRL__SRCSEL {PSS_REF_CLK} \
CONFIG.PSU__CRL_APB__RPLL_FRAC_CFG__ENABLED {1} \
CONFIG.PSU__CRL_APB__RPLL_TO_FPD_CTRL__DIVISOR0 {3} \
CONFIG.PSU__CRL_APB__SDIO0_REF_CTRL__ACT_FREQMHZ {187.500000} \
CONFIG.PSU__CRL_APB__SDIO0_REF_CTRL__DIVISOR0 {8} \
CONFIG.PSU__CRL_APB__SDIO0_REF_CTRL__DIVISOR1 {1} \
CONFIG.PSU__CRL_APB__SDIO0_REF_CTRL__SRCSEL {IOPLL} \
CONFIG.PSU__CRL_APB__SDIO1_REF_CTRL__ACT_FREQMHZ {187.500000} \
CONFIG.PSU__CRL_APB__SDIO1_REF_CTRL__DIVISOR0 {8} \
CONFIG.PSU__CRL_APB__SDIO1_REF_CTRL__DIVISOR1 {1} \
CONFIG.PSU__CRL_APB__SDIO1_REF_CTRL__SRCSEL {IOPLL} \
CONFIG.PSU__CRL_APB__SPI0_REF_CTRL__ACT_FREQMHZ {187.500000} \
CONFIG.PSU__CRL_APB__SPI0_REF_CTRL__DIVISOR0 {8} \
CONFIG.PSU__CRL_APB__SPI0_REF_CTRL__DIVISOR1 {1} \
CONFIG.PSU__CRL_APB__SPI0_REF_CTRL__SRCSEL {IOPLL} \
CONFIG.PSU__CRL_APB__SPI1_REF_CTRL__ACT_FREQMHZ {187.500000} \
CONFIG.PSU__CRL_APB__SPI1_REF_CTRL__DIVISOR0 {8} \
CONFIG.PSU__CRL_APB__SPI1_REF_CTRL__DIVISOR1 {1} \
CONFIG.PSU__CRL_APB__SPI1_REF_CTRL__SRCSEL {IOPLL} \
CONFIG.PSU__CRL_APB__TIMESTAMP_REF_CTRL__ACT_FREQMHZ {100.000000} \
CONFIG.PSU__CRL_APB__TIMESTAMP_REF_CTRL__DIVISOR0 {15} \
CONFIG.PSU__CRL_APB__TIMESTAMP_REF_CTRL__SRCSEL {IOPLL} \
CONFIG.PSU__CRL_APB__UART0_REF_CTRL__ACT_FREQMHZ {100.000000} \
CONFIG.PSU__CRL_APB__UART0_REF_CTRL__DIVISOR0 {15} \
CONFIG.PSU__CRL_APB__UART0_REF_CTRL__DIVISOR1 {1} \
CONFIG.PSU__CRL_APB__UART0_REF_CTRL__SRCSEL {IOPLL} \
CONFIG.PSU__CRL_APB__UART1_REF_CTRL__ACT_FREQMHZ {100.000000} \
CONFIG.PSU__CRL_APB__UART1_REF_CTRL__DIVISOR0 {15} \
CONFIG.PSU__CRL_APB__UART1_REF_CTRL__DIVISOR1 {1} \
CONFIG.PSU__CRL_APB__UART1_REF_CTRL__SRCSEL {IOPLL} \
CONFIG.PSU__CRL_APB__USB0_BUS_REF_CTRL__ACT_FREQMHZ {250.000000} \
CONFIG.PSU__CRL_APB__USB0_BUS_REF_CTRL__DIVISOR0 {6} \
CONFIG.PSU__CRL_APB__USB0_BUS_REF_CTRL__DIVISOR1 {1} \
CONFIG.PSU__CRL_APB__USB0_BUS_REF_CTRL__FREQMHZ {250} \
CONFIG.PSU__CRL_APB__USB0_BUS_REF_CTRL__SRCSEL {IOPLL} \
CONFIG.PSU__CRL_APB__USB1_BUS_REF_CTRL__ACT_FREQMHZ {250.000000} \
CONFIG.PSU__CRL_APB__USB1_BUS_REF_CTRL__DIVISOR0 {6} \
CONFIG.PSU__CRL_APB__USB1_BUS_REF_CTRL__DIVISOR1 {1} \
CONFIG.PSU__CRL_APB__USB1_BUS_REF_CTRL__SRCSEL {IOPLL} \
CONFIG.PSU__CRL_APB__USB3_DUAL_REF_CTRL__ACT_FREQMHZ {20.000000} \
CONFIG.PSU__CRL_APB__USB3_DUAL_REF_CTRL__DIVISOR0 {5} \
CONFIG.PSU__CRL_APB__USB3_DUAL_REF_CTRL__DIVISOR1 {15} \
CONFIG.PSU__CRL_APB__USB3_DUAL_REF_CTRL__FREQMHZ {20} \
CONFIG.PSU__CRL_APB__USB3_DUAL_REF_CTRL__SRCSEL {IOPLL} \
CONFIG.PSU__CRL_APB__USB3__ENABLE {1} \
CONFIG.PSU__CSUPMU__PERIPHERAL__VALID {1} \
CONFIG.PSU__DDRC__ADDR_MIRROR {1} \
CONFIG.PSU__DDRC__AL {0} \
CONFIG.PSU__DDRC__BANK_ADDR_COUNT {3} \
CONFIG.PSU__DDRC__BG_ADDR_COUNT {NA} \
CONFIG.PSU__DDRC__BRC_MAPPING {ROW_BANK_COL} \
CONFIG.PSU__DDRC__BUS_WIDTH {32 Bit} \
CONFIG.PSU__DDRC__CL {NA} \
CONFIG.PSU__DDRC__CLOCK_STOP_EN {0} \
CONFIG.PSU__DDRC__COL_ADDR_COUNT {10} \
CONFIG.PSU__DDRC__COMPONENTS {Components} \
CONFIG.PSU__DDRC__CWL {NA} \
CONFIG.PSU__DDRC__DDR3L_T_REF_RANGE {NA} \
CONFIG.PSU__DDRC__DDR3_T_REF_RANGE {NA} \
CONFIG.PSU__DDRC__DDR4_ADDR_MAPPING {NA} \
CONFIG.PSU__DDRC__DDR4_CAL_MODE_ENABLE {NA} \
CONFIG.PSU__DDRC__DDR4_CRC_CONTROL {NA} \
CONFIG.PSU__DDRC__DDR4_MAXPWR_SAVING_EN {NA} \
CONFIG.PSU__DDRC__DDR4_T_REF_MODE {NA} \
CONFIG.PSU__DDRC__DDR4_T_REF_RANGE {NA} \
CONFIG.PSU__DDRC__DEEP_PWR_DOWN_EN {0} \
CONFIG.PSU__DDRC__DEVICE_CAPACITY {16384 MBits} \
CONFIG.PSU__DDRC__DIMM_ADDR_MIRROR {0} \
CONFIG.PSU__DDRC__DM_DBI {DM_NO_DBI} \
CONFIG.PSU__DDRC__DQMAP_0_3 {0} \
CONFIG.PSU__DDRC__DQMAP_12_15 {0} \
CONFIG.PSU__DDRC__DQMAP_16_19 {0} \
CONFIG.PSU__DDRC__DQMAP_20_23 {0} \
CONFIG.PSU__DDRC__DQMAP_24_27 {0} \
CONFIG.PSU__DDRC__DQMAP_28_31 {0} \
CONFIG.PSU__DDRC__DQMAP_32_35 {0} \
CONFIG.PSU__DDRC__DQMAP_36_39 {0} \
CONFIG.PSU__DDRC__DQMAP_40_43 {0} \
CONFIG.PSU__DDRC__DQMAP_44_47 {0} \
CONFIG.PSU__DDRC__DQMAP_48_51 {0} \
CONFIG.PSU__DDRC__DQMAP_4_7 {0} \
CONFIG.PSU__DDRC__DQMAP_52_55 {0} \
CONFIG.PSU__DDRC__DQMAP_56_59 {0} \
CONFIG.PSU__DDRC__DQMAP_60_63 {0} \
CONFIG.PSU__DDRC__DQMAP_64_67 {0} \
CONFIG.PSU__DDRC__DQMAP_68_71 {0} \
CONFIG.PSU__DDRC__DQMAP_8_11 {0} \
CONFIG.PSU__DDRC__DRAM_WIDTH {32 Bits} \
CONFIG.PSU__DDRC__ECC {Disabled} \
CONFIG.PSU__DDRC__ENABLE_2T_TIMING {0} \
CONFIG.PSU__DDRC__ENABLE_DP_SWITCH {1} \
CONFIG.PSU__DDRC__ENABLE_LP4_HAS_ECC_COMP {0} \
CONFIG.PSU__DDRC__ENABLE_LP4_SLOWBOOT {0} \
CONFIG.PSU__DDRC__FGRM {NA} \
CONFIG.PSU__DDRC__LPDDR3_T_REF_RANGE {NA} \
CONFIG.PSU__DDRC__LPDDR4_T_REF_RANGE {High (95 Max)} \
CONFIG.PSU__DDRC__LP_ASR {NA} \
CONFIG.PSU__DDRC__MEMORY_TYPE {LPDDR 4} \
CONFIG.PSU__DDRC__PARITY_ENABLE {NA} \
CONFIG.PSU__DDRC__PER_BANK_REFRESH {0} \
CONFIG.PSU__DDRC__PHY_DBI_MODE {0} \
CONFIG.PSU__DDRC__RANK_ADDR_COUNT {0} \
CONFIG.PSU__DDRC__ROW_ADDR_COUNT {16} \
CONFIG.PSU__DDRC__SB_TARGET {NA} \
CONFIG.PSU__DDRC__SELF_REF_ABORT {NA} \
CONFIG.PSU__DDRC__SPEED_BIN {LPDDR4_1066} \
CONFIG.PSU__DDRC__STATIC_RD_MODE {0} \
CONFIG.PSU__DDRC__TRAIN_DATA_EYE {1} \
CONFIG.PSU__DDRC__TRAIN_READ_GATE {1} \
CONFIG.PSU__DDRC__TRAIN_WRITE_LEVEL {1} \
CONFIG.PSU__DDRC__T_FAW {40.0} \
CONFIG.PSU__DDRC__T_RAS_MIN {42} \
CONFIG.PSU__DDRC__T_RC {63} \
CONFIG.PSU__DDRC__T_RCD {10} \
CONFIG.PSU__DDRC__T_RP {12} \
CONFIG.PSU__DDRC__VENDOR_PART {OTHERS} \
CONFIG.PSU__DDRC__VREF {0} \
CONFIG.PSU__DDR_HIGH_ADDRESS_GUI_ENABLE {0} \
CONFIG.PSU__DDR_QOS_ENABLE {1} \
...
This file has been truncated, please download it to see its full contents.
Comments