CCS C Software and Maintenance Offers
FAQFAQ   FAQForum Help   FAQOfficial CCS Support   SearchSearch  RegisterRegister 

ProfileProfile   Log in to check your private messagesLog in to check your private messages   Log inLog in 

CCS does not monitor this forum on a regular basis.

Please do not post bug reports on this forum. Send them to CCS Technical Support

Help with abs() function

 
Post new topic   Reply to topic    CCS Forum Index -> General CCS C Discussion
View previous topic :: View next topic  
Author Message
dbj



Joined: 01 Jun 2014
Posts: 3

View user's profile Send private message

Help with abs() function
PostPosted: Sun Jun 01, 2014 12:55 pm     Reply with quote

Can someone please tell me what I'm doing wrong. I can't seem to get the abs() function to return the correct value - (s, t, and x are always -500). Code compiles without errors. Compiler version 5.026

Code:

#include <16F1847.H>
#device *=16
#FUSES MCLR
#FUSES NOWDT                    //No Watch Dog Timer
#FUSES NOBROWNOUT               //No brownout reset
#FUSES NOLVP                    //No low voltage prgming
#use delay (internal=4M)
#use rs232(baud=19200,parity=N,xmit=PIN_B4,rcv=PIN_B3,bits=8,stream=PORT1)     // Tx=(PIN 10), Rx=(PIN 9)
#include <stdlib.h>

void main()
{
   long s = -500;
   long t = abs(s);
   long x = labs(s);
   printf("s= %Ld   t= %Ld   x= %Ld  \r\n",s,t,x);
}

PCM programmer



Joined: 06 Sep 2003
Posts: 21708

View user's profile Send private message

PostPosted: Sun Jun 01, 2014 1:11 pm     Reply with quote

Read the CCS manual. It says:
Quote:

unsigned -
Data is always positive. This is the default data type if not specified.

Which means you need to declare your variables as 'signed long',
to get your program to work properly.

Or, also given in the manual, you could put the compiler in ANSI mode:
Quote:

#include <16F1847.H>
#device ANSI

The manual says:
Quote:
ANSI - Default data type is SIGNED
Ttelmah



Joined: 11 Mar 2010
Posts: 19499

View user's profile Send private message

PostPosted: Sun Jun 01, 2014 2:40 pm     Reply with quote

As a further bit of explanation.

The value -500, codes as 0xFE0C.

When you write this into an unsigned int16, you store 0xFE0C, which in an unsigned variable is treated as 65036.
Feeding 65036 into abs, gives 65036 out (abs knows the types of the variables it is given).
Then taking the unsigned integer 65036, and printing this as a signed value, displays -500.

As a comment, I'd suggest getting out of the habit of using 'indeterminate' types like 'long'. Much safer to code as int16, which you then 'know' how long the value is whatever processor/compiler you are using. Even better, load stdint.h, and be really explicit, with 'uint16_t', and 'int16_t' for unsigned and signed.
dbj



Joined: 01 Jun 2014
Posts: 3

View user's profile Send private message

PostPosted: Sun Jun 01, 2014 4:57 pm     Reply with quote



PCM - I knew it was something simple and stupid like that. I think I'll fix it by changing how I declare it. Yeah, I've read quite a bit of the manual, but it's hard to keep track of all the nuances that are so obvious to seasoned programmers.

Ttelmah - Thanks for the detailed explanation, that makes a lot of sense now. It's been about 20 yrs since the last time I did programming, and that was in assembly on a 68HC11, so not only do I have to ramp back up with how to program a microcontroller but also learn C. I'll change the code in my real program (not the test one I posted) to what you suggested.

And thanks to both of you for all your help, not only in this post, but in the dozens of other threads that I've searched through in the past few weeks.
Display posts from previous:   
Post new topic   Reply to topic    CCS Forum Index -> General CCS C Discussion All times are GMT - 6 Hours
Page 1 of 1

 
Jump to:  
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