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

Possible bug in ccsc 4.104 using PIC16F57 compiling subtract

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







Possible bug in ccsc 4.104 using PIC16F57 compiling subtract
PostPosted: Mon Feb 22, 2010 4:51 am     Reply with quote

hi,

I have this behavior when I compile this C line:
Code:

signed char tre;
signed char bass;
tre=(0x1-bass)|0x80;

this is a one substraction and a seven bit set.

the output in Disassembly Listing:
Code:

362:   tre=(0x1-bass)|0x80;
   569     217     MOVF 0x17, W
   56A     081     SUBWF 0x1, W
   56B     D80     IORLW 0x80
   56C     036     MOVWF 0x16

If I put tre=(0x10-bass)|0x80;
Code:

362:  tre=(0x10-bass)|0x80;
   569     217     MOVF 0x17, W
   56A     090     SUBWF 0x10, W
   56B     D80     IORLW 0x80
   56C     036     MOVWF 0x16

It seems that the literal value is taken as direction. Address 0x17 is bass variable and 0x16 is tre.

Is it a bug?
FvM



Joined: 27 Aug 2008
Posts: 2337
Location: Germany

View user's profile Send private message

PostPosted: Mon Feb 22, 2010 7:31 am     Reply with quote

It's correct in my V4.104 compilation

CCS PCM C Compiler, Version 4.104, 48030 22-Feb-10 14:29

.................... signed char tre;
.................... signed char bass;
.................... tre=(0x1-bass)|0x80;
040A: MOVF 4F,W
040B: SUBLW 01
040C: IORLW 80
040D: MOVWF 4E
Ttelmah
Guest







PostPosted: Mon Feb 22, 2010 11:37 am     Reply with quote

Yes, it ilooks like the old 'multiple CCS releases' syndrome:

CCS PCB C Compiler, Version 4.104, 51458 22-Feb-10 17:25

Simple test code:
Code:

#include <16F57.h>
#FUSES XT
#use delay(clock=4000000)

signed char tre;
signed char bass;

#define x &

void main(void) {

   tre=(0x1-bass)|0x80;
   
   while (TRUE) {
      delay_ms(1);
   }
}


Note it has selected 'PCB'!.
Generates:

Code:

....................    tre=(0x1-bass)|0x80; 
0017:  MOVF   0B,W
0018:  SUBWF  01,W
0019:  IORLW  80
001A:  MOVWF  0A


It looks as if this earlier release, really gets confused by the 16F57....

Change the chip to 16F84, and it correctly selects PCM, and generates the right code....

Best Wishes
FvM



Joined: 27 Aug 2008
Posts: 2337
Location: Germany

View user's profile Send private message

PostPosted: Mon Feb 22, 2010 1:18 pm     Reply with quote

I wasn't aware that CCS C requests PCB with 16F57.

The bug is also present with various previous PCB V4 versions, but not all.

V4.084 and V4.087 generated correct, but rather long-winded code
Code:
CCS PCB C Compiler, Version 4.084, 45911
.................... signed char tre; 
.................... signed char bass; 
.................... tre=(0x1-bass)|0x80; 
*
0004:  MOVF   0C,W
0005:  MOVWF  09
0006:  MOVLW  01
0007:  MOVWF  0C
0008:  MOVF   09,W
0009:  SUBWF  0C,W
000A:  IORLW  80
000B:  MOVWF  0B


At lest since V4.093, the code is incorrect
Code:
.................... signed char tre; 
.................... signed char bass; 
.................... tre=(0x1-bass)|0x80; 
*
0004:  MOVF   0C,W
0005:  SUBWF  01,W
0006:  IORLW  80
0007:  MOVWF  0B
Ttelmah
Guest







PostPosted: Mon Feb 22, 2010 1:53 pm     Reply with quote

Sorry about the #define, I was trying some silly defines, like the one shown, to see if it triggered the fault, then found none was needed....
They make no difference.
To the original poster, report it. It seems to be a real 'gaffe' with this particular chip...

Best Wishes
Diego
Guest







PostPosted: Tue Feb 23, 2010 3:32 am     Reply with quote

