Re: GCC sloučení do správného typu

Tomáš Hamouz konfery.tomas.hamouz na seznam.cz
Čtvrtek Říjen 7 10:37:05 CEST 2021


Je. Dáváte tím překladači najevo že chcete "u" interpretovat jako signed. Může vyhodit warning, že může dojít ke ztrátě dat, ale to je očekávané chování.
Ještě bych k tomu skládání přidal masky na jednotlivé bity. Sice to trochu bude zdržovcat, ale máte jistotu že se nikde nepřiplete nastavený bit který nechcete.

Tedy 
  uint16_t  temp = (((uint16_t)precteno[0] & 0x03U) << 14)
                 | (((uint16_t)precteno[1] & 0x7FU) << 7)
                 | ((uint16_t)precteno[2] & 0x7FU));
  int16_t result = (int16_t)temp; 


Tomáš




No a je spravne napsat napr.:
uint16_t u = 65535;
int16_t i = (int16_t)u;
?
Vim, ze v C to asi funguje ale v C# to nesezere, takze si k tomu davam automaticky !, protoze to je asi v principu nebezpecna konstrukce.
A bitove posuvy v signed muzou taky asi dopadnout ruzne podle platformy a prekladace, ale taky si nejsem jisty.

Dne 07.10.2021 v 10:17 Tomáš Hamouz napsal(a):
Re: GCC sloučení do správného typu Znaménko není třeba řešit. Pokud je v D15 znaménko a budete to skládat do int16_t, tak bude správně nastavené.
Jen bych dal pozor na to, dělat bitové posuny jako unsigned a až na konci to přetypoval na signed.

Tomáš


> No a ted to znamenko,
> int16_t i = (int16_t)res;
> Myslim, ze to funguje ale je mi to nejak proti srsti, je to korektni 
> obecne takto napsat?
> Prasarny typu konverze pres ukazatele... nevim.
> Nejcistsi mi prijde:
> int16_t i = (res & 0x8000) ? (int16_t)((int32_t) res - 65536) : 
> (int16_t)res;
> snad jsem se neseknul, prekladac si s tim pri pohledu do ASM poradi 
> vetsinou se cti.

> Dne 07.10.2021 v 9:24 Jindroush napsal(a):
>> On 07.10.2021 9:03, Jindrich Fucik wrote:
>>> mám tu jednu takovou spíš akademickou otázku. Nejprve popíšu 
>>> prostředí. Hardware je ESP8266, programovaný v Arduino IDE, takže 
>>> překladač je GCC.

>>> ESP je připojeno sériovou linkou do zařízení, které komunikuje 
>>> sedmibitově. zařízení je založeno na 8bit intel platformě, data jsou 
>>> tedy integery 16 bit (znaménkové). Při posílání se nejprve posílá 
>>> MSB, první dva bity, pak prostředních 7 a pak posledních 7 LSB. Data 
>>> přečtu jako pole "byte" (což je jen alias k unsigned char). Pokud se 
>>> pokusím to rozepsat po bitech tak je to takto:

>>> precteno byte[3]
>>> |0 0 0 0  0 0 D15 D14| |0 D13 D12 D11  D10 D9 D8 D7| |0 D6 D5 D4 D3 
>>> D2 D1 D0|

>>> A teď otázka - jak nejefektivněji na tom ESP poskládat zpátky int, 
>>> který zachová znaménko? 

>> pokud mate int16_t na tom esp, tak asi nejak jako, pokud je zajisteno, 
>> ze to, co jste vyse napsal jako '0' je vzdy 0.
>> int16_t res = ( precteno[0] << 14 ) || ( precteno[1]) << 7 ) || 
>> precteno[2];
>> Netusim samozrejme, jak drahy je na takovem procesoru shift a v jak 
>> 'dlouhe' smycce to je.


> _______________________________________________
> HW-list mailing list  -  sponsored by www.HW.cz
> Hw-list na list.hw.cz
> http://list.hw.cz/mailman/listinfo/hw-list 
_______________________________________________
HW-list mailing list  -  sponsored by www.HW.cz
Hw-list na list.hw.cz
http://list.hw.cz/mailman/listinfo/hw-list

No a je spravne napsat napr.:
uint16_t u = 65535;
int16_t i = (int16_t)u;
?
Vim, ze v C to asi funguje ale v C# to nesezere, takze si k tomu davam automaticky !, protoze to je asi v principu nebezpecna konstrukce.
A bitove posuvy v signed muzou taky asi dopadnout ruzne podle platformy a prekladace, ale taky si nejsem jisty.

Dne 07.10.2021 v 10:17 Tomáš Hamouz napsal(a):
Znaménko není třeba řešit. Pokud je v D15 znaménko a budete to skládat do int16_t, tak bude správně nastavené.
Jen bych dal pozor na to, dělat bitové posuny jako unsigned a až na konci to přetypoval na signed.

Tomáš


> No a ted to znamenko,
> int16_t i = (int16_t)res;
> Myslim, ze to funguje ale je mi to nejak proti srsti, je to korektni 
> obecne takto napsat?
> Prasarny typu konverze pres ukazatele... nevim.
> Nejcistsi mi prijde:
> int16_t i = (res & 0x8000) ? (int16_t)((int32_t) res - 65536) : 
> (int16_t)res;
> snad jsem se neseknul, prekladac si s tim pri pohledu do ASM poradi 
> vetsinou se cti.

> Dne 07.10.2021 v 9:24 Jindroush napsal(a):
>> On 07.10.2021 9:03, Jindrich Fucik wrote:
>>> mám tu jednu takovou spíš akademickou otázku. Nejprve popíšu 
>>> prostředí. Hardware je ESP8266, programovaný v Arduino IDE, takže 
>>> překladač je GCC.

>>> ESP je připojeno sériovou linkou do zařízení, které komunikuje 
>>> sedmibitově. zařízení je založeno na 8bit intel platformě, data jsou 
>>> tedy integery 16 bit (znaménkové). Při posílání se nejprve posílá 
>>> MSB, první dva bity, pak prostředních 7 a pak posledních 7 LSB. Data 
>>> přečtu jako pole "byte" (což je jen alias k unsigned char). Pokud se 
>>> pokusím to rozepsat po bitech tak je to takto:

>>> precteno byte[3]
>>> |0 0 0 0  0 0 D15 D14| |0 D13 D12 D11  D10 D9 D8 D7| |0 D6 D5 D4 D3 
>>> D2 D1 D0|

>>> A teď otázka - jak nejefektivněji na tom ESP poskládat zpátky int, 
>>> který zachová znaménko? 

>> pokud mate int16_t na tom esp, tak asi nejak jako, pokud je zajisteno, 
>> ze to, co jste vyse napsal jako '0' je vzdy 0.
>> int16_t res = ( precteno[0] << 14 ) || ( precteno[1]) << 7 ) || 
>> precteno[2];
>> Netusim samozrejme, jak drahy je na takovem procesoru shift a v jak 
>> 'dlouhe' smycce to je.


> _______________________________________________
> HW-list mailing list  -  sponsored by www.HW.cz
> Hw-list na list.hw.cz
> http://list.hw.cz/mailman/listinfo/hw-list 
_______________________________________________
HW-list mailing list  -  sponsored by www.HW.cz
Hw-list na list.hw.cz
http://list.hw.cz/mailman/listinfo/hw-list
------------- další část ---------------
HTML příloha byla odstraněna...
URL: <http://list.hw.cz/pipermail/hw-list/attachments/20211007/772d20e6/attachment.html>


Další informace o konferenci Hw-list