#include <avr/io.h>
#include <stdio.h>
#include <util/setbaud.h>
void uart_init (void)
{
UBRR0H = UBRRH_VALUE;
UBRR0L = UBRRL_VALUE;
#if USE_2X
UCSR0A |= _BV(U2X0);
#else
UCSR0A &= ~(_BV(U2X0));
#endif
UCSR0C = _BV(UCSZ01) | _BV(UCSZ00); /* 8-bit data */
UCSR0B = _BV(RXEN0) | _BV(TXEN0); /* Enable RX and TX */
}
int uart_putchar (char c, FILE *stream)
{
loop_until_bit_is_set(UCSR0A, UDRE0); /* Wait until data register empty. */
UDR0 = c;
return 0;
}
FILE uart_output = FDEV_SETUP_STREAM(uart_putchar, NULL, _FDEV_SETUP_WRITE);
// Returns the index of the highest 1-bit in an integer, starting with 1,
// or zero if the operand is zero.
// Working version. Uses r16 for temporary and mov's the result into %[res].
#if 0
static uint8_t highest_bit (uint32_t op)
{
uint8_t res;
__asm__(
" cpse %D[op],__zero_reg__\n"
" rjmp foundD%=\n"
" cpse %C[op],__zero_reg__\n"
" rjmp foundC%=\n"
" cpse %B[op],__zero_reg__\n"
" rjmp foundB%=\n"
" cpse %A[op],__zero_reg__\n"
" rjmp foundA%=\n"
" clr r16\n"
" rjmp end%=\n"
"foundD%=:\n"
" ldi r16,0x18\n"
" mov r17,%D[op]\n"
" rjmp examine%=\n"
"foundC%=:\n"
" ldi r16,0x10\n"
" mov r17,%C[op]\n"
" rjmp examine%=\n"
"foundB%=:\n"
" ldi r16,0x08\n"
" mov r17,%B[op]\n"
" rjmp examine%=\n"
"foundA%=:\n"
" ldi r16,0x00\n"
" mov r17,%A[op]\n"
"examine%=:\n"
" bst r17,7\n"
" brts bit7%=\n"
" bst r17,6\n"
" brts bit6%=\n"
" bst r17,5\n"
" brts bit5%=\n"
" bst r17,4\n"
" brts bit4%=\n"
" bst r17,3\n"
" brts bit3%=\n"
" bst r17,2\n"
" brts bit2%=\n"
" bst r17,1\n"
" brts bit1%=\n"
" subi r16,0xFF\n"
" rjmp end%=\n"
"bit7%=:\n"
" subi r16,0xF8\n"
" rjmp end%=\n"
"bit6%=:\n"
" subi r16,0xF9\n"
" rjmp end%=\n"
"bit5%=:\n"
" subi r16,0xFA\n"
" rjmp end%=\n"
"bit4%=:\n"
" subi r16,0xFB\n"
" rjmp end%=\n"
"bit3%=:\n"
" subi r16,0xFC\n"
" rjmp end%=\n"
"bit2%=:\n"
" subi r16,0xFD\n"
" rjmp end%=\n"
"bit1%=:\n"
" subi r16,0xFE\n"
"end%=:\n"
" mov %[res],r16\n"
: [res] "=r" (res)
: [op] "r" (op)
: "r16", "r17"
);
return res;
}
#endif
// Broken version. Works directly with %[res].
// This code was obtained from the above code like that:
// - remove the final mov instruction,
// - remove r16 from clobber list,
// - replace all use of r16 with %[res].
// It's only "half" broken. While the main loop below should print out the numbers 0-32.
// with this code it prints:
// 0 1 1 1 1 1 1 1 1 9 10 11 12 13 14 15 16 17 18 19 20 21 22 23 24 25 26 27 28 29 30 31 32
static uint8_t highest_bit (uint32_t op)
{
uint8_t res;
__asm__(
" cpse %D[op],__zero_reg__\n"
" rjmp foundD%=\n"
" cpse %C[op],__zero_reg__\n"
" rjmp foundC%=\n"
" cpse %B[op],__zero_reg__\n"
" rjmp foundB%=\n"
" cpse %A[op],__zero_reg__\n"
" rjmp foundA%=\n"
" clr %[res]\n"
" rjmp end%=\n"
"foundD%=:\n"
" ldi %[res],0x18\n"
" mov r17,%D[op]\n"
" rjmp examine%=\n"
"foundC%=:\n"
" ldi %[res],0x10\n"
" mov r17,%C[op]\n"
" rjmp examine%=\n"
"foundB%=:\n"
" ldi %[res],0x08\n"
" mov r17,%B[op]\n"
" rjmp examine%=\n"
"foundA%=:\n"
" ldi %[res],0x00\n"
" mov r17,%A[op]\n"
"examine%=:\n"
" bst r17,7\n"
" brts bit7%=\n"
" bst r17,6\n"
" brts bit6%=\n"
" bst r17,5\n"
" brts bit5%=\n"
" bst r17,4\n"
" brts bit4%=\n"
" bst r17,3\n"
" brts bit3%=\n"
" bst r17,2\n"
" brts bit2%=\n"
" bst r17,1\n"
" brts bit1%=\n"
" subi %[res],0xFF\n"
" rjmp end%=\n"
"bit7%=:\n"
" subi %[res],0xF8\n"
" rjmp end%=\n"
"bit6%=:\n"
" subi %[res],0xF9\n"
" rjmp end%=\n"
"bit5%=:\n"
" subi %[res],0xFA\n"
" rjmp end%=\n"
"bit4%=:\n"
" subi %[res],0xFB\n"
" rjmp end%=\n"
"bit3%=:\n"
" subi %[res],0xFC\n"
" rjmp end%=\n"
"bit2%=:\n"
" subi %[res],0xFD\n"
" rjmp end%=\n"
"bit1%=:\n"
" subi %[res],0xFE\n"
"end%=:\n"
: [res] "=r" (res)
: [op] "r" (op)
: "r17"
);
return res;
}
int main ()
{
uart_init();
stdout = &uart_output;
for (int i = 0; i < 32; i++) {
printf(" %d", highest_bit
((uint32_t)1 << i
)); }
}
I2luY2x1ZGUgPGF2ci9pby5oPgojaW5jbHVkZSA8c3RkaW8uaD4KCiNpbmNsdWRlIDx1dGlsL3NldGJhdWQuaD4KCnZvaWQgdWFydF9pbml0ICh2b2lkKQp7CiAgICBVQlJSMEggPSBVQlJSSF9WQUxVRTsKICAgIFVCUlIwTCA9IFVCUlJMX1ZBTFVFOwojaWYgVVNFXzJYCiAgICBVQ1NSMEEgfD0gX0JWKFUyWDApOwojZWxzZQogICAgVUNTUjBBICY9IH4oX0JWKFUyWDApKTsKI2VuZGlmCiAgICBVQ1NSMEMgPSBfQlYoVUNTWjAxKSB8IF9CVihVQ1NaMDApOyAvKiA4LWJpdCBkYXRhICovIAogICAgVUNTUjBCID0gX0JWKFJYRU4wKSB8IF9CVihUWEVOMCk7ICAgLyogRW5hYmxlIFJYIGFuZCBUWCAqLwp9CgppbnQgdWFydF9wdXRjaGFyIChjaGFyIGMsIEZJTEUgKnN0cmVhbSkKewogICAgbG9vcF91bnRpbF9iaXRfaXNfc2V0KFVDU1IwQSwgVURSRTApOyAvKiBXYWl0IHVudGlsIGRhdGEgcmVnaXN0ZXIgZW1wdHkuICovCiAgICBVRFIwID0gYzsKICAgIHJldHVybiAwOwp9CgpGSUxFIHVhcnRfb3V0cHV0ID0gRkRFVl9TRVRVUF9TVFJFQU0odWFydF9wdXRjaGFyLCBOVUxMLCBfRkRFVl9TRVRVUF9XUklURSk7CgovLyBSZXR1cm5zIHRoZSBpbmRleCBvZiB0aGUgaGlnaGVzdCAxLWJpdCBpbiBhbiBpbnRlZ2VyLCBzdGFydGluZyB3aXRoIDEsCi8vIG9yIHplcm8gaWYgdGhlIG9wZXJhbmQgaXMgemVyby4KLy8gV29ya2luZyB2ZXJzaW9uLiBVc2VzIHIxNiBmb3IgdGVtcG9yYXJ5IGFuZCBtb3YncyB0aGUgcmVzdWx0IGludG8gJVtyZXNdLgojaWYgMApzdGF0aWMgdWludDhfdCBoaWdoZXN0X2JpdCAodWludDMyX3Qgb3ApCnsKICAgIHVpbnQ4X3QgcmVzOwogICAgX19hc21fXygKICAgICAgICAiICAgIGNwc2UgJURbb3BdLF9femVyb19yZWdfX1xuIgogICAgICAgICIgICAgcmptcCBmb3VuZEQlPVxuIgogICAgICAgICIgICAgY3BzZSAlQ1tvcF0sX196ZXJvX3JlZ19fXG4iCiAgICAgICAgIiAgICByam1wIGZvdW5kQyU9XG4iCiAgICAgICAgIiAgICBjcHNlICVCW29wXSxfX3plcm9fcmVnX19cbiIKICAgICAgICAiICAgIHJqbXAgZm91bmRCJT1cbiIKICAgICAgICAiICAgIGNwc2UgJUFbb3BdLF9femVyb19yZWdfX1xuIgogICAgICAgICIgICAgcmptcCBmb3VuZEElPVxuIgogICAgICAgICIgICAgY2xyIHIxNlxuIgogICAgICAgICIgICAgcmptcCBlbmQlPVxuIgogICAgICAgICJmb3VuZEQlPTpcbiIKICAgICAgICAiICAgIGxkaSByMTYsMHgxOFxuIgogICAgICAgICIgICAgbW92IHIxNywlRFtvcF1cbiIKICAgICAgICAiICAgIHJqbXAgZXhhbWluZSU9XG4iCiAgICAgICAgImZvdW5kQyU9OlxuIgogICAgICAgICIgICAgbGRpIHIxNiwweDEwXG4iCiAgICAgICAgIiAgICBtb3YgcjE3LCVDW29wXVxuIgogICAgICAgICIgICAgcmptcCBleGFtaW5lJT1cbiIKICAgICAgICAiZm91bmRCJT06XG4iCiAgICAgICAgIiAgICBsZGkgcjE2LDB4MDhcbiIKICAgICAgICAiICAgIG1vdiByMTcsJUJbb3BdXG4iCiAgICAgICAgIiAgICByam1wIGV4YW1pbmUlPVxuIgogICAgICAgICJmb3VuZEElPTpcbiIKICAgICAgICAiICAgIGxkaSByMTYsMHgwMFxuIgogICAgICAgICIgICAgbW92IHIxNywlQVtvcF1cbiIKICAgICAgICAiZXhhbWluZSU9OlxuIgogICAgICAgICIgICAgYnN0IHIxNyw3XG4iCiAgICAgICAgIiAgICBicnRzIGJpdDclPVxuIgogICAgICAgICIgICAgYnN0IHIxNyw2XG4iCiAgICAgICAgIiAgICBicnRzIGJpdDYlPVxuIgogICAgICAgICIgICAgYnN0IHIxNyw1XG4iCiAgICAgICAgIiAgICBicnRzIGJpdDUlPVxuIgogICAgICAgICIgICAgYnN0IHIxNyw0XG4iCiAgICAgICAgIiAgICBicnRzIGJpdDQlPVxuIgogICAgICAgICIgICAgYnN0IHIxNywzXG4iCiAgICAgICAgIiAgICBicnRzIGJpdDMlPVxuIgogICAgICAgICIgICAgYnN0IHIxNywyXG4iCiAgICAgICAgIiAgICBicnRzIGJpdDIlPVxuIgogICAgICAgICIgICAgYnN0IHIxNywxXG4iCiAgICAgICAgIiAgICBicnRzIGJpdDElPVxuIgogICAgICAgICIgICAgc3ViaSByMTYsMHhGRlxuIgogICAgICAgICIgICAgcmptcCBlbmQlPVxuIgogICAgICAgICJiaXQ3JT06XG4iCiAgICAgICAgIiAgICBzdWJpIHIxNiwweEY4XG4iCiAgICAgICAgIiAgICByam1wIGVuZCU9XG4iCiAgICAgICAgImJpdDYlPTpcbiIKICAgICAgICAiICAgIHN1YmkgcjE2LDB4RjlcbiIKICAgICAgICAiICAgIHJqbXAgZW5kJT1cbiIKICAgICAgICAiYml0NSU9OlxuIgogICAgICAgICIgICAgc3ViaSByMTYsMHhGQVxuIgogICAgICAgICIgICAgcmptcCBlbmQlPVxuIgogICAgICAgICJiaXQ0JT06XG4iCiAgICAgICAgIiAgICBzdWJpIHIxNiwweEZCXG4iCiAgICAgICAgIiAgICByam1wIGVuZCU9XG4iCiAgICAgICAgImJpdDMlPTpcbiIKICAgICAgICAiICAgIHN1YmkgcjE2LDB4RkNcbiIKICAgICAgICAiICAgIHJqbXAgZW5kJT1cbiIKICAgICAgICAiYml0MiU9OlxuIgogICAgICAgICIgICAgc3ViaSByMTYsMHhGRFxuIgogICAgICAgICIgICAgcmptcCBlbmQlPVxuIgogICAgICAgICJiaXQxJT06XG4iCiAgICAgICAgIiAgICBzdWJpIHIxNiwweEZFXG4iCiAgICAgICAgImVuZCU9OlxuIgogICAgICAgICIgICAgbW92ICVbcmVzXSxyMTZcbiIKICAgICAgICA6IFtyZXNdICI9ciIgKHJlcykKICAgICAgICA6IFtvcF0gInIiIChvcCkKICAgICAgICA6ICJyMTYiLCAicjE3IgogICAgKTsKICAgIHJldHVybiByZXM7Cn0KI2VuZGlmCgovLyBCcm9rZW4gdmVyc2lvbi4gV29ya3MgZGlyZWN0bHkgd2l0aCAlW3Jlc10uCi8vIFRoaXMgY29kZSB3YXMgb2J0YWluZWQgZnJvbSB0aGUgYWJvdmUgY29kZSBsaWtlIHRoYXQ6Ci8vIC0gcmVtb3ZlIHRoZSBmaW5hbCBtb3YgaW5zdHJ1Y3Rpb24sCi8vIC0gcmVtb3ZlIHIxNiBmcm9tIGNsb2JiZXIgbGlzdCwKLy8gLSByZXBsYWNlIGFsbCB1c2Ugb2YgcjE2IHdpdGggJVtyZXNdLgovLyBJdCdzIG9ubHkgImhhbGYiIGJyb2tlbi4gV2hpbGUgdGhlIG1haW4gbG9vcCBiZWxvdyBzaG91bGQgcHJpbnQgb3V0IHRoZSBudW1iZXJzIDAtMzIuCi8vIHdpdGggdGhpcyBjb2RlIGl0IHByaW50czoKLy8gICAwIDEgMSAxIDEgMSAxIDEgMSA5IDEwIDExIDEyIDEzIDE0IDE1IDE2IDE3IDE4IDE5IDIwIDIxIDIyIDIzIDI0IDI1IDI2IDI3IDI4IDI5IDMwIDMxIDMyCnN0YXRpYyB1aW50OF90IGhpZ2hlc3RfYml0ICh1aW50MzJfdCBvcCkKewogICAgdWludDhfdCByZXM7CiAgICBfX2FzbV9fKAogICAgICAgICIgICAgY3BzZSAlRFtvcF0sX196ZXJvX3JlZ19fXG4iCiAgICAgICAgIiAgICByam1wIGZvdW5kRCU9XG4iCiAgICAgICAgIiAgICBjcHNlICVDW29wXSxfX3plcm9fcmVnX19cbiIKICAgICAgICAiICAgIHJqbXAgZm91bmRDJT1cbiIKICAgICAgICAiICAgIGNwc2UgJUJbb3BdLF9femVyb19yZWdfX1xuIgogICAgICAgICIgICAgcmptcCBmb3VuZEIlPVxuIgogICAgICAgICIgICAgY3BzZSAlQVtvcF0sX196ZXJvX3JlZ19fXG4iCiAgICAgICAgIiAgICByam1wIGZvdW5kQSU9XG4iCiAgICAgICAgIiAgICBjbHIgJVtyZXNdXG4iCiAgICAgICAgIiAgICByam1wIGVuZCU9XG4iCiAgICAgICAgImZvdW5kRCU9OlxuIgogICAgICAgICIgICAgbGRpICVbcmVzXSwweDE4XG4iCiAgICAgICAgIiAgICBtb3YgcjE3LCVEW29wXVxuIgogICAgICAgICIgICAgcmptcCBleGFtaW5lJT1cbiIKICAgICAgICAiZm91bmRDJT06XG4iCiAgICAgICAgIiAgICBsZGkgJVtyZXNdLDB4MTBcbiIKICAgICAgICAiICAgIG1vdiByMTcsJUNbb3BdXG4iCiAgICAgICAgIiAgICByam1wIGV4YW1pbmUlPVxuIgogICAgICAgICJmb3VuZEIlPTpcbiIKICAgICAgICAiICAgIGxkaSAlW3Jlc10sMHgwOFxuIgogICAgICAgICIgICAgbW92IHIxNywlQltvcF1cbiIKICAgICAgICAiICAgIHJqbXAgZXhhbWluZSU9XG4iCiAgICAgICAgImZvdW5kQSU9OlxuIgogICAgICAgICIgICAgbGRpICVbcmVzXSwweDAwXG4iCiAgICAgICAgIiAgICBtb3YgcjE3LCVBW29wXVxuIgogICAgICAgICJleGFtaW5lJT06XG4iCiAgICAgICAgIiAgICBic3QgcjE3LDdcbiIKICAgICAgICAiICAgIGJydHMgYml0NyU9XG4iCiAgICAgICAgIiAgICBic3QgcjE3LDZcbiIKICAgICAgICAiICAgIGJydHMgYml0NiU9XG4iCiAgICAgICAgIiAgICBic3QgcjE3LDVcbiIKICAgICAgICAiICAgIGJydHMgYml0NSU9XG4iCiAgICAgICAgIiAgICBic3QgcjE3LDRcbiIKICAgICAgICAiICAgIGJydHMgYml0NCU9XG4iCiAgICAgICAgIiAgICBic3QgcjE3LDNcbiIKICAgICAgICAiICAgIGJydHMgYml0MyU9XG4iCiAgICAgICAgIiAgICBic3QgcjE3LDJcbiIKICAgICAgICAiICAgIGJydHMgYml0MiU9XG4iCiAgICAgICAgIiAgICBic3QgcjE3LDFcbiIKICAgICAgICAiICAgIGJydHMgYml0MSU9XG4iCiAgICAgICAgIiAgICBzdWJpICVbcmVzXSwweEZGXG4iCiAgICAgICAgIiAgICByam1wIGVuZCU9XG4iCiAgICAgICAgImJpdDclPTpcbiIKICAgICAgICAiICAgIHN1YmkgJVtyZXNdLDB4RjhcbiIKICAgICAgICAiICAgIHJqbXAgZW5kJT1cbiIKICAgICAgICAiYml0NiU9OlxuIgogICAgICAgICIgICAgc3ViaSAlW3Jlc10sMHhGOVxuIgogICAgICAgICIgICAgcmptcCBlbmQlPVxuIgogICAgICAgICJiaXQ1JT06XG4iCiAgICAgICAgIiAgICBzdWJpICVbcmVzXSwweEZBXG4iCiAgICAgICAgIiAgICByam1wIGVuZCU9XG4iCiAgICAgICAgImJpdDQlPTpcbiIKICAgICAgICAiICAgIHN1YmkgJVtyZXNdLDB4RkJcbiIKICAgICAgICAiICAgIHJqbXAgZW5kJT1cbiIKICAgICAgICAiYml0MyU9OlxuIgogICAgICAgICIgICAgc3ViaSAlW3Jlc10sMHhGQ1xuIgogICAgICAgICIgICAgcmptcCBlbmQlPVxuIgogICAgICAgICJiaXQyJT06XG4iCiAgICAgICAgIiAgICBzdWJpICVbcmVzXSwweEZEXG4iCiAgICAgICAgIiAgICByam1wIGVuZCU9XG4iCiAgICAgICAgImJpdDElPTpcbiIKICAgICAgICAiICAgIHN1YmkgJVtyZXNdLDB4RkVcbiIKICAgICAgICAiZW5kJT06XG4iCiAgICAgICAgOiBbcmVzXSAiPXIiIChyZXMpCiAgICAgICAgOiBbb3BdICJyIiAob3ApCiAgICAgICAgOiAicjE3IgogICAgKTsKICAgIHJldHVybiByZXM7Cn0KCmludCBtYWluICgpCnsKICAgIHVhcnRfaW5pdCgpOwogICAgc3Rkb3V0ID0gJnVhcnRfb3V0cHV0OwogICAgCiAgICBwcmludGYoIiVkIiwgaGlnaGVzdF9iaXQoMCkpOwogICAgZm9yIChpbnQgaSA9IDA7IGkgPCAzMjsgaSsrKSB7CiAgICAgICAgcHJpbnRmKCIgJWQiLCBoaWdoZXN0X2JpdCgodWludDMyX3QpMSA8PCBpKSk7CiAgICB9CiAgICBwcmludGYoIlxuIik7Cn0K