Skip to main content
Explorer
September 11, 2020
Question

Cosmic compiler producing wrong asm

  • September 11, 2020
  • 3 replies
  • 843 views

I couldn't find a forum for the cosmic compiler. If anyone knows of one let me know and I'll ask there instead.

I have code that is compiling wrong. A function has a u16 parameter and that param is being referenced as u8. This is the declaration of the function ...

u16 getTempFromAdcCount(u16 count);

This is the function ...

u16 getTempFromAdcCount(u16 count) {
 u8 countOfs, lowIdx, idxOfs;
 u16 lowTemp, hiTemp, tempDiff;
 if(count < MIN_ADC_COUNT) return 200*10;
 if(count >= MAX_ADC_COUNT) return 0;
 count -= MIN_ADC_COUNT;
 lowIdx = countOfs >> DELTA_SHIFT;
 idxOfs = countOfs & DELTA_MASK;
 hiTemp = tempTable[lowIdx];
 if(idxOfs == 0) 
 return hiTemp;
 lowTemp = tempTable[lowIdx+1];
 tempDiff = hiTemp - lowTemp;
 return hiTemp - ((tempDiff * idxOfs) >> DELTA_SHIFT);
}

This is the call ...

 temp = getTempFromAdcCount(adjCount);

This is the asm for the call. Note that the param is correctly pushing u16 on the stack ...

 106 ; 23 temp = getTempFromAdcCount(adjCount);
 108 0023 1e01 	ldw	x,(OFST-1,sp)
 109 0025 cd0000 	call	_getTempFromAdcCount
 111 0028 1f01 	ldw	(OFST-1,sp),x

And this is the incorrect asm for the function being called. Note that it is treating the param as u8 ...

 225 0000 _getTempFromAdcCount:
 227 0000 89 	pushw	x
 228 0001 5208 	subw	sp,#8
 229 00000008 OFST:	set	8
 232 ; 147 if(count < MIN_ADC_COUNT) return 200*10;
 234 0003 a30020 	cpw	x,#32
 235 0006 2405 	jruge	L75
 238 0008 ae07d0 	ldw	x,#2000
 240 000b 2008 	jra	L6
 241 000d L75:
 242 ; 148 if(count >= MAX_ADC_COUNT) return 0;
 244 000d 1e09 	ldw	x,(OFST+1,sp)
 245 000f a30388 	cpw	x,#904
 246 0012 2504 	jrult	L16
 249 0014 5f 	clrw	x
 251 0015 L6:
 253 0015 5b0a 	addw	sp,#10
 254 0017 81 	ret
 255 0018 L16:
 256 ; 149 countOfs = count - MIN_ADC_COUNT;
 258 0018 7b0a 	ld	a,(OFST+2,sp)
 259 001a a020 	sub	a,#32
 260 001c 6b08 	ld	(OFST+0,sp),a
...snip...

Can anyone tell me what is going on?

    This topic has been closed for replies.

    3 replies

    mchahnAuthor
    Explorer
    September 11, 2020

    Correction. I showed asm for a different version of the code. Just note that this code in the function has the wrong asm ...

     256 ; 149 countOfs = count - MIN_ADC_COUNT;
     258 0018 7b0a 	ld	a,(OFST+2,sp) <-- should be u16
     259 001a a020 	sub	a,#32
     260 001c 6b08 	ld	(OFST+0,sp),a

    Graduate II
    September 11, 2020

    countOfs is however a u8

    Try

    #define MIN_ADC_COUNT ((u16)32)

    mchahnAuthor
    Explorer
    September 11, 2020

    And also, this is the definition of MIN_ADC_COUNT

    #define MIN_ADC_COUNT 32 // index for adc count 32 is 0

    mchahnAuthor
    Explorer
    September 11, 2020

    Yes, the left-side, countOfs, is a u8. But it should do the u16 arithmetic in 16-bit and then auto-convert the result to 8-bit to store in countOfs. I'll change countOfs to u16 but I still think the compiler is wrong. From a google search ...

    • All the data types of the variables are upgraded to the data type of the variable with largest data type.

    Graduate II
    September 12, 2020

    Yeah, and you're probably using the optimizer.

    The earlier code, does a min/max scoping, then masks and shifts.

    Why on earth have an intermediate value that's not going to hold a number in the 32 .. 904 range, you're asking for some failure across the input number space.

    mchahnAuthor
    Explorer
    September 12, 2020

    Thanks. It's a long story. Works fine now.