I was reading up on the flash eeprom and best I can tell for the stm32f chips this is needed. micromouseusa.com/
Has Keil mdk5 not provided a simple function?
So, if you have a chip without it, you're either going to have to add it externally or emulate it in Flash.
Or is battery backup an option for you?
ST have an App Note on emulating EEPROM in STM32 Flash - but note that their supplied linker script is fundamentally flawed (it doesn't tell the linker that some flash is being used for the EEPROM emulation).
Yes, it gets complicated because of wear-levelling and coping with erasing & re-writing the data in Flash.
Other manufacturers have similar App Notes - you might also be able to get ideas from them...
Sorry I was not clear on that.
I have a st32f205 with eeprom on the chip, I simply just want to write and read form it. This "emulating EEPROM" is confusing me. Is there no easy way to write/read to eeprom on the chip. All the info I find talks about this "emulating EEPROM" when searching for how to use the eeprom.
Difficult is a relative term. It sadly depends on experience. Flashing anything out side a tool will be difficult for us. In this case even more so because there are not specific chip examples.
SO, apparently that is the case. We specifically budgeted for eeprom. Somehow this was over looked. Now emulation is our only option. It is hard enough to write code with a eeporm viewer and eeprom read and write commands, no we really have work cut out.
So I see the only option is to dedicate a section of code for an eeprom effect. This will certainly work but I'm going to need a good write up to understand this. Processor stalls are fine, we only need to write a few bytes to tell the device how to operate. The plan is to send a USB control transfer to a report ID and tell the chip write bytes here. Then the device can read these values on boot up to know what to do. The problem will be the understanding; Where can I write safely, how can I write, how can I read. The max I would need is 16 bytes.
I would avoid the EEPROM Emulation completely if all you want to do is save a configuration structure.
Pick one (or two) of the early 16KB sectors (@ 0x08004000, 0x08008000 or 0x0800C000), and then journal the writing of your structure across this space, selecting the last one written, and writing the new/changed one beyond the current.
Reading, it's in the address space, so create a structure pointer to the base of the sector and index into them. Have the first word of your structure be a signature, ie not 0xFFFFFFFF and the last word a CRC or checksum to prove/confirm validity.
Simplified method,
typedef struct _CONFIG { uint32_t Signature; // 0x12345678 ? // .. other neat stuff uint32_t Checksum; } CONFIG; CONFIG *config = (CONFIG *)0x08004000; // Config FLASH Sector Base CONFIG curr; const CONFIG default = { 0 }; // Add int i; i = 0; while(config[i+1].Signature != 0xFFFFFFFF) // Index to last i++; if (config[i].Signature == 0xFFFFFFFF) // Empty case { puts("Config Empty, using defaults"); memcpy(&curr, &default, sizeof(CONFIG)); } else { // Check signature and checksum puts("Loading Config"); memcpy(&curr, &config[i], sizeof(CONFIG)); // .. } // ... // Writing next block if (config[i].Signature != 0xFFFFFFFF) // Advance to blank i++; curr.Signature = 0x12345678; // Checksum new configuration, then write to FLASH curr.Checksum = CRC32(0xFFFFFFFF, &curr, sizeof(CONFIG) - 4); FLASH_WriteBlock((uint32_t)&config[i], &curr, sizeof(CONFIG)); // Addr, Buffer, Size
That's not really "avoiding EEPROM emulation completely". That is, for all practical intents and purposes, EEPROM emulation (although a somewhat coarse one).
I see 1 reference to EEPROM in the STM32F20xxx manual. It this what you are talking about using?
Real-time clock (RTC), backup SRAM and backup registers The backup domain of the STM32F20x devices includes: • The real-time clock (RTC) • 4 Kbytes of backup SRAM • 20 backup registers The real-time clock (RTC) is an independent BCD timer/counter. Its main features are the following: • Dedicated registers contain the second, minute, hour (in 12/24 hour), week day, date, month, year, in BCD (binary-coded decimal) format. • Automatic correction for 28, 29 (leap year), 30, and 31 day of the month. • Programmable alarm and programmable periodic interrupts with wakeup from Stop and Standby modes. • It is clocked by a 32.768 kHz external crystal, resonator or oscillator, the internal lowpower RC oscillator or the high-speed external clock divided by 128. The internal lowspeed RC has a typical frequency of 32 kHz. The RTC can be calibrated using an external 512 Hz output to compensate for any natural quartz deviation. • Two alarm registers are used to generate an alarm at a specific time and calendar fields can be independently masked for alarm comparison. To generate a periodic interrupt, a 16-bit programmable binary auto-reload downcounter with programmable resolution is available and allows automatic wakeup and periodic alarms from every 120 µs to every 36 hours. • A 20-bit prescaler is used for the time base clock. It is by default configured to generate a time base of 1 second from a clock at 32.768 kHz. • Reference clock detection: a more precise second source clock (50 or 60 Hz) can be used to enhance the calendar precision. The 4-Kbyte backup SRAM is an EEPROM-like area.It can be used to store data which need to be retained in VBAT and standby mode.This memory area is disabled to minimize power consumption (see Section 3.18: Low-power modes). It can be enabled by software. The backup registers are 32-bit registers used to store 80 bytes of user application data when VDD power is not present. Backup registers are not reset by a system, a power reset, or when the device wakes up from the Standby mode (see Section 3.18: Low-power modes). Like backup SRAM, the RTC and backup registers are supplied through a switch that is powered either from the VDD supply when present or the VBAT pin.
It does avoid pretending it is EEPROM and treats it like FLASH, so it does dispense with a rather thick abstraction from ST with an Adddress/Byte storage system that immediately reduces the available space by at least a quarter.
The problem with pretending is that you keep doing things which are inappropriate rather than change the paradigm to a more appropriate one. ie a FLASH within the MPU address space, vs a I2C EEPROM
Bit weaselly, the data sheet doesn't talk about EEPROM. Must have been losing sails* because the keyword "EEPROM" wasn't hitting on the parametric search.
EEPROM doesn't need batteries, ST has an emulation library using FLASH.
The NVRAM/BKPRAM is within the MPU address space, if the OP has a battery and is comfortable with using that, then map a structure within the NVRAM, copy stuff in/out, or add it to a scatter file.
*beats detector
Yes that may have been the section that game us the clue that eeprom was available. In our situation a battery would work. If enabled in code, could eeprom be read and written to in the normal convention )(via a command)?
is this what I need? stackoverflow.com/.../how-to-use-backup-sram-as-eeprom-in-stm32f4
Yes, although I think calling it NVRAM will be more inline with what it is.
Guessing ill have to convert this to 205. I had to fix the implicit declarations with prototypes.
static void RCC_AHB1PeriphClockCmd(char, bool); static void RCC_APB1PeriphClockCmd(char, bool); static void PWR_BackupAccessCmd(bool); static void PWR_BackupRegulatorCmd(bool);
but the following are unknown to the 205 RCC_AHB1Periph_BKPSRAM RCC_APB1Periph_PWR
Guessing the 205 has different naming and possibly different address ranges. The data sheet shows AHB1 with a BKPSRAM perf but these are unknown to the IDE. Do I have to enable this in RTE or add an include.
Surely, ST provide examples of how to do this for the specific chip that you have?
Yes, it is important to know (at least for you to know) what ST libraries you are using, assuming that you are in fact using some. There is the STM32F2xx_StdPeriph_Lib of which the example you posted uses. It fully supports the STM32F205. There is also the STM32F2xx_HAL_Driver?
The linked Stack Overflow thread specifically states that it uses STM32F4xx_DSP_StdPeriph_Lib - which is clearly not the one for STM32F2...
I have STM32F2xx_StdPeriph_Lib_V1.1.0 to hand.
It does, indeed, have a Backup Domain example - in Project\STM32F2xx_StdPeriph_Examples\RTC\BKP_Domain
I don't see the example in C:\Keil_v5\ I normally use the pack installer and I don't see it in there either. Anyone have a link to the example. I can't find it searching the net.
"Get Software", bottom of the page gets you to the software examples Andrew and I have worked with. www.st.com/.../stsw-stm32062.html
Ok thx, one thing before I start this journey. Is this example only going to get me the 80 bytes? I read the RTC only had 80 and the other (more battery drain) had more.
The RTC has 80 bytes of backup registers, as I recall.
The BKPRAM (NVRAM) has 4KB
hmm, same errors as my post on 22-Aug-2017 15:28
Many definitions missing. I tried to included #include "stm322xg_eval.h" but it is not found and also not included in the example download.
Again, what firmware library are you using? CLEARLY (at least to me) you are not using the STM32F2xx_StdPeriph_Lib. Your examples that you have posted are expecting you to be using that firmware library. The reason you are getting errors EVERY TIME you build your example code is because it is making references to the STM32F2xx_StdPeriph_Lib and you are not actually using that library.
The library is stm32f2xx_hal
After destruction with the team and considering nvram/i2c, eeprom, flash. We decided to go with flash. Eeprom emulation or may what "Clive One" suggested. Can anyone suggest a way to see the flash after I do a test write? A visual debug would be essential in troubleshooting.
oops / discussion - but sometimes does feel like destruction.
That's what the debugger is for!
Please read the manual: http://www.keil.com/support/man/docs/uv4/uv4_db_dbg_memwin.htm
I found a project of some help.
github.com/.../eepromConfig.h
It compiles all but he flash erase.
flashErase.NbPages=1;//error no member flashErase.Banks = FLASH_BANK_1; flashErase.PageAddress = _EEPROM_FLASH_PAGE_ADDRESS; //error no member flashErase.TypeErase = FLASH_TYPEERASE_PAGES;
and FLASH_TYPEERASE_PAGES does no exist.
flashErase has; voltageRange nbSectors sector
guesssing nbSectors/sectors and nbPages/PageAddress interchangeable? and how can I find the missing define FLASH_TYPEERASE_PAGES what would I use for a voltageRange?
ok got it all flashErase.NbSectors=1; flashErase.Banks = FLASH_BANK_1; flashErase.Sector = _EEPROM_FLASH_PAGE_ADDRESS; flashErase.TypeErase = FLASH_TYPEERASE_SECTORS;
Right I forgot this Keil had a rather useful debugger, thx.
Thank you. The Flash solution is a very good choice (as Clive suggested very early). Even better than the EEPROM. Good Luck.
forget all you heard about EEPROM. although not always true EEPROM has become to mean "serial storage" the flash is accessible parallel.
remember you can tot set a bit in flash, only clear it
bad code but shows the principle
struct flashthinh unsigned char mark = o unsigned char unsigned char
to write scan the structures till you find mark =0xff write there
to read scan the structures till you find mark =0xff back up one and read
The STM32 Flash arrays have parity/haming bits associated with them, they are write-once, so you can't really incrementally knock one bits down.
The L family parts supposedly use "EEPROM", the erased state is zero (0x00), but this could just be FLASH with an inverter on the data bus. The block diagrams and slide decks really don't given much fabrication detail.
Typically NAND FLASH accesses like a block storage device. NOR FLASH accesses like random-access memory, and you can execute from it.
thx for all the advice but I'll have to start somewhere. Thus far that eeprom emulation code in my github link above helps. but few this confusing me yet.
flashErase.VoltageRange = FLASH_VOLTAGE_RANGE_4;//1,2,3,4.. Where do I look this up. I'm not finding this in the data sheet.
I can read in words (ffffffff=4294967295) so for so good and reading from my data area I do see the correct values as shown in the debugger.
writing I can not do. Per the code I sampled from no data is written. Also in the debug I can not change the memory outside my data area, I get an error. Cannot access Memory Internal command error
Do I need to enable something in the RTE?
thx for all the advice but I'll have to start somewhere. Thus far that eeprom emulation code in my github link above helps. but few this confusing me yet.>/i>
You also need to know how to move forward. I thought you did. You said you were going to go with the approach Clive proposed and use the Flash. I thought that was a very appropriate idea which started with him stating "I would avoid the idea of EEPROM emulation completely". The whole concept of the EEPROM emulation was making it very difficult for you to move forward. It was clear that it was not helping you to move forward. It was keeping you stuck on something that was just not appropriate for you to be spending time on. It was fairly clear that what Clive suggested was most likely a very good way for you to go forward. You finally said that you wanted to go with what Clive presented (NO EEPROM) which seemed like progress. Now you are back to saying that starting from EEPROM emulation code as a starting point is helping you!
Moving forward is a few steps a way. As I said I need to start with a few things to understand how all this works. This example I found shows things pretty well and got me a little further. I still "think" Clive has a good idea but what do I know? This is all new to me, so whatever works out of the box is going to fundamentally assist in learning the basics. Like the debugger.
View all questions in Keil forum