I have some equations with int64 variables that are supposed to run on an Aduino. I need to run them on a PIC16F866.
A few simple tests on a PIC16F886 reveals that it is easy to overflow and get garbage with no warnings.

Code:

float32 SENS;
SENS = 123456789;

results in displaying SENS = -5392220.13

Code:

SENS = 12345678;

displays as 12345678.08

Code:

SENS = 1.23456789E6;

displays as 1234567.92

Code:

SENS = 1.23456789E7;

displays as 12345679.36

Code:

SENS = 1.23456789E8;

displays as -5392220.13

where did I see that before (above)
So the following gives garbage, unlike my HP48 calculator that gives the correct answer.

What am I doing wrong and what should I do?
Why does the compiler not complain or warn?
The big numbers are coming from a sensor via I2c and the original code uses in64 for several variables.
Switching to a 24bit PIC was suggested but the compiler is $400 which is a bit much to solve one problem.
I would think the compiler would round off the numbers to maximum digits and get the correct answer.
Any other suggestions?

Ttelmah

Joined: 11 Mar 2010Posts: 12622

Posted: Sun Dec 10, 2017 1:54 pm

Quote:

I have some equations with int64 variables that are supposed to run on an Aduino. I need to run them on a PIC16F866.
A few simple tests on a PIC16F886 reveals that it is easy to overflow and get garbage with no warnings.

Code:
float32 SENS;
SENS = 123456789;

results in displaying SENS = -5392220.13

How are you seeing this 'result'.
What is your compiler version?.

The maths doesn't overflow like this. What it does do is give the small errors like you have in your next part. However all FP systems do give these to some extent. There are numbers (1/3 for example), that just won't represent in binary FP. The 4 byte version typically gives about 6 digits of usable accuracy.

A wrong display may occur on some compiler versions if you don't specify a 'width' for an FP output.
So %f may give a display error like this. Try %7f instead and you may well find this problem disappears.
It happens when the output can't decide if it should display normally or in exponential form.

rovtech

Joined: 24 Sep 2006Posts: 182

Posted: Sun Dec 10, 2017 4:12 pm

Thanks Ttelmah, here is more of my code. The results are displayed on a 4 line x 20 LCD. It has worked well so I don't suspect it. I was using %f and changing as you suggested gave completely different values.
%f gave -5392220.13
%7f gave -2030.024528 for both OFFSET and SENS
PCM compiler ver 5.05 MPLAB v 8.92 PIC16F886

There isn't any such compiler version as 5.05. CCS versions are always x.xxx
However if this is 5.005, then this was an early beta. The V5 compilers need to be around 5.012, before they started working at all well....

rovtech

Joined: 24 Sep 2006Posts: 182

Posted: Mon Dec 11, 2017 8:18 am

Sorry, I was in a hurry to leave yesterday. My compiler is:
CCS PCM C Compiler, Version 5.055

I will strip my code (several pages) down to minimum and post the whole thing but I don't think it will make any difference. Except for where the definitions are located the rest of the code is one block in main() so it should not matter what happened to the variables before that.

I could buy the latest version but if it doesn't work then I may have to consider going to the 24 bit PIC which would be wasted money on the update. I really don't want to run the code on an Arduino either.

My problems with the Arduino from my original post was explained to me:
"The reason you are unable to print at int64_t is because there is no "Serial.print" function definition for Serial.print(int64_t var). The math libraries support the 64 bit operations but you cannot print the numbers with Arduino's current code."

temtronic

Joined: 01 Jul 2010Posts: 5816Location: Greensville,Ontario

Posted: Mon Dec 11, 2017 8:29 am

re:
My problems with the Arduino from my original post was explained to me:
"The reason you are unable to print at int64_t is because there is no "Serial.print" function definition for Serial.print(int64_t var). The math libraries support the 64 bit operations but you cannot print the numbers with Arduino's current code."

gee ain't that great....NO way to confirm/deny the numbers are right !!

gives OFFSET as 8.00 not as good as my HP48 calculator which gives 1. I just had to check.
and

Code:

OFFSET = 123456789;
OFFSET = OFFSET - 123450000;

