Porting to STM32F429, where to increase code size?

Discussion and questions about boards that can run MicroPython but don't have a dedicated forum.
Target audience: Everyone interested in running MicroPython on other hardware.
kylesat
Posts: 5
Joined: Tue Mar 24, 2015 5:20 pm
Location: Mountain View, CA, USA

Porting to STM32F429, where to increase code size?

Post by kylesat » Fri Jun 26, 2015 12:12 am

Hello,

I have been working on porting micropython to run on the STM32F429 Discovery board. I have read about others attempting to do so with some limited success:
* http://forum.micropython.org/viewtopic. ... STM32F429i
* http://forum.micropython.org/viewtopic. ... =STM32F429

However, I have gotten past the USB issues by simply making a custom USB cable and connecting it to the header pins PA10, PA11, PA9, 5V, and GND. To enter DFU mode I simply place jumpers across the header pins (VDD and BOOT0) and (PB2 and GND). This works and I am able to program the device with dfu-utils without any issue. The REPL then comes up on my custom USB cable even using either the PYBV10 or STM32F4DISC projects.

My main goal is to try and prove that micropython can utilize the extra 1MB of flash space (vs. the pyboard's STM32F05's flash space) because our current micropython project is running into code space limitations. No matter what I try, the board comes up with the "standard" 96KB of code space (looking like a flash drive in Windows). I have tried modifying the following files:
1. Created a new file "stm32f429.ld" based on "stm32f405.ld" but changed the following lines:

Code: Select all

FLASH (rx)      : ORIGIN = 0x08000000, LENGTH = 0x200000 /* entire flash, 2 MiB */

Code: Select all

FLASH_TEXT (rx) : ORIGIN = 0x08020000, LENGTH = 0x100000 /* sectors 5,6,7,8, 4*128KiB = 512 KiB (could increase it more) */
2. Changed the following line in the "stm32f4xx_hal_conf.h":

Code: Select all

#define STM32F405xx

to

Code: Select all

#define STM32F429xx
3. In "storage.c" added a case statement for the STM32F429xx:
In this code I also increased the number of blocks (to try and see any sort of increase in code availability of code space).

Code: Select all

...
#elif defined(STM32F429xx)

#define CACHE_MEM_START_ADDR (0x10000000) // CCM data RAM, 64k
#define FLASH_PART1_START_BLOCK (0x100)
#define FLASH_PART1_NUM_BLOCKS (300) // 16k+16k+16k+64k=112k
#define FLASH_MEM_START_ADDR (0x08004000) // sector 1, 16k
#define FLASH_SECTOR_SIZE_MAX (0x10000) // 64k max, size of CCM
The code compiles, creates a DFU file, and loads properly. However, I still see 96KB as the available size for code. What else do I need to configure? I'm obviously missing something. Any tips/pointers would be much appreciated.

Thanks,
- Kyle

P.S. I will attempt to post a reply to this with a photo of my test setup (in case that helps anyone else in the future).

User avatar
dhylands
Posts: 3228
Joined: Mon Jan 06, 2014 6:08 pm
Location: Peachland, BC, Canada
Contact:

Re: Porting to STM32F429, where to increase code size?

Post by dhylands » Fri Jun 26, 2015 1:21 am

On the 405, the flash memory is arranged as 4 x 16K sectors, 1 x 64K sector, with the remaining sectors as 128K sectors.

It looks like the 429 has 2 banks which are similarly arranged.

In order to use flash sectors as part of the file system, there needs to be a RAM buffer which is big enough to store the sector which is being written. So this means that only 16K and 64K sectors can be used as part of the filesystem. Further, the very first 16K sector has the interrupt vectors in it so it can't be used as part of the file system.

For the 405, this then limits the filesystem to 112K, which is 3 x 16K + 1 x 64K.

On the 429, sectors 12, 13, 14, and 15 are 16K each, and sector 16 is 64K. So it should be possible to include those into the filesystem, giving a total of 112 + 128 = 240K.

This will require some changes in stmhal/storage.c and also the linker map (to prevent code from overlapping with the filesystem).

kylesat
Posts: 5
Joined: Tue Mar 24, 2015 5:20 pm
Location: Mountain View, CA, USA

