Jak se prelozi

Pavel Hudeček edizon na seznam.cz
Čtvrtek Duben 25 18:33:18 CEST 2024


Na to jsem se chtěl zeptat. Mě taky překvapilo, že mezitím nejsou řádky 
C kódu, jak jsem si pamatoval že vždycky byly. Takže předpokládám, že 
bych někam do nastavení buildu musel připsat pár písmenek.

PH

Dne 25.04.2024 v 18:27 Jan Waclawek napsal(a):
> <__TEXT_REGION_LENGTH__+0x7f0447>
>     fe:    40 91 a8 04     lds    r20, 0x04A8    ; 0x8004a8
> <__TEXT_REGION_LENGTH__+0x7f04a8>
>    102:    30 91 a8 04     lds    r19, 0x04A8    ; 0x8004a8
> [...]
> <__TEXT_REGION_LENGTH__+0x7f0444>
>    10e:    46 fd           sbrc    r20, 6
>    110:    90 93 44 04     sts    0x0444, r25    ; 0x800444
> <__TEXT_REGION_LENGTH__+0x7f0444>
>    114:    37 fd           sbrc    r19, 7
>    116:    20 93 44 04     sts    0x0444, r18    ; 0x800444
> <__TEXT_REGION_LENGTH__+0x7f0444>
>
>
> Skoda, ze v tom listingu nie su zdrojove riadky, to je C++ artefakt, alebo
> len zle nastaveny nejaky -gX switch pri preklade?
>
> Kazdopadne, v tomto priklade je uplne vyoptimalizovany samotny struct - v
> prvych dvoch riadkoch sa precita port (musi sa citat dvakrat, lebo
> volatile); a vo zvysku sa na zaklade tych precitanych hodnot priamo v
> registroch zapise do vystupneho portu.
>
>
> Ja som to skusil s volatile structom, aby ho nevyoptimalizoval (a
> neplusplus C):
>
> #include <stdint.h>
> #include <stdbool.h>  // bring in bool, which is not a native type in C
>
> struct {
>    bool b0:1;
>    bool b1:1;
> } volatile b;
>
> volatile uint8_t k;
>
> int main(void) {
>    b.b0 = (bool)k;
>    b.b1 = (bool)k;
>    if(b.b0) {
>      k = 10;
>    };
>    if(b.b1) {
>      k = 20;
>    };
> }
>
>
> avr-gcc 4.2.2:
> int main(void) {
>    b.b0 = (bool)k;
>   112:	90 91 01 02 	lds	r25, 0x0201
>   116:	91 11       	cpse	r25, r1
>   118:	91 e0       	ldi	r25, 0x01	; 1
>   11a:	91 70       	andi	r25, 0x01	; 1
>   11c:	80 91 00 02 	lds	r24, 0x0200
>   120:	8e 7f       	andi	r24, 0xFE	; 254
>   122:	89 2b       	or	r24, r25
>   124:	80 93 00 02 	sts	0x0200, r24
>    b.b1 = (bool)k;
>   128:	90 91 01 02 	lds	r25, 0x0201
>   12c:	91 11       	cpse	r25, r1
>   12e:	91 e0       	ldi	r25, 0x01	; 1
>   130:	91 70       	andi	r25, 0x01	; 1
>   132:	99 0f       	add	r25, r25
>   134:	80 91 00 02 	lds	r24, 0x0200
>   138:	8d 7f       	andi	r24, 0xFD	; 253
>   13a:	89 2b       	or	r24, r25
>   13c:	80 93 00 02 	sts	0x0200, r24
>    if(b.b0) {
>   140:	80 91 00 02 	lds	r24, 0x0200
>   144:	80 ff       	sbrs	r24, 0
>   146:	03 c0       	rjmp	.+6      	; 0x14e <main+0x3c>
>      k = 10;
>   148:	8a e0       	ldi	r24, 0x0A	; 10
>   14a:	80 93 01 02 	sts	0x0201, r24
>    };
>    if(b.b1) {
>   14e:	80 91 00 02 	lds	r24, 0x0200
>   152:	81 ff       	sbrs	r24, 1
>   154:	03 c0       	rjmp	.+6      	; 0x15c <main+0x4a>
>      k = 20;
>   156:	84 e1       	ldi	r24, 0x14	; 20
>   158:	80 93 01 02 	sts	0x0201, r24
>    };
> }
>   15c:	08 95       	ret
>
>
> avr-gcc 8.0:
> int main(void) {
>    b.b0 = (bool)k;
>    f8:	80 91 01 02 	lds	r24, 0x0201	; 0x800201 <k>
>    fc:	91 e0       	ldi	r25, 0x01	; 1
>    fe:	81 11       	cpse	r24, r1
>   100:	01 c0       	rjmp	.+2      	; 0x104 <main+0xc>
>   102:	90 e0       	ldi	r25, 0x00	; 0
>   104:	80 91 00 02 	lds	r24, 0x0200	; 0x800200 <_edata>
>   108:	90 fb       	bst	r25, 0
>   10a:	80 f9       	bld	r24, 0
>   10c:	80 93 00 02 	sts	0x0200, r24	; 0x800200 <_edata>
>    b.b1 = (bool)k;
>   110:	80 91 01 02 	lds	r24, 0x0201	; 0x800201 <k>
>   114:	91 e0       	ldi	r25, 0x01	; 1
>   116:	81 11       	cpse	r24, r1
>   118:	01 c0       	rjmp	.+2      	; 0x11c <main+0x24>
>   11a:	90 e0       	ldi	r25, 0x00	; 0
>   11c:	80 91 00 02 	lds	r24, 0x0200	; 0x800200 <_edata>
>   120:	90 fb       	bst	r25, 0
>   122:	81 f9       	bld	r24, 1
>   124:	80 93 00 02 	sts	0x0200, r24	; 0x800200 <_edata>
>    if(b.b0) {
>   128:	80 91 00 02 	lds	r24, 0x0200	; 0x800200 <_edata>
>   12c:	80 ff       	sbrs	r24, 0
>   12e:	03 c0       	rjmp	.+6      	; 0x136 <main+0x3e>
>      k = 10;
>   130:	8a e0       	ldi	r24, 0x0A	; 10
>   132:	80 93 01 02 	sts	0x0201, r24	; 0x800201 <k>
>    };
>    if(b.b1) {
>   136:	80 91 00 02 	lds	r24, 0x0200	; 0x800200 <_edata>
>   13a:	81 ff       	sbrs	r24, 1
>   13c:	03 c0       	rjmp	.+6      	; 0x144 <main+0x4c>
>      k = 20;
>   13e:	84 e1       	ldi	r24, 0x14	; 20
>   140:	80 93 01 02 	sts	0x0201, r24	; 0x800201 <k>
>    };
> }
>   144:	90 e0       	ldi	r25, 0x00	; 0
>   146:	80 e0       	ldi	r24, 0x00	; 0
>   148:	08 95       	ret
>
>
> cize viacmenej identicky, najprv sa cita z "portu" (volatile premennej na
> adrese 0x0201) do r24, do r25 sa vyrobi 0 alebo 1 (t.j. bool), a potom sa
> ten bit ulozi(*) do toho structu co je na adrese 0x200; to iste sa urobi s
> druhym bitom; no a nakoniec sa pouzije sbrs (t.j. bitovy test a
> obskocenie, take to PICkarske btfsz).
>
> Jediny rozdiel je, ze to ulozenie bitu do structu (*) je v jednom pripade
> and/or, a v druhom sa vyuziva bit T v stavovom slove a instrukcie bst a
> bld.
>
> Zlata '51 s bitovou pamatou... a este aj ten bit-banding (a
> bitfield-clear-set-copy instrukcie) v Cortex-M3/M4... :-) ale pouzitelne
> to aj na tom AVR je.
>
> wek
>
>
> _______________________________________________
> HW-list mailing list  -  sponsored by www.HW.cz
> Hw-list na list.hw.cz
> http://list.hw.cz/mailman/listinfo/hw-list



Další informace o konferenci Hw-list