I`m trying to get a workaround, I paste this simple code.

Note that in the pic16f84 there is a SUBLW opcode. So the result is always right for pic16f84.

Is there any limitation of several literals per line?
This could be the cause of the problem.
Code:

//#define 16f57
//#include <16f57.h>
#define 16f84
#include <16f84.h>
unsigned char result,op,literal;
void main(){
   op=1;
   result=1;
   literal=20;
   //work fine with one literal per line
   result=(literal-op)|0x80;
   // don't work with two literal per line
   result=(20-op)|0x80;   
   //workaround
   result=20-op;
   result=result|0x80;
}


Disasembly Listing for 16f84
Code:

1:                 //#define 16f57
   000    3000     MOVLW 0
   001    008A     MOVWF 0xa
   002    2804     GOTO 0x4
   003    0000     NOP
2:                 //#include <16f57.h>
3:                 #define 16f84
4:                 #include <16f84.h>
5:                 unsigned char result,op,literal;
6:                 void main(){
   004    0184     CLRF 0x4
   005    301F     MOVLW 0x1f
   006    0583     ANDWF 0x3, F
7:                    op=1;
   007    3001     MOVLW 0x1
   008    0091     MOVWF 0x11
8:                    result=1;
   009    0090     MOVWF 0x10
9:                    literal=20;
   00A    3014     MOVLW 0x14
   00B    0092     MOVWF 0x12
10:                   //work fine with one literal per line
11:                   result=(literal-op)|0x80;
   00C    0811     MOVF 0x11, W
   00D    0212     SUBWF 0x12, W
   00E    3880     IORLW 0x80
   00F    0090     MOVWF 0x10
12:                   // don't work with two literal per line
13:                   result=(20-op)|0x80;   
   010    0811     MOVF 0x11, W
   011    3C14     SUBLW 0x14
   012    3880     IORLW 0x80
   013    0090     MOVWF 0x10
14:                   //workaround
15:                   result=20-op;
   014    0811     MOVF 0x11, W
   015    3C14     SUBLW 0x14
   016    0090     MOVWF 0x10
16:                   result=result|0x80;
   017    1790     BSF 0x10, 0x7
   018    0063     SLEEP


Disasembly Listing for 16f57
Code:

1:                 #define 16f57
   000     A01     GOTO 0x1
   7FF     A00     GOTO 0
2:                 #include <16f57.h>
3:                 //#define 16f84
4:                 //#include <16f84.h>
5:                 unsigned char result,op,literal;
6:                 void main(){
   001     064     CLRF 0x4
7:                    op=1;
   002     C01     MOVLW 0x1
   003     02B     MOVWF 0xb
8:                    result=1;
   004     C01     MOVLW 0x1
   005     02A     MOVWF 0xa
9:                    literal=20;
   006     C14     MOVLW 0x14
   007     02C     MOVWF 0xc
10:                   //work fine with one literal per line
11:                   result=(literal-op)|0x80;
   008     20B     MOVF 0xb, W
   009     08C     SUBWF 0xc, W
   00A     D80     IORLW 0x80
   00B     02A     MOVWF 0xa
12:                   // don't work with two literal per line
13:                   result=(20-op)|0x80;   
   00C     20B     MOVF 0xb, W
   00D     094     SUBWF 0x14, W
   00E     D80     IORLW 0x80
   00F     02A     MOVWF 0xa
14:                   //workaround
15:                   result=20-op;
   010     C14     MOVLW 0x14
   011     02A     MOVWF 0xa
   012     20B     MOVF 0xb, W
   013     0AA     SUBWF 0xa, F
16:                   result=result|0x80;
   014     5EA     BSF 0xa, 0x7
   015     003     SLEEP
Ttelmah
Guest







PostPosted: Tue Feb 23, 2010 3:47 am     Reply with quote

You can 'code round' the problem using:

tre=(0x1+(-bass))|0x80;

The problem seems to only apply to what are effectively '12' chips. A few chips like the 16x57, have the more limited instruction set from these smaller chips, lacking the SUBLW instruction. On chips with this instruction, everything is fine, but on the ones without, the compiler doesn't seem to understand how to subtract a signed value...
On these chips, the 'PCB' compiler is used.
The bodge, simply performs an addition, of a negative value. This codes correctly....
There almost certainly is a compiler limitation on 'literals per line', but it is a long way past this point.
I really would complain, since it is rather fundamental....

Best Wishes
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