Re: Porting to STM32F429, where to increase code size?

Post by kylesat » Fri Jun 26, 2015 8:32 pm

Thanks for your response.

This morning I did some more edits in storage.c and in flash.c -- still without any effect. When you say "the linker map" is this just the *.ld file or somewhere else as well?

This is my first real dive into the micropython environment itself so I'm still trying to figure out what all the internal pieces are and how they actually fit together.

Here is a photo of my setup:
IMG_DISC_DFU_USB_small.jpeg
IMG_DISC_DFU_USB_small.jpeg (222.67 KiB) Viewed 5705 times

User avatar
dhylands
Posts: 3228
Joined: Mon Jan 06, 2014 6:08 pm
Location: Peachland, BC, Canada
Contact:

Re: Porting to STM32F429, where to increase code size?

Post by dhylands » Fri Jun 26, 2015 10:28 pm

Yeah - linker map is the incorrect term, I should have said linker script, which is the .ld file.

The code also now supports frozen modules, which is basically copying python source code and linking it into the image portion of the file.

So the disadvantage of using frozen modules is that you need to reflash the firmware to update them. The advantage is that they don't take up space in the file system.

As long as the code is small enough, you can probably get away without having to change the linker script. Modifying the linker script would allow you to detect when you get more than (1Mb - 128K) of code.

Damien
Site Admin
Posts: 619
Joined: Mon Dec 09, 2013 5:02 pm

Re: Porting to STM32F429, where to increase code size?

Post by Damien » Sat Jun 27, 2015 9:34 pm

As Dave suggests, you can try using frozen modules to put your code (or at least modules that don't change much) in the actual firmware (ie in the dfu file). See tools/make-frozen.py.

The other option is to use more of the flash pages for the filesystem. You can actually use a 128k page, but only the first 64k of it will be used for filesystem data. This is how the F401 and F411 ports work: they only have a 16k buffer so can only use 16k of a page. Their page layout for the filesystem is to use 3 of the 16k pages, then 16k of the following 64k page. You can do the same with the F429: use 3 16k pages, then 1 64k page, then 64k of the following 128k page. To do this increase FLASH_PART1_NUM_BLOCKS to 352 and make FLASH_TEXT in stm32f405.ld have ORIGIN=0x08040000 (to start after the bigger filesystem).

If you want more than that then you'll need to split the storage into separate sections. As Dave says, there are other 16k pages that are not adjacent to the first set of 16k pages, and you can use them but it'll require a bit of coding to split the storage sections.

Damien
Site Admin
Posts: 619
Joined: Mon Dec 09, 2013 5:02 pm

Re: Porting to STM32F429, where to increase code size?

Post by Damien » Sat Jun 27, 2015 10:32 pm

I just added some code to storage.c that allows you to increase the amount of flash used for the filesystem. Specifically you can split the filesystem over 2 separate regions of the flash; eg sectors 1-4 and sector 11.

kylesat
Posts: 5
Joined: Tue Mar 24, 2015 5:20 pm
Location: Mountain View, CA, USA

Re: Porting to STM32F429, where to increase code size?

Post by kylesat » Mon Jun 29, 2015 6:22 pm

Hey guys -- Thank you for pointing me to the frozen modules, I will certainly need to take a closer look at this approach. It sounds like something that would be workable for my project.

I downloaded the latest code this morning and enabled your changes in storage.c. I didn't see any change on my STM32F429DISC board. But based on your comments and reading the code it was apparent that these changes would enable a bit more space on the standard PyBoard V10, so I did a DFU update to my Pyboard. I again saw no immediate changes. But then I thought to do a "factory reset" following the procedure here:
* http://docs.micropython.org/en/latest/t ... filesystem

After this the Pyboard came back up with a larger flash drive space. I was then able to load all of my current project's code onto the Pyboard.

Thank you!

Now my main questions are:
1. How do I "factory reset" my STM32F429 Discovery board?
2. Is it possible with either dfu-util or DfuSe to force the equivalent of a "factory reset" so that any modifications in the flash sectors, etc are automatically updated? (obviously erasing whatever files previously existed).

I'm now thinking that some of my previous modifications were maybe working but not really taking effect without the force of a "factory reset".

Thanks
Attachments
pyboard_more_memory2.png
pyboard_more_memory2.png (12.85 KiB) Viewed 5640 times

User avatar
dhylands
Posts: 3228
Joined: Mon Jan 06, 2014 6:08 pm
Location: Peachland, BC, Canada
Contact:

Re: Porting to STM32F429, where to increase code size?

Post by dhylands » Mon Jun 29, 2015 7:09 pm

If you do the following, then it will effectively cause the pyboard to initialize the internal flash drive:

Code: Select all

echo -e -n "\xff" > ff.bin
dfu-util -s 0x08004000:leave -a 0 -d 0483:df11 -D ff.bin
The internal flash drive starts at sector 1, which is at address 0x08004000.

By writing a single 0xff we cause the entire first sector (which is 16K) to be erased. This in turns wipes out all of the header information that the FatFS expects. So the pyboard sees the internal flash as invalid, and reinitializes everything from scratch.

The :leave option tells dfu-util to exit when done and run the internal firmware. This requires dfu-util >= 0.7. If your dfu-util is earlier, just drop the :leave.

I was also able to use:

Code: Select all

dfu-util -s :mass-erase:force -a 0 -d 0483:df11 -D build-PYBV10/firmware.dfu
dfu-util says that it failed, but I think it actually performed the mass erase and timed out waiting for a reply. Pressing the reset button after this leaves the board in a hooped mode (I had to use the BOOT0/Reset to get back into DFU mode), and if I then flash the firmware, then the filesystem is re-initialized.

So I'd be inclined to use the first technique.

kylesat
Posts: 5
Joined: Tue Mar 24, 2015 5:20 pm
Location: Mountain View, CA, USA

Re: Porting to STM32F429, where to increase code size?

Post by kylesat » Mon Jun 29, 2015 7:59 pm

Thanks David, your first method worked perfectly (I do apparently have an older version of dfu-utils, so I had to remove the ":leave"):

Code: Select all

echo -e -n "\xff" > ff.bin
dfu-util -s 0x08004000: -a 0 -d 0483:df11 -D ff.bin
I will continue today to work on my port. It's clear that my code modifications weren't "sticking" due to this unknown step to force a rebuild of the FatFS -- so I have a bit of code clean-up to do.

What would the best way be to proceed to help the following two scenarios moving forward:
1. Make sure the STM32F429 is supported by micropython
a) Add pin mapping file stm32f429_af.csv and memory link map/script stm32f429.ld
b) Add space for additional blocks in storage.c (also in flash.c ?)
C) anything else?

