From: SourceForge.net <no...@so...> - 2004-07-29 16:03:26
|
Bugs item #1000077, was opened at 2004-07-29 14:30 Message generated for change (Comment added) made by bernhardheld You can respond by visiting: https://sourceforge.net/tracker/?func=detail&atid=100599&aid=1000077&group_id=599 Category: None >Group: non bugs >Status: Closed >Resolution: Rejected Priority: 5 Submitted By: Nobody/Anonymous (nobody) >Assigned to: Bernhard Held (bernhardheld) Summary: SDCC int genOr bug Initial Comment: I has found several mistakes in SDCC: Source: #include <8051.h> #define pin1 P1_0 static unsigned int temp; static unsigned int work; unsigned char wrk(void) { return 0; } unsigned int test(void) { register unsigned char tmp1, tmp2; register unsigned int tmp3; tmp1=wrk(); tmp2=wrk(); tmp3=256*tmp1; tmp3|=(unsigned char)tmp2; temp=tmp3; tmp1=wrk(); tmp2=wrk(); tmp3=(unsigned char)tmp1; tmp3|=tmp2 << 8; work=tmp3; tmp3|=pin1; temp=tmp3; return tmp3; } unsigned int test2(void) { register unsigned int tmp; register unsigned char wrk1, wrk2; wrk1=wrk() ; wrk2=wrk() ; tmp=wrk2 << 8; tmp|=wrk1; return tmp; } void main(void) { } SDCC run command: sdcc --verbose --model-small --peep-asm -mmcs51 -- iram-size 128 --xram-size 0 --code-size 4096 -- nojtbound test.c SDCC version: SDCC : mcs51/gbz80/z80/avr/ds390/pic16/pic14/TININative/xa51 /ds400/hc08 2.4.3 #779 (Jul 28 2004) (MINGW32) Asm list: 329 ;------------------------------ ------------------------------ 330 ;Allocation info for local variables in function 'test' 331 ;------------------------------ ------------------------------ 332 ;tmp1 Allocated to registers r2 333 ;tmp2 Allocated to registers r3 334 ;tmp3 Allocated to registers r4 r5 335 ;------------------------------ ------------------------------ 336 ;test.c:13: unsigned int test (void) 337 ; --------------------------- -------------- 338 ; function test 339 ; --------------------------- -------------- 0035 340 _test: 341 ;test.c:17: tmp1=wrk(); 342 ; genCall 0035 12s00r31 343 lcall _wrk 0038 AA 82 344 mov r2,dpl 345 ;test.c:18: tmp2=wrk(); 346 ; genCall 003A C0 02 347 push ar2 003C 12s00r31 348 lcall _wrk 003F AB 82 349 mov r3,dpl 0041 D0 02 350 pop ar2 351 ;test.c:19: tmp3=256*tmp1; 352 ; genCast 0043 8A 04 353 mov ar4,r2 354 ; genLeftShift 355 ; genLeftShiftLiteral 356 ; genlshTwo 357 ; peephole 177.e removed redundant move 0045 8C 05 358 mov ar5,r4 0047 7C 00 359 mov r4,#0x00 360 ;test.c:20: tmp3|=(unsigned char)tmp2; 361 ; genCast 0049 8B 06 362 mov ar6,r3 004B 7F 00 363 mov r7,#0x00 <= Unneeded operation 364 ; genOr 004D EE 365 mov a,r6 004E 42 04 366 orl ar4,a 0050 EF 367 mov a,r7 <= Unneeded operation 0051 42 05 368 orl ar5,a <= Unneeded operation 369 ;test.c:21: temp=tmp3; 370 ; genAssign 0053 8C*00 371 mov _temp,r4 0055 8D*01 372 mov (_temp + 1),r5 373 ;test.c:22: tmp1=wrk(); 374 ; genCall 0057 12s00r31 375 lcall _wrk 005A AA 82 376 mov r2,dpl 377 ;test.c:23: tmp2=wrk(); 378 ; genCall 005C C0 02 379 push ar2 005E 12s00r31 380 lcall _wrk 0061 AB 82 381 mov r3,dpl 0063 D0 02 382 pop ar2 383 ;test.c:24: tmp3=(unsigned char)tmp1; 384 ; genCast 0065 8A 04 385 mov ar4,r2 0067 7D 00 386 mov r5,#0x00 387 ;test.c:25: tmp3|=tmp2 << 8; 388 ; genCast 389 ; genLeftShift 390 ; genLeftShiftLiteral 391 ; genlshTwo 392 ; peephole 177.e removed redundant move 0069 8B 02 393 mov ar2,r3 006B 7B 00 394 mov r3,#0x00 <= Unneeded operation 395 ; genOr 006D EB 396 mov a,r3 <= Unneeded operation 006E 42 04 397 orl ar4,a <= Unneeded operation 0070 EA 398 mov a,r2 0071 42 05 399 orl ar5,a 400 ;test.c:26: work=tmp3; 401 ; genAssign 0073 8C*02 402 mov _work,r4 0075 8D*03 403 mov (_work + 1),r5 404 ;test.c:27: tmp3|=pin1; 405 ; genCast 0077 E4 406 clr a 0078 A2 90 407 mov c,_P1_0 007A 33 408 rlc a 409 ; genOr 410 ; Peephole 177.d removed redundant move 007B FA 411 mov r2,a 007C 7B 00 412 mov r3,#0x00 <= Unneeded operation 007E 42 04 413 orl ar4,a 0080 EB 414 mov a,r3 <= Unneeded operation 0081 42 05 415 orl ar5,a <= Unneeded operation 416 ;test.c:28: temp=tmp3; 417 ; genAssign 0083 8C*00 418 mov _temp,r4 0085 8D*01 419 mov (_temp + 1),r5 420 ;test.c:29: return tmp3; 421 ; genRet 0087 8C 82 422 mov dpl,r4 0089 8D 83 423 mov dph,r5 008B 424 00101$: 008B 22 425 ret 426 ;------------------------------ ------------------------------ 427 ;Allocation info for local variables in function 'test2' 428 ;------------------------------ ------------------------------ 429 ;tmp Allocated to registers r3 r4 430 ;wrk1 Allocated to registers r2 431 ;wrk2 Allocated to registers r3 432 ;------------------------------ ------------------------------ 433 ;test.c:32: unsigned int test2 (void) 434 ; --------------------------- -------------- 435 ; function test2 436 ; --------------------------- -------------- 008C 437 _test2: 438 ;test.c:36: wrk1=wrk() ; 439 ; genCall 008C 12s00r31 440 lcall _wrk 008F AA 82 441 mov r2,dpl 442 ;test.c:37: wrk2=wrk() ; 443 ; genCall 0091 C0 02 444 push ar2 0093 12s00r31 445 lcall _wrk 0096 AB 82 446 mov r3,dpl 0098 D0 02 447 pop ar2 448 ;test.c:38: tmp=wrk2 << 8; 449 ; genCast 450 ; genLeftShift 451 ; genLeftShiftLiteral 452 ; genlshTwo 453 ; peephole 177.e removed redundant move 009A 8B 04 454 mov ar4,r3 455 ;test.c:39: tmp|=wrk1; 456 ; genCast 457 ; genOr 458 ; Peephole 3.c changed mov to clr 009C E4 459 clr a <= Unneeded operation 009D FB 460 mov r3,a <= Unneeded operation 009E FD 461 mov r5,a <= Unneeded operation 009F EA 462 mov a,r2 <= Unneeded operation 00A0 42 03 463 orl ar3,a <= Unneeded operation 00A2 ED 464 mov a,r5 <= Unneeded operation 00A3 42 04 465 orl ar4,a <= Unneeded operation 466 ;test.c:40: return tmp; 467 ; genRet 00A5 8B 82 468 mov dpl,r3 00A7 8C 83 469 mov dph,r4 00A9 470 00101$: 00A9 22 471 ret I'm fix these bug by the following peephole rules: replace { clr a mov r%1,a mov r%2,a mov a,r%3 orl ar%1,a mov a,r%2 orl ar%4,a } by { ; Peephole R.1 super optimized int genOr mov ar%1,r%3 } replace { mov r%1,#0x00 mov a,r%1 orl ar%2,a mov a,r%3 orl ar%4,a } by { ; Peephole R.2 optimized int genOr (low byte skip) mov a,r%3 orl ar%4,a } replace { mov r%1,#0x00 mov a,r%2 orl ar%3,a mov a,r%1 orl ar%4,a } by { ; Peephole R.3 optimized int genOr (high byte skip) mov a,r%2 orl ar%3,a } replace { mov r%1,#0x00 orl ar%2,a mov a,r%1 orl ar%3,a } by { ; Peephole R.4 optimized int genOr (high byte skip) mov r%2,a } With the best wishes, Ruslan. ---------------------------------------------------------------------- >Comment By: Bernhard Held (bernhardheld) Date: 2004-07-29 16:33 Message: Logged In: YES user_id=203539 For my feeling these are not bugs, because the results are correct. Please accept that even the best optimizing C compiler will never generate code, which can keep up with hand optimized assembler. There will always be some overhead. It doesn't make much sense to try to fix all these small sub- optimal code snippets with peephole rules, because there are many, many combinations of code, in which you can find them. It would only make sense on a per-project basis in a performance-critical loop or in an ISR. The superflous "mov r%1,%2" is already reported in your feature request #1000079. ---------------------------------------------------------------------- You can respond by visiting: https://sourceforge.net/tracker/?func=detail&atid=100599&aid=1000077&group_id=599 |