Im Allgemeinen nicht unbedingt spezifisch für diesen Prozessor, hat es mit Vorzeichenerweiterung und Maskierung zu tun, erfordern zusätzliche Anweisungen getreulich den C-Quellcode zu implementieren. Ein vorzeichenbehafteter 8-Bit-Wert in einem 16- oder 32- oder 64-Bit-Prozessor kann zusätzliche Anweisungen zum Signieren von Extend beinhalten. Ein 8-Bit auf 32-Bit-Prozessor hinzufügen könnte beinhalten zusätzliche Anweisungen und mit 0xFF usw.
Sie sollten ein paar einfache Experimente durchführen, es dauerte ein paar Wiederholungen, aber ich traf schnell etwas, das einen Unterschied zeigte.
unsigned int fun (unsigned int a, unsigned int b)
{
return(a+b)<<3;
}
unsigned char bfun (unsigned char a, unsigned char b)
{
return(a+b)<<3;
}
int sfun ( int a, int b)
{
return(a+b)<<3;
}
char sbfun ( char a, char b)
{
return(a+b)<<3;
}
produziert
00000000 <fun>:
0: 0f 5e add r14, r15
2: 0f 5f rla r15
4: 0f 5f rla r15
6: 0f 5f rla r15
8: 30 41 ret
0000000a <bfun>:
a: 4f 5e add.b r14, r15
c: 4f 5f rla.b r15
e: 4f 5f rla.b r15
10: 4f 5f rla.b r15
12: 30 41 ret
00000014 <sfun>:
14: 0f 5e add r14, r15
16: 0f 5f rla r15
18: 0f 5f rla r15
1a: 0f 5f rla r15
1c: 30 41 ret
0000001e <sbfun>:
1e: 8f 11 sxt r15
20: 8e 11 sxt r14
22: 0f 5e add r14, r15
24: 0f 5f rla r15
26: 0f 5f rla r15
28: 0f 5f rla r15
2a: 4f 4f mov.b r15, r15
2c: 30 41 ret
Die msp430 Wort und Byte-Versionen der Befehle hat so eine einfache Addition oder Subtraktion muß nicht den Ausschnitt zu tun oder Verlängerung zu unterzeichnen, die man erwarten würde bei der Verwendung kleiner als registrieren Größe Variablen. Als Programmierer wissen wir vielleicht, dass wir sbfun nur mit sehr kleinen Zahlen füttern würden, aber der Compiler tut das nicht und muss unseren Code wie geschrieben treu umsetzen und mehr Code zwischen sfun und sbfun generieren. Es ist nicht schwer, diese Experimente mit verschiedenen Compilern und Prozessoren zu machen, um dies in Aktion zu sehen. Der einzige Trick besteht darin, Code zu erstellen, den der Prozessor nicht einfach zu lösen braucht.
weiteres Beispiel
unsigned int fun (unsigned int a, unsigned int b)
{
return(a+b)>>1;
}
unsigned char bfun (unsigned char a, unsigned char b)
{
return(a+b)>>1;
}
produziert
00000000 <fun>:
0: 0f 5e add r14, r15
2: 12 c3 clrc
4: 0f 10 rrc r15
6: 30 41 ret
00000008 <bfun>:
8: 4f 4f mov.b r15, r15
a: 4e 4e mov.b r14, r14
c: 0f 5e add r14, r15
e: 0f 11 rra r15
10: 4f 4f mov.b r15, r15
12: 30 41 ret
afaik MSP430 keinen Unterschied in Anweisungs Latenz zwischen 8-Bit- und 16-Bit-Operanden hat. Ich bin auch neugierig. –
Ich möchte nur hinzufügen, dass die wunderbare Sache, die ich liebe, über '(u) int_ (schnell | dest) (8 | 16 | 32) _t' ist, dass Sie angeben können, welche Art von Optimierung Sie wollen und in der Regel den Compiler Griff lassen es. Wenn Sie so wenig Platz wie möglich nutzen wollen, und Sie müssen repräsentieren bis zu 20.000, Verwendung '(u) int_least16_t', aber wenn Sie etwas für schwere Berechnung verwenden, die Sie schnell wollen, können Sie' (u) int_fast16_t' weitgehend ohne sich Gedanken darüber machen zu müssen, welchen Typ es unter der Haube gibt. – rjp