2. Help support for the STM32F429 DISCOVERY board? What about the following steps?:
a) Create a new folder in /stmhal/boards/
b) Setup pin mappings for this board
C) It'd probably be best for people not to have to make a custom USB cable. (Although it just took cutting an old A to B USB cable, a few pieces of wire, and some minor soldering).

User avatar
dhylands
Posts: 3228
Joined: Mon Jan 06, 2014 6:08 pm
Location: Peachland, BC, Canada
Contact:

Re: Porting to STM32F429, where to increase code size?

Post by dhylands » Mon Jun 29, 2015 9:04 pm

Those all look like reasonable steps.

I'm also interested in this as I also have an STM32F429 Discovery board (still in the packaging), as well as a 427 board.

I generally try to make changes feature based rather than chip based. So adding more onboard flash storage should probably be based on flash size and not the CPU (each of the CPUs is available in a variety of flash sizes). It may also make sense to use config options for controlling whether the extra flash blocks are coded as storage or as code space. The 429 has an attached SDRAM (for the LCD frame buffer) and it may also be possible to use part of that to allow using some of the larger flash blocks as part of the file system.

It looks like DFU mode will only work on the PA11/PA12 pins (i.e. OTG1) and CN6 is connected to OTG2. So using stlink or adding a custom cable and using dfu mode seem like the 2 options for programming.

I'd recommend that we call the new board directory STM32F429DISC.

It sounds like you have some code working. I'd be happy to help out with structuring stuff. I'm also very familiar with the pins stuff. And, since I have a 429 board, I can help out with testing as well.

Do you have a github branch that you're working on?

Post Reply