element14 Community
element14 Community
    Register Log In
  • Site
  • Search
  • Log In Register
  • Community Hub
    Community Hub
    • What's New on element14
    • Feedback and Support
    • Benefits of Membership
    • Personal Blogs
    • Members Area
    • Achievement Levels
  • Learn
    Learn
    • Ask an Expert
    • eBooks
    • element14 presents
    • Learning Center
    • Tech Spotlight
    • STEM Academy
    • Webinars, Training and Events
    • Learning Groups
  • Technologies
    Technologies
    • 3D Printing
    • FPGA
    • Industrial Automation
    • Internet of Things
    • Power & Energy
    • Sensors
    • Technology Groups
  • Challenges & Projects
    Challenges & Projects
    • Design Challenges
    • element14 presents Projects
    • Project14
    • Arduino Projects
    • Raspberry Pi Projects
    • Project Groups
  • Products
    Products
    • Arduino
    • Avnet Boards Community
    • Dev Tools
    • Manufacturers
    • Multicomp Pro
    • Product Groups
    • Raspberry Pi
    • RoadTests & Reviews
  • About Us
  • Store
    Store
    • Visit Your Store
    • Choose another store...
      • Europe
      •  Austria (German)
      •  Belgium (Dutch, French)
      •  Bulgaria (Bulgarian)
      •  Czech Republic (Czech)
      •  Denmark (Danish)
      •  Estonia (Estonian)
      •  Finland (Finnish)
      •  France (French)
      •  Germany (German)
      •  Hungary (Hungarian)
      •  Ireland
      •  Israel
      •  Italy (Italian)
      •  Latvia (Latvian)
      •  
      •  Lithuania (Lithuanian)
      •  Netherlands (Dutch)
      •  Norway (Norwegian)
      •  Poland (Polish)
      •  Portugal (Portuguese)
      •  Romania (Romanian)
      •  Russia (Russian)
      •  Slovakia (Slovak)
      •  Slovenia (Slovenian)
      •  Spain (Spanish)
      •  Sweden (Swedish)
      •  Switzerland(German, French)
      •  Turkey (Turkish)
      •  United Kingdom
      • Asia Pacific
      •  Australia
      •  China
      •  Hong Kong
      •  India
      •  Korea (Korean)
      •  Malaysia
      •  New Zealand
      •  Philippines
      •  Singapore
      •  Taiwan
      •  Thailand (Thai)
      • Americas
      •  Brazil (Portuguese)
      •  Canada
      •  Mexico (Spanish)
      •  United States
      Can't find the country/region you're looking for? Visit our export site or find a local distributor.
  • Translate
  • Profile
  • Settings
FPGA
  • Technologies
  • More
FPGA
Forum How to write the contents of a text file to DDR RAM on the Arty S7-50 board (or any fpga)?
  • Blog
  • Forum
  • Documents
  • Quiz
  • Events
  • Polls
  • Files
  • Members
  • Mentions
  • Sub-Groups
  • Tags
  • More
  • Cancel
  • New
Join FPGA to participate - click to join for free!
Actions
  • Share
  • More
  • Cancel
Forum Thread Details
  • State Verified Answer
  • Replies 12 replies
  • Subscribers 554 subscribers
  • Views 7509 views
  • Users 0 members are here
  • xilinx
  • fpga
  • vivado
  • spartan-7
  • Arty S7 50
  • vitis
  • Spartan_Migration
Related

How to write the contents of a text file to DDR RAM on the Arty S7-50 board (or any fpga)?

cbohra00627
cbohra00627 over 3 years ago

I am trying to load a image directly to the DDR SDRAM on the Art S7 board. I have converted the jpg image into a txt file containing the integer RGB values for each pixel in separate lines. The file is as shown below:

goku.txt

Then I created a block design in vivado for microcontroller preset with uartlite and the MIG as shown below and programmed my fpga board with this design.

Block Design

Now, I am trying to open a file in Vitis and load the contents of the file byte by byte into the SDRAM memory locations with the code given below:

#include <stdio.h>
#include <stdlib.h>
#include "platform.h"
#include "xparameters.h"
#include "xil_io.h"
#include "xil_printf.h"

int main() {

	char line[2];
	int num = 0;
	int num_rec = 0;
	int i = 0;

	FILE *source = fopen("C:/Users/Chinmay/Desktop/goku.txt", "r");
	FILE *target = fopen("C:/Users/Chinmay/Desktop/goku_vitis.txt", "w");

	if ((source == NULL) || (target == NULL)) {
		xil_printf("File Failure");
		exit(1);
	}

	init_platform();

	while (fscanf(source, "%s", line) == 1) {
		num = atoi(line);
		Xil_Out8(XPAR_MIG7SERIES_0_BASEADDR + i, num);
		i++;
	}

	for (long int j=0; j<4; j++) {
		num_rec = Xil_In8(XPAR_MIG7SERIES_0_BASEADDR + j);
		fprintf(target, "%d\n", num_rec);
	}

	cleanup_platform();

	fclose(source);
	fclose(target);

	return 0;
}

