Okay I was able to fix this problem ! But now I am facing another obstacle !
Is there away to figure out the size of the used Flash Memory by the application code I know when you compile it tells you the size of you app, but I want to be able to save it as a variable and use it to figure out how much free space I have so when I write to flash memory i don't over write my application ?
HI , I am back with more question. I got the size thing working out and I can write to the flash memeory from the Application, However ther is one set back.
If I write from the application any thing less than 2096 i have no problems
but if i tried to write something more like 3311 , everything locks up and nothing gets written , I am trying to troubleshoot now, but no luck
Yes the ICE is not much help in my case. I figure out what is my problem
I am using arduino Micro and it oly have up to 2K of RAM so when I try to allocate a memory buffer for the 3K file the whole thing locks up because there is no enough memory space. Maybe I can writ in small packs but the question now, Do atmega32u4 required restarting after writing each pack ? if it does that is an issue
when i call my bootloader function from my application one single time it works and everything executes as expected
However, If I put it in a loop pr called two consecutive times from the application, it gets stuck some how
SNSFlashWrite(page_w ,flash_buffer,length); --> Assembly --> 00000080 ICALL Indirect call to (Z) // Z= 0x3856 (0x3856*2 = 70ac....
which is the location of the array in the bootloader ) this is correct
SNSFlashWrite(0x3100 ,flash_buffer,length); -->>> 00000087 ICALL Indirect call to (Z) //z = 0x0203 i am not sure what is 0x0203 refer too?
SNSFlashWrite(0x2700 ,flash_buffer,length); -->>>> 0000305E ICALL Indirect call to (Z) //z = 0x0203 i am not sure what is 0x0203 refer too?
Show the real LSS but just a small question. Are the called bootloader functions reentrant? That is do they only use stack frame autos? (Bss and .data for the bootloader will not exist when called from the app)
Posted by AVATAR_Freaks: Thu. Dec 27, 2018 - 04:52 PM
1
2
3
4
5
Total votes: 0
sternst wrote:
Gosh, WHY ON EARTH do you still use __attribute__ ((naked))???
See If I removed the naked attribute, and call the function single time or several times, the code stuck at the function and never executes the next command line and to fix that i have to put a manual jump to the next line location (__asm__ volatile(".org 0x60B2");
with the naked attribute I don't need that.
I think the reason it works because with the naked, that i have "__asm__ volatile("RET") and when it is not naked then it seems like the compiler skip it...
My understanind that naked tell the compiler this considered to be assembly
See If I removed the naked attribute, and call the function single time or several times, the code stuck at the function and never executes the next command line
It's actually the other way round. Your "function does not return" problem is CAUSED by the naked attribute.
Interesting, I was describing what I was saying, okay i followed what you said i removed the naked and I am using the manual jumo /(.org) , but when that didn't fix the main issue that when i put my bootloader function inside the loop it only excutes once ?
okay i followed what you said i removed the naked and I am using the manual jumo /(.org)
Where did I say that you should use this .org nonsense?
Write the function in a normal way. No naked, no .org, no manual ret/jump, nothing. The only "abnormal" thing you may need to do is to prevent the function from being removed due to optimisation.
You totally right, I was just doing EEMEM and using pgm_read_byte, so I was writing to the EEPROM and reading from the flash! Dump LOL
I have another obstacle tho, My serial number, device ID and VID ID, is working however when I upload a sketch it gets overriden by USBCORE.cpp that come with the arduino package , any idea how to disable it ?
By NOT putting it in "EEMEM" but into some other named data section. In effect all EEMEM really achieves s the same as:
__attribute__((section(".eeprom")))
(perhaps also applying other attributes such as "used").
Later on the stuff in the linker script effectively has the same effect as if:
-Wl,secton-start=.eeprom=0x810000
had been used. So if you wanted something at 0x140 in EEPROM then just assign the data to a section such as ".myee" and then later section-start this to 0x810140. To create the EEP file at present there is then an objcopy command that changes the 0x810000 base address to be 0x000000 so you'd want to modify that to also include .myee
Remember previously I was able to expand the bootloader by another 2k so now my bootloader starts from 0x6800 instead of 0x7000 (atmega32u4)
the part starting from 0x7000 is write protected when uploading application alone. now How I can make the rest (from 0x6800 to ox7000) write protected ?
the reason is, when I upload the application by it self I don't have to worry about that extra 2k to be overwritten or deleted
Just in the bootloader code. Ultimately you must have a kind of:
void do_write_page(uint16_t addr, uint8_t * page_data) {
// write SPM_PAGESIZE bytes from page_data to "addr"
}
so you just say:
void do_write_page(uint16_t addr, uint8_t * page_data) {
if (addr > 0x6800) {
return;
}
// write SPM_PAGESIZE bytes from page_data to "addr"
}
You may want to then make this a bool rather than a void return and return some kind of success/failure code. Then later layers will handle the occasion it returns false. (flashing LEDs etc).
EDIT: OK that should either be ">= 0x6800" or "> 0x67FF"
What gets burned is based purely on the addresses in the hex. But why would you be programming the APP using ISP? Surely the very point of using a bootloader is that IT will then do all the app flashing?
PS the very first (and only) time you flash the AVR you might want to put both bootloader and first version of the app in together but you'd do that by combining app.hex and boot.hex as one then program the combined image. If you use a sensible tool like Srecord to combine it will hopefully warn of any overlap.
EDIT: yup the SRecord manual contains this:
It is common to want to “join” two hex files together, without any changes of address. on the assumption neither file intersects with the other. This is a simple “layers”, it is quite common for linkers to output the main code, and then a whole bunch of relocation and jump destination, by writing a two layered files.
srec_cat one.he two.hex −o three.hex
Almost always you see an error
srec_cat: two.srec: 49282: contradictory 0x00000000 value (previous = 0x00, this one = 0x80)
So, yes, it will give an error by default if sections overlap with different data values.
What is the "It" that "erases"? As that it talking to "-c avr109" which is presumably your bootloader? Then surely any erasing being done is as a result of a command passed in the avr109 protocol? In fact it must be this:
So your own bootloader is being "too aggressive" when it receives a "e" command in the protocol. It should just do writes of 0xFF pages from 0x0000 to 0x67FF and not attempt to perform a full "chip erase" beyond that in any way.
Well on the avrdude side you can add four -v so it gets very verbose about the 109 commands it is sending then on the AVR side you can breakpoint and track the execution of each command byte that arrives so none of this should be a mystery.
what I am trying to say is, when I call a function the return address is pushed to the stack.
How can I jump back to the return address with code
i know I need something like that , but how can i know the adress of tha Stack_ADRESS ?
- Log in or register to post comments
TopStefan Ernst
- Log in or register to post comments
Top- Log in or register to post comments
TopDo you know what it does?? If not (a) why are you using it? and (b) do you think it might be time to consult the user manual?
- Log in or register to post comments
TopYea I know, it identifies the function as ASM function. and The reason I included is that I have few lines in my function in __ASM__
so I thought i should use it !?!?
- Log in or register to post comments
Toptime to read the manual - no point simply guessing
- Log in or register to post comments
TopOkay I was able to fix this problem ! But now I am facing another obstacle !
Is there away to figure out the size of the used Flash Memory by the application code I know when you compile it tells you the size of you app, but I want to be able to save it as a variable and use it to figure out how much free space I have so when I write to flash memory i don't over write my application ?
Any suggestions
- Log in or register to post comments
TopWhat I mean is , How can I calculate the Free Memory space in the Flash memory ? (Using coding language )
the reason is I want to be able to determine how much free space do I have and make sure to not write any more data than this size ?
- Log in or register to post comments
TopOne approach is to write a cookie as a marker.
- Log in or register to post comments
TopAnother approach is to use __data_load_end.
Stefan Ernst
- Log in or register to post comments
Topyes that works i used the __data_load_end
now how can i find the start of my bootloader ?
is it possible to pass avariable from the MAKEFILE to the flashmemeory ?
something like __data_load_end but used defined ?
- Log in or register to post comments
TopThe start of the bootliader is surely at the BOOTSZ address?
- Log in or register to post comments
TopHI , I am back with more question. I got the size thing working out and I can write to the flash memeory from the Application, However ther is one set back.
If I write from the application any thing less than 2096 i have no problems
but if i tried to write something more like 3311 , everything locks up and nothing gets written , I am trying to troubleshoot now, but no luck
any suggestions ?
- Log in or register to post comments
TopThis is why God invented ICEs
- Log in or register to post comments
TopYes the ICE is not much help in my case. I figure out what is my problem
I am using arduino Micro and it oly have up to 2K of RAM so when I try to allocate a memory buffer for the 3K file the whole thing locks up because there is no enough memory space. Maybe I can writ in small packs but the question now, Do atmega32u4 required restarting after writing each pack ? if it does that is an issue
- Log in or register to post comments
TopYou only ever deal in SPM_PAGESIZE packets so why would you ever need to hold 3K?
Have you looked at the design of other bootloaders?
- Log in or register to post comments
TopHappy holidays guys !
I am back with one more question
when i call my bootloader function from my application one single time it works and everything executes as expected
However, If I put it in a loop pr called two consecutive times from the application, it gets stuck some how
why the ICAL going to some random address ?
- Log in or register to post comments
TopShow the real LSS but just a small question. Are the called bootloader functions reentrant? That is do they only use stack frame autos? (Bss and .data for the bootloader will not exist when called from the app)
- Log in or register to post comments
Tophere is the the entire LSS
this is the LSS for the bootloader function
and I think yes the functions is reentrant , since i am not using any global variables
- Log in or register to post comments
TopNo wonder strange things happen in the application when your SNSFlashWrite function clobbers several registers.
Stefan Ernst
- Log in or register to post comments
TopSee If I removed the naked attribute, and call the function single time or several times, the code stuck at the function and never executes the next command line and to fix that i have to put a manual jump to the next line location (__asm__ volatile(".org 0x60B2");
with the naked attribute I don't need that.
I think the reason it works because with the naked, that i have "__asm__ volatile("RET") and when it is not naked then it seems like the compiler skip it...
My understanind that naked tell the compiler this considered to be assembly
- Log in or register to post comments
TopStefan Ernst
- Log in or register to post comments
TopInteresting, I was describing what I was saying, okay i followed what you said i removed the naked and I am using the manual jumo /(.org) , but when that didn't fix the main issue that when i put my bootloader function inside the loop it only excutes once ?
- Log in or register to post comments
TopWrite the function in a normal way. No naked, no .org, no manual ret/jump, nothing. The only "abnormal" thing you may need to do is to prevent the function from being removed due to optimisation.
Stefan Ernst
- Log in or register to post comments
TopYES, You are right ! that was my issue , the "Attribute (Naked) " screwed me over plus the __asm__ volatile("RET");
It is better now, but the problem now is when naked is removed for some reason my boot loader bigger in size without adding any extra code !??
==
- Log in or register to post comments
TopHow can i do that part, at the moment I'm having it at the __attribute__((section(".vectors"))); but I don't want to keep it that way
is there is a way to turn optimisation for a single function , ot it has to be for the whole project
- Log in or register to post comments
TopHello again,
SO I am almost done with this project ! but I still have a question?
How can i define a variable to br saved in the eeprom from the boatloader?
i have the following variable, which i would like to save it to the EEPROM ?
I tried EEMEM
but no luck
- Log in or register to post comments
TopIf it already in PROGMEM, why do you also need to save it to EEPROM???
Jim
(Possum Lodge oath) Quando omni flunkus, moritati.
"I thought growing old would take longer"
- Log in or register to post comments
TopI want to be able to update the serial number in the fly. without need to recompile
SO it is not in the promem it is only in the memm
i am using this now
but this thing is when i look at the serial number of the device it rgives an error
- Log in or register to post comments
TopIt will be the wrong value UNTIL you program the EEP file.
- Log in or register to post comments
TopI write the eep file, but the serial number under device properties is giving an error
- Log in or register to post comments
TopOkay It was my mistake, I was reading from the wrong location !
Thanks
- Log in or register to post comments
TopHow could you get the location wrong? It's &STRING_SERIALNUMBER. You need never know the actual address as the linker handles that for you.
- Log in or register to post comments
TopYou totally right, I was just doing EEMEM and using pgm_read_byte, so I was writing to the EEPROM and reading from the flash! Dump LOL
I have another obstacle tho, My serial number, device ID and VID ID, is working however when I upload a sketch it gets overriden by USBCORE.cpp that come with the arduino package , any idea how to disable it ?
- Log in or register to post comments
Tophow can i make
saved at a specific address lets say 0x140 ;
without changing the linker
the reason I am asking for that, is I have the 0x00 location reserved for something else.
i can be asking that question in another way, how can I reserve the 0x00 location in the EEPROM ?
- Log in or register to post comments
Top__attribute__((section(".eeprom")))
(perhaps also applying other attributes such as "used").
Later on the stuff in the linker script effectively has the same effect as if:
-Wl,secton-start=.eeprom=0x810000
had been used. So if you wanted something at 0x140 in EEPROM then just assign the data to a section such as ".myee" and then later section-start this to 0x810140. To create the EEP file at present there is then an objcopy command that changes the 0x810000 base address to be 0x000000 so you'd want to modify that to also include .myee
- Log in or register to post comments
TopI actually seen your answwer for another post and I just used
.eeprom = 0x00144 under tool chain
- Log in or register to post comments
TopI guess that would work but watch for the avr-objcopy that creates the EEP - I think it has a fixed 810000 in it.
- Log in or register to post comments
TopYes it works!!
Remember previously I was able to expand the bootloader by another 2k so now my bootloader starts from 0x6800 instead of 0x7000 (atmega32u4)
the part starting from 0x7000 is write protected when uploading application alone. now How I can make the rest (from 0x6800 to ox7000) write protected ?
the reason is, when I upload the application by it self I don't have to worry about that extra 2k to be overwritten or deleted
is there away ?
- Log in or register to post comments
TopJust validity check the addresses you are about to write to and just make sure it never exceeds 6800
- Log in or register to post comments
Tophow can i do that ?
in the avr level or the bootloader level
- Log in or register to post comments
TopJust in the bootloader code. Ultimately you must have a kind of:
so you just say:
void do_write_page(uint16_t addr, uint8_t * page_data) { if (addr > 0x6800) { return; } // write SPM_PAGESIZE bytes from page_data to "addr" }
You may want to then make this a bool rather than a void return and return some kind of success/failure code. Then later layers will handle the occasion it returns false. (flashing LEDs etc).
EDIT: OK that should either be ">= 0x6800" or "> 0x67FF"
- Log in or register to post comments
TopI don't mean whan i am writting from application to flash memory. I mean when I am burning the App.hex
Is there away to tell avrdude to burn to a specific location ?
- Log in or register to post comments
TopWhat gets burned is based purely on the addresses in the hex. But why would you be programming the APP using ISP? Surely the very point of using a bootloader is that IT will then do all the app flashing?
- Log in or register to post comments
TopPS the very first (and only) time you flash the AVR you might want to put both bootloader and first version of the app in together but you'd do that by combining app.hex and boot.hex as one then program the combined image. If you use a sensible tool like Srecord to combine it will hopefully warn of any overlap.
EDIT: yup the SRecord manual contains this:
So, yes, it will give an error by default if sections overlap with different data values.
- Log in or register to post comments
TopI see your point, but i think i didn't say all the information.
SO the 1st time we are flashing the device we are writting a combined version of bootloader.hex and app.hex through the ISP.
then the IT don't use ISP they use the USB connection and the bootloader that already exist to update the app.hex
with the help of avrdude to write we use the following command while pushing the rest button to start burning
so what you explained previously is exactly what I'm doing, but the obstacle is that It erases the extra 2K i was talking about previously .
I'm Using a modified version of the Caterina Bootloader
- Log in or register to post comments
TopWhat is the "It" that "erases"? As that it talking to "-c avr109" which is presumably your bootloader? Then surely any erasing being done is as a result of a command passed in the avr109 protocol? In fact it must be this:
So your own bootloader is being "too aggressive" when it receives a "e" command in the protocol. It should just do writes of 0xFF pages from 0x0000 to 0x67FF and not attempt to perform a full "chip erase" beyond that in any way.
- Log in or register to post comments
TopYes You totally right, It was erasing to 7000 i changed it to be 0x67FF. in the "e" command .
now the problem if i try to uplaod the application.hex by it self i get the following error
i gues at the command 'A'
I dont think it is related
- Log in or register to post comments
TopWell on the avrdude side you can add four -v so it gets very verbose about the 109 commands it is sending then on the AVR side you can breakpoint and track the execution of each command byte that arrives so none of this should be a mystery.
- Log in or register to post comments
TopPages