|
|
View previous topic :: View next topic |
Author |
Message |
Cappiam
Joined: 10 Apr 2018 Posts: 17 Location: New England
|
Bootloader Issue: Bootloaded program fails after address FF |
Posted: Fri Dec 13, 2019 2:09 pm |
|
|
I've been using the CCS bootloader example, and I have something strange occurring, and for the life of me, I can't figure out what the difference is or what the error is.
I'm using a PIC18F45K80. I modifed the bootloader example so this chip is used, and the RS232 port is using pins D6 and D7. In an effort to track down the error, I left the rest of the code unmodified. Now onto the issue:
I program the bootloader and example code and I run it in debug as well as release. It works perfectly. Next, I bootload my own code, and it works perfectly in debug, but fails to run at all when I've programmed the bootloader for release.
As I was working towards tracking down the error, I thought maybe the issue was with my code, since the example code works fine. I commented most of the code out, and it would run. Then I would uncomment out a new section of code and I repeated till it failed. I could never get past a certain point.
At this time, I went back to the demo code (bootload.c) and added in dummy lines of code, Example: If (x==1) x=0; Just lines that use up programming memory. By doing this, I found out that the demo code would become questionable after instruction address FF, ie: 100FF000020802E1170E416F405301E0416B406B64
If the hex file progresses after this point, the code may crash, restart, or simply fail to run, depending on how many extra lines are added. If I program this code or my own to run without a bootloader, it will work fine. The same is true if I run the bootloader code using the ICD3 and MPLAB debug. It is only when I program the pic with the release version of the bootloader that the issue appears.
My only guess is that the bootloader code isn't progressing to 100 and instead either wraps around back to address 001 or simply doesn't write it correctly after FF. I have no way to explain this, or reasonably test it since it works when it runs in debug. I wrote some test code into loader.c to send the address written after each line, and it consistently reports the correct address.
I can share the code I'm working but other than the changes I've mentioned, I'm pretty much using the bootloader demo code provided with the most recent CCS (And I'm not sure that is supposed to be posted). Any ideas would be helpful. I've also tried using a different board instead the first was damaged somehow, but the symptoms are identical. |
|
|
PCM programmer
Joined: 06 Sep 2003 Posts: 21708
|
|
Posted: Fri Dec 13, 2019 5:04 pm |
|
|
I don't think that's FF. The first two digits after the colon are the record
length. The next four are the address.
Hex file format:
http://www.keil.com/support/docs/1584/ |
|
|
Ttelmah
Joined: 11 Mar 2010 Posts: 19543
|
|
Posted: Sat Dec 14, 2019 1:46 am |
|
|
Seriously to be writing to address 0FF0, there would need to be quite a
lot of code, not just an extra line like If (x==1) x=0; bootload.c, uses
up just a couple of hundred bytes of code. The bootloader itself just
a few hundred bytes. This address is 4KB up the ROM...
I'd suspect something is wrong with the bootloader setup for the
processor. You need to show what you are doing.
Working in debug but not release, is usually tied to:
1) MCLR not properly pulled up when debugger not present.
2) Power supply.
3) Grounding (remember the debugger supplies a ground connection). |
|
|
Cappiam
Joined: 10 Apr 2018 Posts: 17 Location: New England
|
|
Posted: Mon Dec 16, 2019 7:32 am |
|
|
PCM programmer wrote: | I don't think that's FF. The first two digits after the colon are the record
length. The next four are the address.
Hex file format:
http://www.keil.com/support/docs/1584/ |
I've debugged the code up to the point that the address is FF, I figured this out by modifying loader.c to reply with the line address after each successful write.
Code: | if (do_ACKLOD){
BootLoaderPutc(ACKLOD);
temp = addr;
for (i=0; i<8;i++)
{
temp2 = temp%16;
if (temp2>9) BootLoaderPutc(temp2+55);
else BootLoaderPutc(temp2+48);
temp = temp>>4;
}
printf("\r\n");
} |
I converted the address myself rather than using printf's function since it saves a lot of code space for the bootloader. Addr and temp are 32 bit integers. addr is the variable written into loader.c that provides the address where the line is written, temp is just a variable I can modify instead of addr, and temp2 is an 8 bit integer, used for output with the putC function(Again, all of this is for code space conservation in the bootloader)
So by doing this, I could guarantee the written address definitely started having errors once it moved from 0x0FF to 0x100. Long way of saying it, but I didn't rely on my ability to interpret the hex code to determine where the error starts. |
|
|
Ttelmah
Joined: 11 Mar 2010 Posts: 19543
|
|
Posted: Mon Dec 16, 2019 7:43 am |
|
|
OK.
The point is that the packet you posted is not where the address is 0x0FF.
The packet you post is for address 0x0FF0.
Now address 0xFF, should never be written, since it is inside the bootloader.
If you are attempting to write address 0x0FF, then 'no wonder' it stops
things working, since this will be overwriting the bootloader. This implies
that the #build line in bootloader.h is not correctly being applied to the
bootloaded code.
Study ex_bootload.c This shows how code that is going to be loaded with the
bootloader needs to be compiled. Note that it loads bootloader.h, but
without _BOOTLOADER defined.
Code that is loaded with the bootloader, _cannot have code at address
0x0FF_. (for a normal low memory bootloader). |
|
|
Cappiam
Joined: 10 Apr 2018 Posts: 17 Location: New England
|
|
Posted: Mon Dec 16, 2019 8:45 am |
|
|
Ttelmah wrote: | Seriously to be writing to address 0FF0, there would need to be quite a
lot of code, not just an extra line like If (x==1) x=0; bootload.c, uses
up just a couple of hundred bytes of code. The bootloader itself just
a few hundred bytes. This address is 4KB up the ROM... |
Sorry if I wasn't clear, I used multiple lines like that to pad the code. It was over a hundred of lines similar to that one. Since I don't know how smart the compiler is for code efficiency, I made sure the lines the lines were different. I added those lines to the ex_bootload.c program, which is the example code to be bootloaded, not the bootloader itself. Other than compatibility includes, I didn't modify this one beyond the padded code.
Quote: | I'd suspect something is wrong with the bootloader setup for the
processor. You need to show what you are doing.
|
I can post the code, but it's almost identical to the example provided by CCS, with the changes I mentioned. (Again, not sure what the rules are for posting primarily CCS provided code is).
Loader.c was unchanged, until I modified it to reply with the address written, as mentioned in a previous post for debugging purposes. ex_bootloader.c I changed the pinout for RS232 to the pins I'm using, I changed the #include <16F887.h> to #include <18F45K80.h>
And, because it threw a memory problem upon compilation, I changed:
#org LOADER_END+1,LOADER_END+2
to
#org LOADER_END+1,LOADER_END+3
But it is also my suspicion something needs to change in the loader.c file. I'm just not familiar enough with bootloader setups to do much more than make guesses and attempts. Still, see below since I don't honestly understand how it can have an issue with code length only when using the bootloader in release.
Quote: | Working in debug but not release, is usually tied to:
1) MCLR not properly pulled up when debugger not present.
2) Power supply.
3) Grounding (remember the debugger supplies a ground connection). |
I'm certainly aware of these issues, but both the test code and my official code (that's about 900 lines verses 180) work perfectly fine when programmed directly, IE not bootloaded. The bootloader itself works fine when running in release as well. It's only when I try to bootload any code larger than what I mentioned that there's an issue. In attempting to troubleshoot the problem, I also tested with the programmer connected, but running in release, but the issue is the same.
Last edited by Cappiam on Mon Dec 16, 2019 1:03 pm; edited 1 time in total |
|
|
Cappiam
Joined: 10 Apr 2018 Posts: 17 Location: New England
|
|
Posted: Mon Dec 16, 2019 10:12 am |
|
|
Ttelmah wrote: | OK.
The point is that the packet you posted is not where the address is 0x0FF.
The packet you post is for address 0x0FF0.
Now address 0xFF, should never be written, since it is inside the bootloader.
If you are attempting to write address 0x0FF, then 'no wonder' it stops
things working, since this will be overwriting the bootloader. This implies
that the #build line in bootloader.h is not correctly being applied to the
bootloaded code. |
Yea, my mistake in misinterpreting what you meant. It is 0x0FF0 as you stated. I definitely misrepresented the address unintentionally. The test code I wrote outputs the address in reverse(Something I was aware of but forgot when I was writing the address here, so the first three characters are sent as 0x0FF rather than 0xFF0).
Until I can resolve the issue, I'm using the exact code provided by CCS(with the only changes being for processor compatibility, see earlier email for the changes).
Quote: | Study ex_bootload.c This shows how code that is going to be loaded with the
bootloader needs to be compiled. Note that it loads bootloader.h, but
without _BOOTLOADER defined.
Code that is loaded with the bootloader, _cannot have code at address
0x0FF_. (for a normal low memory bootloader). |
That was the first thing I did, and I paid close attention to that, especially after seeing it mentioned in a different forum post dealing with the bootloader. All of this should correct in my main code, but since I'm using ex_bootload.c to test with, I haven't modified anything but the processor .h file and the RS232 pins before main(), and I only added the padding code after to the section after main(). So the ex_bootload.c works perfectly if I comment out one padding line, putting the max address to 0x0FF0. with the line uncommented and the max address is 0x0100, it will crash and restart the program. It will then persistently send the "Application Version 1.0" line, but will never progress to the while(true) loop at the end, which is how I know the code is crashing and the PIC is restarting. For reference, this is the ex_bootload.c code, I've removed the majority of the padding code to shorten the length here:
Code: | #include <18F45K80.h>
#use delay( crystal=20MHz )
#use rs232(baud=9600,xmit=PIN_D6,rcv=PIN_D7, stream=PORT1) //Text through the UART
#include <bootloader.h>
void main(void)
{
int8 i, test;
delay_ms(100);
fprintf(PORT1,"\r\nApplication Version 1.0\r\n");
if (test) i =1;
if (!test) i =0;
[b]--- Rest of padding code goes here.[/b]
if (test>0) i =0;
while(true)//test == 0)
{
delay_ms(100);
fprintf(PORT1,"%3u ",++i);
}
test = 0; i = 0;
} |
|
|
|
Ttelmah
Joined: 11 Mar 2010 Posts: 19543
|
|
Posted: Mon Dec 16, 2019 11:40 am |
|
|
Er. That load line is completely wrong, and is not the load line it should
be reaching or using. The correct one for _PCH_, is:
#build(reset=LOADER_END+1, interrupt=LOADER_END+9)
The line you are posting is the PCM line (so for a PIC16).
It sounds as if you have removed the #IF tests that select which line
to use, without understanding what they do. |
|
|
Cappiam
Joined: 10 Apr 2018 Posts: 17 Location: New England
|
|
Posted: Mon Dec 16, 2019 12:01 pm |
|
|
Ttelmah wrote: | Er. That load line is completely wrong, and is not the load line it should
be reaching or using. The correct one for _PCH_, is:
#build(reset=LOADER_END+1, interrupt=LOADER_END+9)
The line you are posting is the PCM line (so for a PIC16).
It sounds as if you have removed the #IF tests that select which line
to use, without understanding what they do. |
I'm not sure which line you're referring to, unless it was #org LOADER_END+1,LOADER_END+2, but that wasn't contained in any #IF statement. This was changed in the ex_bootloader.c file, not the bootloader.h file.
I haven't touched bootloader.h at all, so the file should be exactly the one provided with the CCS installer, nor have I messed with any of the #IF statements in loader.c (nor bootloader.c, but doesn't contain any anyway), specifically because I know exactly how risky that is. So that shouldn't be the issue. During one of my tests, I did confirm that _PCH_ is being used. Honestly, the only files that should have any changes currently are ex_bootloader.c and ex_bootload.c with the changes being the ones I've listed.
I've double checked the loader.c and bootloader.h files, and they haven't been modified. Since I don't think the ex_bootloader.c code contains any of the critical copyright code, I'll post that code here since it's the only one I've done any modification to, other than the ex_bootload.c code I've posted already.
Code: | #include <18F45K80.h>
#use delay( crystal=20MHz)
//#use rs232(icd) //Text through the ICD
#use rs232(baud=9600,xmit=PIN_D6,rcv=PIN_D7)
#define PUSH_BUTTON PIN_C0
#define _BOOTLOADER
//#define BOOTLOADER_MODE2X
#include <bootloader.h>
#include <loader.c>
#org LOADER_END+1,LOADER_END+3
void application(void) {
while(TRUE);
}
void main(void) {
if(!input(PUSH_BUTTON))
{
printf("\r\nBootloader Version 1.0\r\n");
// Let the user know it is ready to accept a download
printf("\r\nWaiting for download...");
load_program();
}
application();
}
#int_global
void isr(void) {
jump_to_isr(LOADER_END+5*(getenv("BITS_PER_INSTRUCTION")/8));
} |
If I do not change LOADER_END+2 to LOADER_END+3, this is the error the compiler throws, and points to the jump_to_isr line:
ex_bootloader.c:73:1: Error#71 Out of ROM, A segment or the program is too large application
Seg 00500-00500, 0002 left, need 00004 Orged |
|
|
Ttelmah
Joined: 11 Mar 2010 Posts: 19543
|
|
Posted: Tue Dec 17, 2019 1:13 am |
|
|
OK.
Your new line is wrong.
I was talking about what is being 'loaded', rather than what is doing the
loading.
The correct lines are:
Code: |
#if defined(__PCM__)
#org LOADER_END+1,LOADER_END+2
#elif defined(__PCH__)
#org LOADER_END+2,LOADER_END+4
#endif
|
You are loading one byte out of position. This could cause all sorts of
problems. This may well be the issue.
As a separate comment, you have got XON/XOFF flow control enabled
on whatever program you are using to send the data?. The bootloader
_will not program correctly_ unless this is enabled. It is _required_.
Do you have a old version of the compiler available?. 5.07x?
Somehow the copy of ex_bootloader.c included with the latest compiler
versions has 'gone back' to the old version that used to be supplied
before PCH support was added. It was correct up to 5.080, then has
gone wrong. Load the copy of this file from the old compiler version
if you have it....
I have reported this to CCS. |
|
|
Cappiam
Joined: 10 Apr 2018 Posts: 17 Location: New England
|
|
Posted: Tue Dec 17, 2019 6:45 am |
|
|
Ttelmah wrote: | OK.
Your new line is wrong.
I was talking about what is being 'loaded', rather than what is doing the
loading.
The correct lines are:
Code: |
#if defined(__PCM__)
#org LOADER_END+1,LOADER_END+2
#elif defined(__PCH__)
#org LOADER_END+2,LOADER_END+4
#endif
|
|
I believe I had tried LOADER_END+2, +4 previously, and I changed it when I had issues. Either way, I switched it to the #IF statement you provided. That definitely does not exist in the ex_bootloader.c file from my CCS folder. Unfortunately, this did not resolve the issue. I was hopeful, for a bit.
However, since you say the older version of the compiler had newer versions of the file, I'm going to see if I can find my copy from a year or two ago, and try the loader.c file from there in case there's more than one difference. I'm not sure I'll be able to find it, since my computer has been upgraded since then and the PICC folder was in the programs folder and I don't believe that was backed up by IT.
Quote: | As a separate comment, you have got XON/XOFF flow control enabled
on whatever program you are using to send the data?. The bootloader
_will not program correctly_ unless this is enabled. It is _required_. |
I do have xon/xoff flow control enabled. Though if I didn't, I would expect the problem to either be persistent regardless of running in debug or release, and fail long before 0x0FF0. But this is part of why I wrote the test code into loader to report out the address, it helped confirm that the correct information was being received. |
|
|
Ttelmah
Joined: 11 Mar 2010 Posts: 19543
|
|
Posted: Wed Dec 18, 2019 12:37 am |
|
|
Post what you have changed in loader.c.
The bootloader does work, so it is something you have done that is
causing the problem. You need to give us a chance to see 'what'. |
|
|
Cappiam
Joined: 10 Apr 2018 Posts: 17 Location: New England
|
|
Posted: Wed Dec 18, 2019 7:26 am |
|
|
Ttelmah wrote: | Post what you have changed in loader.c.
The bootloader does work, so it is something you have done that is
causing the problem. You need to give us a chance to see 'what'. |
That's the thing, I'm working with an unmodified version of loader.c. I have previously modified it like when I added the test code, but I've always reverted to the original loader.c provided by CCS afterwards, for the very reason that I figured it must have been something I changed. To preserve the original, I copied and renamed the files any time I made a change, so #include <loader.c> should only be calling the original in the CCS drivers folder. During this discussion, I've checked several times to make sure I don't have another file named loader.c that it could be accidentally calling.
Now, I did consider the possibility I accidentally changed the original loader.c file, as such I can certainly post the entire loader.c file, if that's acceptable(Or DM it?). However, Windows shows the date modified as 6/16/2015 so unless windows is incorrectly displaying the modified date, it should be identical to the one CCS installed, same should be true for the bootloader.h file. |
|
|
Ttelmah
Joined: 11 Mar 2010 Posts: 19543
|
|
Posted: Thu Dec 19, 2019 8:37 am |
|
|
What is your compiler version number?
Critical thing that people forget to post. We need this to see what code you
are actually using. |
|
|
Cappiam
Joined: 10 Apr 2018 Posts: 17 Location: New England
|
|
Posted: Thu Dec 19, 2019 10:56 am |
|
|
Ttelmah wrote: | What is your compiler version number?
|
Sorry, you're right, I completely forgot to post that. I believe it is the most recent since I recently updated it a few weeks ago, 5.091. |
|
|
|
|
You cannot post new topics in this forum You cannot reply to topics in this forum You cannot edit your posts in this forum You cannot delete your posts in this forum You cannot vote in polls in this forum
|
Powered by phpBB © 2001, 2005 phpBB Group
|