Now, I doubt that my approach is wrong. In fact, I am getting some error when I try to build this code in vitis. The console output is given below:

22:44:58 **** Incremental Build of configuration Debug for project MIG1 ****
make all 
'Building file: ../src/main.cpp'
'Invoking: MicroBlaze g++ compiler'
mb-g++ -Wall -O0 -g3 -c -fmessage-length=0 -MT"src/main.o" -IC:/Users/Chinmay/Desktop/Verilog_Vivado/MIG1_Vitis/MIG1_wrapper/export/MIG1_wrapper/sw/MIG1_wrapper/standalone_microblaze_0/bspinclude/include -mno-xl-reorder -mlittle-endian -mxl-barrel-shift -mxl-pattern-compare -mcpu=v11.0 -mno-xl-soft-mul -Wl,--no-relax -ffunction-sections -fdata-sections -MMD -MP -MF"src/main.d" -MT"src/main.o" -o "src/main.o" "../src/main.cpp"
'Finished building: ../src/main.cpp'
' '
'Building target: MIG1.elf'
'Invoking: MicroBlaze g++ linker'
mb-g++ -Wl,-T -Wl,../src/lscript.ld -LC:/Users/Chinmay/Desktop/Verilog_Vivado/MIG1_Vitis/MIG1_wrapper/export/MIG1_wrapper/sw/MIG1_wrapper/standalone_microblaze_0/bsplib/lib -mlittle-endian -mxl-barrel-shift -mxl-pattern-compare -mcpu=v11.0 -mno-xl-soft-mul -Wl,--no-relax -Wl,--gc-sections -o "MIG1.elf"  ./src/main.o ./src/platform.o   -Wl,--start-group,-lxil,-lgcc,-lc,-lstdc++,--end-group
d:/xilinx/vitis/2021.2/gnu/microblaze/nt/x86_64-oesdk-mingw32/usr/bin/microblaze-xilinx-elf/../../libexec/microblaze-xilinx-elf/gcc/microblaze-xilinx-elf/10.2.0/real-ld.exe: MIG1.elf section `.text' will not fit in region `microblaze_0_local_memory_ilmb_bram_if_cntlr_Mem_microblaze_0_local_memory_dlmb_bram_if_cntlr_Mem'
d:/xilinx/vitis/2021.2/gnu/microblaze/nt/x86_64-oesdk-mingw32/usr/bin/microblaze-xilinx-elf/../../libexec/microblaze-xilinx-elf/gcc/microblaze-xilinx-elf/10.2.0/real-ld.exe: region `microblaze_0_local_memory_ilmb_bram_if_cntlr_Mem_microblaze_0_local_memory_dlmb_bram_if_cntlr_Mem' overflowed by 88968 bytes
collect2.exe: error: ld returned 1 exit status
make: *** [makefile:50: MIG1.elf] Error 1

22:45:00 Build Finished (took 1s.910ms)

At the end of the 12th line, it says "region `microblaze_0_local_memory_ilmb_bram_if_cntlr_Mem_microblaze_0_local_memory_dlmb_bram_if_cntlr_Mem' overflowed by 88968 bytes". So, my guess is that when I try to open the file, it first gets loaded into the BRAM which has less capacity than the file itself. Well, I might be wrong because when I tried to load a small 1KB file, it showed the same error.

I am stuck here. Is there any way through which I can load my file directly into the SDRAM? The size of my file is around 8MBs.

Actually I am trying to implement image processing on FPGA. I need to load an image on the board, then I will make a image processing IP in vitis HLS and use it in my design.

  • Sign in to reply
  • Cancel

Top Replies

  • saadtiwana_int
    saadtiwana_int over 3 years ago in reply to cbohra00627 +2 verified
    On your linker script screenshot, as i remember, the "memory region" values are drop-down items. Right now everything is assigned to be saved to bram (as you can see in your screenshot). You can use the…
  • Metaforest
    Metaforest over 3 years ago +2
    Make sure you have built and run the memory and platform test projects. Make sure you understand how they work. Including the base address configuration in your Object diagram. Prove you can read and write…
  • saadtiwana_int
    saadtiwana_int over 3 years ago in reply to cbohra00627 +1
    Glad it worked for you. So one way that i can think of to know where your array is stored at, is by looking the address of the variable. In one of the screenshots you shared above, the bram has the address…