gives 6792.00 which is close but not good enough.

rovtech

Joined: 24 Sep 2006Posts: 182

Posted: Mon Dec 11, 2017 10:05 am

Disaster:
I found I had a CCS PCM C Compiler, Version 5.064 downloaded but never installed (if it ain't broke don't fix it).
I installed it but now even my LCD display does not work. It compiles, programs the PIC and verifies, clears it, etc. but just a blank LCD. That's why I hate installing the latest updates.
Was this a bad version?

gives OFFSET as 8.00 not as good as my HP48 calculator which gives 1. I just had to check.
and
Code:

OFFSET = 123456789;
OFFSET = OFFSET - 123450000;

gives 6792.00 which is close but not good enough.

They are both as good as you are going to get.

Float (On the PIC18, there is only one type), has a 23.5 bit mantissa. It is coded as a 23 bit mantissa, with an invisible starting '1'. So numbers that code as 11111111... get 24 bit equivalent accuracy, but anything requiring a '0' at the end, only gets 23 bits. 6.8 digits of equivalent decimal 'accuracy'.
Also though coding as binary fractions in this way has limitations. Some numbers expand to infinite series, and will give errors no matter how many digits you have.

Float is designed to give _flexibility_ by automatically scaling numbers to display the most significant digits, but at a lot of precision.

Just re-install the old version from your backup.

However that 5.064 doesn't work may well be showing that there is something fundamentally flawed in the code. The later compiler will almost certainly default to using the I2C hardware, and will clock it as fast as possible. Are you sure your LCD can support this rate?. Specify a baud rate in the setup.

PCM programmer

Joined: 06 Sep 2003Posts: 20135

Posted: Mon Dec 11, 2017 11:42 am

rovtech wrote:

How do I go back to the old version?

1. If you have the old installer file (.exe file) for vs. 5.055, just run it.

2. If you have System Restore enabled on your Windows PC, you can go
back to a previous restore point. Choose the latest one, just before you
installed vs. 5.064.

PCM programmer

Joined: 06 Sep 2003Posts: 20135

Posted: Mon Dec 11, 2017 12:08 pm

Ttelmah, to me it looks like a bug in printf. The test program shown below,
compiled with vs. 5.075, gives the following output in MPLAB vs. 8.92
simulator. The 2nd number is incorrect:

Just worth adding that calculators generally use BCD arithmetic, not floats. It is not hard to use a BCD library on the PIC.
The PIC does include two features that help with BCD. Swap (allows a nibble to be swapped in one instruction), and the DC bit which flags a carry from the bottom nibble.

Also as a comment, on the PIC24/30/33 the int64 type does print correctly.

rovtech

Joined: 24 Sep 2006Posts: 182

Posted: Mon Dec 11, 2017 1:43 pm

Windows restore did not restore ver 5.055
I cannot find the 5.055 ver install file
I installed ver 5.019 which does the same as 5.064 and my LCD is still blank with blinking cursor top left.
It looks like the update somehow messed up my LCD serial driver, most likely changed it's address. I will sort this out.
The install says it saved a copy of 5.055 but I cannot find instructions on how to open it. I may as well use 5.064.

So the problem is in printf but will purchasing the latest pcm fix the problem?
I don't mind that but pcd is another matter and probably means new circuit boards, a learning curve, and who knows, besides the cost.

PCM programmer

Joined: 06 Sep 2003Posts: 20135

Posted: Mon Dec 11, 2017 1:46 pm

I did my testing with the latest version (vs. 5.075). It has the problem.

Ttelmah

Joined: 11 Mar 2010Posts: 12622

Posted: Mon Dec 11, 2017 2:01 pm

There is another problem. Your functions are fundamentally flawed.

send_str, will keep punching out data past the end of the string. Could be anything....

Then if the compiler switches to exponential format, there is nothing to stop the data overflowing the buffer. This will then result in garbage being displayed.

Make your buffer larger. 32 characters. Then only print the 20 your display supports. You also say 'start with a Z', but don't do so. Does the display need this?. Hopefully you will then see the data, and can work out how much it is actually overflowing.