Parents
  • saadtiwana_int
    0 saadtiwana_int over 3 years ago

    Hi,

    I think there are few issues with your approach:

    1. The file exists on your PC, but the code will run on the FPGA, which will not have the file. Instead, better to convert the image to an array that you can put inside a header file and include that in your code.

    2. Have a look at the project's linker script to see where different parts of the code/data are going in terms of memory. You need to be sure that you know where your image is going. 

    I don't have my Xilinx tools in front of me right now (moving apartment),so can't go into too many specific details. Hope the hints above will be somewhat helpful to you!


    Best Regards,
    Saad

    • Cancel
    • Vote Up 0 Vote Down
    • Sign in to reply
    • Verify Answer
    • Cancel
  • cbohra00627
    0 cbohra00627 over 3 years ago in reply to saadtiwana_int

    Thanks for giving the idea. I tried loading the image array into memory but I am still getting the same error. But this time, it overflowed by 9554696 bytes:

    08:59:38 **** Incremental Build of configuration Debug for project MIG1 ****
    make all 
    'Building file: ../src/main.cpp'
    'Invoking: MicroBlaze g++ compiler'
    mb-g++ -Wall -O0 -g3 -c -fmessage-length=0 -MT"src/main.o" -IC:/Users/Chinmay/Desktop/Verilog_Vivado/MIG1_Vitis/MIG1_wrapper/export/MIG1_wrapper/sw/MIG1_wrapper/standalone_microblaze_0/bspinclude/include -mno-xl-reorder -mlittle-endian -mxl-barrel-shift -mxl-pattern-compare -mcpu=v11.0 -mno-xl-soft-mul -Wl,--no-relax -ffunction-sections -fdata-sections -MMD -MP -MF"src/main.d" -MT"src/main.o" -o "src/main.o" "../src/main.cpp"
    'Finished building: ../src/main.cpp'
    ' '
    'Building target: MIG1.elf'
    'Invoking: MicroBlaze g++ linker'
    mb-g++ -Wl,-T -Wl,../src/lscript.ld -LC:/Users/Chinmay/Desktop/Verilog_Vivado/MIG1_Vitis/MIG1_wrapper/export/MIG1_wrapper/sw/MIG1_wrapper/standalone_microblaze_0/bsplib/lib -mlittle-endian -mxl-barrel-shift -mxl-pattern-compare -mcpu=v11.0 -mno-xl-soft-mul -Wl,--no-relax -Wl,--gc-sections -o "MIG1.elf"  ./src/main.o ./src/platform.o   -Wl,--start-group,-lxil,-lgcc,-lc,-lstdc++,--end-group
    d:/xilinx/vitis/2021.2/gnu/microblaze/nt/x86_64-oesdk-mingw32/usr/bin/microblaze-xilinx-elf/../../libexec/microblaze-xilinx-elf/gcc/microblaze-xilinx-elf/10.2.0/real-ld.exe: MIG1.elf section `.data' will not fit in region `microblaze_0_local_memory_ilmb_bram_if_cntlr_Mem_microblaze_0_local_memory_dlmb_bram_if_cntlr_Mem'
    d:/xilinx/vitis/2021.2/gnu/microblaze/nt/x86_64-oesdk-mingw32/usr/bin/microblaze-xilinx-elf/../../libexec/microblaze-xilinx-elf/gcc/microblaze-xilinx-elf/10.2.0/real-ld.exe: region `microblaze_0_local_memory_ilmb_bram_if_cntlr_Mem_microblaze_0_local_memory_dlmb_bram_if_cntlr_Mem' overflowed by 9554696 bytes
    collect2.exe: error: ld returned 1 exit status
    make: *** [makefile:50: MIG1.elf] Error 1
    
    08:59:45 Build Finished (took 6s.499ms)
    
    

    I made a header file to store my image array as you said. Actually my image array has a total of 798480 elements which is pretty high.

    Header

    This is the code that I am trying to build:

    #include "platform.h"
    #include "xparameters.h"
    #include "xil_io.h"
    #include "xil_printf.h"
    #include "data.h"
    
    int main() {
    
    
    
    	init_platform();
    
    	for (long int i=0; i<798481; i++) {
    		Xil_Out8(XPAR_MIG7SERIES_0_BASEADDR + (3*i), data[i][0]);
    		Xil_Out8(XPAR_MIG7SERIES_0_BASEADDR + (3*i + 1), data[i][1]);
    		Xil_Out8(XPAR_MIG7SERIES_0_BASEADDR + (3*i + 2), data[i][2]);
    	}
    
    	cleanup_platform();
    
    	return 0;
    }
    

    Here is a screenshot of the linker script (if this is the right one!):

    Linker Script

    It seems, all of my data wants to get stored in the BRAM.

    Is there any way to change that to SDRAM?

    • Cancel
    • Vote Up 0 Vote Down
    • Sign in to reply
    • Verify Answer
    • Cancel
  • saadtiwana_int
    +1 saadtiwana_int over 3 years ago in reply to cbohra00627

    On your linker script screenshot, as i remember, the "memory region" values are drop-down items. Right now everything is assigned to be saved to bram (as you can see in your screenshot). You can use the drop down to change the relevant ones to DDR instead. Try moving the following to DDR:
    .heap
    .stack
    .data
    .text

    See if it works? Again, sorry I don't have access to my tools right now, so my help is limited.

    Regards,
    Saad

    • Cancel
    • Vote Up +2 Vote Down
    • Sign in to reply
    • Reject Answer
    • Cancel
  • cbohra00627
    0 cbohra00627 over 3 years ago in reply to saadtiwana_int

    Oh, you don't need tools. It worked. It built successfully.

    So, does it mean that now my array will be stored in DDR instead of BRAM? Is there any way by which I can know between which addresses is this array getting stored on DDR?

    Now, if the array is already stored on the DDR, I don't need to store it again byte by byte using the Xil_Out8() as I was trying in  my code earlier, right?

    • Cancel
    • Vote Up 0 Vote Down
    • Sign in to reply
    • Verify Answer
    • Cancel
  • saadtiwana_int
    0 saadtiwana_int over 3 years ago in reply to cbohra00627

    Glad it worked for you.

    So one way that i can think of to know where your array is stored at, is by looking the address of the variable. In one of the screenshots you shared above, the bram has the address range in the beginning (I cannot read the exact) and then the DDR (mig_7series_0_memaddr) start at 0x80000000. So if the address of the variable pointer is 0x80000000 above, then it's getting stored in DDR. And in that case, it's already have it in RAM, so don't need to store it again :)

    • Cancel
    • Vote Up +1 Vote Down
    • Sign in to reply
    • Verify Answer
    • Cancel
Reply
  • saadtiwana_int
    0 saadtiwana_int over 3 years ago in reply to cbohra00627

    Glad it worked for you.

    So one way that i can think of to know where your array is stored at, is by looking the address of the variable. In one of the screenshots you shared above, the bram has the address range in the beginning (I cannot read the exact) and then the DDR (mig_7series_0_memaddr) start at 0x80000000. So if the address of the variable pointer is 0x80000000 above, then it's getting stored in DDR. And in that case, it's already have it in RAM, so don't need to store it again :)

    • Cancel
    • Vote Up +1 Vote Down
    • Sign in to reply
    • Verify Answer
    • Cancel
Children
  • cbohra00627
    0 cbohra00627 over 3 years ago in reply to saadtiwana_int

    OK, Thank You very much!

    • Cancel
    • Vote Up 0 Vote Down
    • Sign in to reply
    • Verify Answer
    • Cancel
  • cbohra00627
    0 cbohra00627 over 3 years ago in reply to saadtiwana_int

    I tried to initialize a variable and read it back after doing the changes in the linker file as you said but now when I run my code on the hardware, the terminal doesn't show anything. The terminal remains blank. I am not able to print any value on terminal Moreover I am not even able to get values directly from memory locations using Xil_In8() but strangely when I select BRAM for all the options in the linker file, the same code words fine!

    #include "platform.h"
    #include "xparameters.h"
    #include "xil_io.h"
    #include "xil_printf.h"
    //#include "data.h"
    
    int main() {
    
    	int x = 5;
    
    	init_platform();
    
    	int y = 6;
    	int num;
    
    	num = Xil_In8(0x80001000);
    
    	xil_printf("%d %d %d",x, y, num);
    
    	cleanup_platform();
    
    	return 0;
    }
    

    • Cancel
    • Vote Up 0 Vote Down
    • Sign in to reply
    • Verify Answer
    • Cancel
  • cbohra00627
    0 cbohra00627 over 3 years ago in reply to cbohra00627

    Well, its solved now. I just had to enable AXI peripheral interface in the microblaze customize IP window.

    • Cancel
    • Vote Up +1 Vote Down
    • Sign in to reply
    • Verify Answer
    • Cancel
element14 Community

element14 is the first online community specifically for engineers. Connect with your peers and get expert answers to your questions.

  • Members
  • Learn
  • Technologies
  • Challenges & Projects
  • Products
  • Store
  • About Us
  • Feedback & Support
  • FAQs
  • Terms of Use
  • Privacy Policy
  • Legal and Copyright Notices
  • Sitemap
  • Cookies

An Avnet Company © 2025 Premier Farnell Limited. All Rights Reserved.

Premier Farnell Ltd, registered in England and Wales (no 00876412), registered office: Farnell House, Forge Lane, Leeds LS12 2NE.

ICP 备案号 10220084.

Follow element14

  • X
  • Facebook
  • linkedin
  • YouTube