#include <avr/interrupt.h>
#include <avr/io.h>
#include <stdint.h>
enum states {
GREEN_NORTH,
BLINKING_NORTH_ON_1,
BLINKING_NORTH_OFF_1,
BLINKING_NORTH_ON_2,
BLINKING_NORTH_OFF_2,
BLINKING_NORTH_ON_3,
BLINKING_NORTH_OFF_3,
YELLOW_NORTH,
GREEN_SOUTH,
BLINKING_SOUTH_ON_1,
BLINKING_SOUTH_OFF_1,
BLINKING_SOUTH_ON_2,
BLINKING_SOUTH_OFF_2,
BLINKING_SOUTH_ON_3,
BLINKING_SOUTH_OFF_3,
YELLOW_SOUTH,
GREEN_EAST,
BLINKING_EAST_ON_1,
BLINKING_EAST_OFF_1,
BLINKING_EAST_ON_2,
BLINKING_EAST_OFF_2,
BLINKING_EAST_ON_3,
BLINKING_EAST_OFF_3,
YELLOW_EAST,
GREEN_WEST,
BLINKING_WEST_ON_1,
BLINKING_WEST_OFF_1,
BLINKING_WEST_ON_2,
BLINKING_WEST_OFF_2,
BLINKING_WEST_ON_3,
BLINKING_WEST_OFF_3,
YELLOW_WEST,
STATES_N
} current_state;
static const uint32_t ticks = (1.0 / ((1.0 / ((double) F_CPU * 1024.0)) * 256.0)) + 0.5;
static uint32_t t = 0;
static uint32_t overflows = 0;
static void set_north_green_led(void) {
PORTA |= _BV(PA0);
}
static void set_north_yellow_led(void) {
PORTA |= _BV(PA1);
}
static void set_north_red_led(void) {
PORTA |= _BV(PA2);
}
static void reset_north_green_led(void) {
PORTA &= ~(_BV(PA0));
}
static void reset_north_yellow_led(void) {
PORTA &= ~(_BV(PA1));
}
static void reset_north_red_led(void) {
PORTA &= ~(_BV(PA2));
}
static void set_south_green_led(void) {
PORTA |= _BV(PA3);
}
static void set_south_yellow_led(void) {
PORTA |= _BV(PA4);
}
static void set_south_red_led(void) {
PORTA |= _BV(PA5);
}
static void reset_south_green_led(void) {
PORTA &= ~(_BV(PA3));
}
static void reset_south_yellow_led(void) {
PORTA &= ~(_BV(PA4));
}
static void reset_south_red_led(void) {
PORTA &= ~(_BV(PA5));
}
static void set_east_green_led(void) {
PORTA |= _BV(PA6);
}
static void set_east_yellow_led(void) {
PORTA |= _BV(PA7);
}
static void set_east_red_led(void) {
PORTB |= _BV(PB0);
}
static void reset_east_green_led(void) {
PORTA &= ~(_BV(PA6));
}
static void reset_east_yellow_led(void) {
PORTA &= ~(_BV(PA7));
}
static void reset_east_red_led(void) {
PORTB &= ~(_BV(PB0));
}
static void set_west_green_led(void) {
PORTB |= _BV(PB1);
}
static void set_west_yellow_led(void) {
PORTB |= _BV(PB2);
}
static void set_west_red_led(void) {
PORTB |= _BV(PB3);
}
static void reset_west_green_led(void) {
PORTB &= ~(_BV(PB1));
}
static void reset_west_yellow_led(void) {
PORTB &= ~(_BV(PB2));
}
static void reset_west_red_led(void) {
PORTB &= ~(_BV(PB3));
}
static void set_north_off(void) {
reset_north_green_led();
reset_north_yellow_led();
reset_north_red_led();
}
static void set_north_green(void) {
set_north_green_led();
reset_north_yellow_led();
reset_north_red_led();
}
static void set_north_yellow(void) {
reset_north_green_led();
set_north_yellow_led();
reset_north_red_led();
}
static void set_north_red(void) {
reset_north_green_led();
reset_north_yellow_led();
set_north_red_led();
}
static void set_south_off(void) {
reset_south_green_led();
reset_south_yellow_led();
reset_south_red_led();
}
static void set_south_green(void) {
set_south_green_led();
reset_south_yellow_led();
reset_south_red_led();
}
static void set_south_yellow(void) {
reset_south_green_led();
set_south_yellow_led();
reset_south_red_led();
}
static void set_south_red(void) {
reset_south_green_led();
reset_south_yellow_led();
set_south_red_led();
}
static void set_east_off(void) {
reset_east_green_led();
reset_east_yellow_led();
reset_east_red_led();
}
static void set_east_green(void) {
set_east_green_led();
reset_east_yellow_led();
reset_east_red_led();
}
static void set_east_yellow(void) {
reset_east_green_led();
set_east_yellow_led();
reset_east_red_led();
}
static void set_east_red(void) {
reset_east_green_led();
reset_east_yellow_led();
set_east_red_led();
}
static void set_west_off(void) {
reset_west_green_led();
reset_west_yellow_led();
reset_west_red_led();
}
static void set_west_green(void) {
set_west_green_led();
reset_west_yellow_led();
reset_west_red_led();
}
static void set_west_yellow(void) {
reset_west_green_led();
set_west_yellow_led();
reset_west_red_led();
}
static void set_west_red(void) {
reset_west_green_led();
reset_west_yellow_led();
set_west_red_led();
}
static void begin_pulse(uint32_t seconds) {
t = seconds;
TCCR0 = _BV(CS02) | _BV(CS00);
TCNT0 = 0;
}
static void end_pulse(void) {
TCCR0 = 0;
TCNT0 = 0;
t = 0;
}
static void next_state(void) {
current_state = (current_state != STATES_N ? current_state + 1 : 0);
}
ISR(TIMER0_OVF_vect) {
if (++overflows >= ticks * t) {
switch (current_state) {
case GREEN_NORTH:
begin_pulse(1);
break;
case BLINKING_NORTH_ON_1:
begin_pulse(1);
break;
case BLINKING_NORTH_OFF_1:
begin_pulse(1);
break;
case BLINKING_NORTH_ON_2:
begin_pulse(1);
break;
case BLINKING_NORTH_OFF_2:
begin_pulse(1);
break;
case BLINKING_NORTH_ON_3:
begin_pulse(1);
break;
case BLINKING_NORTH_OFF_3:
begin_pulse(5);
break;
case YELLOW_NORTH:
begin_pulse(5);
break;
case GREEN_SOUTH:
begin_pulse(1);
break;
case BLINKING_SOUTH_ON_1:
begin_pulse(1);
break;
case BLINKING_SOUTH_OFF_1:
begin_pulse(1);
break;
case BLINKING_SOUTH_ON_2:
begin_pulse(1);
break;
case BLINKING_SOUTH_OFF_2:
begin_pulse(1);
break;
case BLINKING_SOUTH_ON_3:
begin_pulse(1);
break;
case BLINKING_SOUTH_OFF_3:
begin_pulse(5);
break;
case YELLOW_SOUTH:
begin_pulse(5);
break;
case GREEN_EAST:
begin_pulse(1);
break;
case BLINKING_EAST_ON_1:
begin_pulse(1);
break;
case BLINKING_EAST_OFF_1:
begin_pulse(1);
break;
case BLINKING_EAST_ON_2:
begin_pulse(1);
break;
case BLINKING_EAST_OFF_2:
begin_pulse(1);
break;
case BLINKING_EAST_ON_3:
begin_pulse(1);
break;
case BLINKING_EAST_OFF_3:
begin_pulse(5);
break;
case YELLOW_EAST:
begin_pulse(5);
break;
case GREEN_WEST:
begin_pulse(1);
break;
case BLINKING_WEST_ON_1:
begin_pulse(1);
break;
case BLINKING_WEST_OFF_1:
begin_pulse(1);
break;
case BLINKING_WEST_ON_2:
begin_pulse(1);
break;
case BLINKING_WEST_OFF_2:
begin_pulse(1);
break;
case BLINKING_WEST_ON_3:
begin_pulse(1);
break;
case BLINKING_WEST_OFF_3:
begin_pulse(5);
break;
case YELLOW_WEST:
begin_pulse(5);
break;
}
overflows = 0;
next_state();
}
}
static void initialize_io_registers(void) {
PORTA = 0xff;
PORTB |= (_BV(PB0) | _BV(PB1) | _BV(PB2) | _BV(PB3));
}
static void initialize_interrupt_registers(void) {
TIMSK |= (_BV(TOIE0));
sei();
}
static void initialize_start_state(void) {
current_state = GREEN_NORTH;
begin_pulse(5);
}
int main(void) {
initialize_io_registers();
initialize_interrupt_registers();
initialize_start_state();
for (;;) {
switch (current_state) {
case GREEN_NORTH:
set_north_green();
set_south_red();
set_east_red();
set_west_red();
break;
case BLINKING_NORTH_ON_1:
set_north_green();
set_south_red();
set_east_red();
set_west_red();
break;
case BLINKING_NORTH_OFF_1:
set_north_off();
set_south_red();
set_east_red();
set_west_red();
break;
case BLINKING_NORTH_ON_2:
set_north_green();
set_south_red();
set_east_red();
set_west_red();
break;
case BLINKING_NORTH_OFF_2:
set_north_off();
set_south_red();
set_east_red();
set_west_red();
break;
case BLINKING_NORTH_ON_3:
set_north_green();
set_south_red();
set_east_red();
set_west_red();
break;
case BLINKING_NORTH_OFF_3:
set_north_off();
set_south_red();
set_east_red();
set_west_red();
break;
case YELLOW_NORTH:
set_north_yellow();
set_south_red();
set_east_red();
set_west_red();
break;
case GREEN_SOUTH:
set_north_red();
set_south_green();
set_east_red();
set_west_red();
break;
case BLINKING_SOUTH_ON_1:
set_north_red();
set_south_green();
set_east_red();
set_west_red();
break;
case BLINKING_SOUTH_OFF_1:
set_north_red();
set_south_off();
set_east_red();
set_west_red();
break;
case BLINKING_SOUTH_ON_2:
set_north_red();
set_south_green();
set_east_red();
set_west_red();
break;
case BLINKING_SOUTH_OFF_2:
set_north_red();
set_south_off();
set_east_red();
set_west_red();
break;
case BLINKING_SOUTH_ON_3:
set_north_red();
set_south_green();
set_east_red();
set_west_red();
break;
case BLINKING_SOUTH_OFF_3:
set_north_red();
set_south_off();
set_east_red();
set_west_red();
break;
case YELLOW_SOUTH:
set_north_red();
set_south_yellow();
set_east_red();
set_west_red();
break;
case GREEN_EAST:
set_north_red();
set_south_red();
set_east_green();
set_west_red();
break;
case BLINKING_EAST_ON_1:
set_north_red();
set_south_red();
set_east_green();
set_west_red();
break;
case BLINKING_EAST_OFF_1:
set_north_red();
set_south_red();
set_east_off();
set_west_red();
break;
case BLINKING_EAST_ON_2:
set_north_red();
set_south_red();
set_east_green();
set_west_red();
break;
case BLINKING_EAST_OFF_2:
set_north_red();
set_south_red();
set_east_off();
set_west_red();
break;
case BLINKING_EAST_ON_3:
set_north_red();
set_south_red();
set_east_green();
set_west_red();
break;
case BLINKING_EAST_OFF_3:
set_north_red();
set_south_red();
set_east_off();
set_west_red();
break;
case YELLOW_EAST:
set_north_red();
set_south_red();
set_east_yellow();
set_west_red();
break;
case GREEN_WEST:
set_north_red();
set_south_red();
set_east_red();
set_west_green();
break;
case BLINKING_WEST_ON_1:
set_north_red();
set_south_red();
set_east_red();
set_west_green();
break;
case BLINKING_WEST_OFF_1:
set_north_red();
set_south_red();
set_east_red();
set_west_off();
break;
case BLINKING_WEST_ON_2:
set_north_red();
set_south_red();
set_east_red();
set_west_green();
break;
case BLINKING_WEST_OFF_2:
set_north_red();
set_south_red();
set_east_red();
set_west_off();
break;
case BLINKING_WEST_ON_3:
set_north_red();
set_south_red();
set_east_red();
set_west_green();
break;
case BLINKING_WEST_OFF_3:
set_north_red();
set_south_red();
set_east_red();
set_west_off();
break;
case YELLOW_WEST:
set_north_red();
set_south_red();
set_east_red();
set_west_yellow();
break;
}
}
return 0;
}
I2luY2x1ZGUgPGF2ci9pbnRlcnJ1cHQuaD4KI2luY2x1ZGUgPGF2ci9pby5oPgojaW5jbHVkZSA8c3RkaW50Lmg+CgplbnVtIHN0YXRlcyB7CiAgR1JFRU5fTk9SVEgsCiAgQkxJTktJTkdfTk9SVEhfT05fMSwKICBCTElOS0lOR19OT1JUSF9PRkZfMSwKICBCTElOS0lOR19OT1JUSF9PTl8yLAogIEJMSU5LSU5HX05PUlRIX09GRl8yLAogIEJMSU5LSU5HX05PUlRIX09OXzMsCiAgQkxJTktJTkdfTk9SVEhfT0ZGXzMsCiAgWUVMTE9XX05PUlRILAogIEdSRUVOX1NPVVRILAogIEJMSU5LSU5HX1NPVVRIX09OXzEsCiAgQkxJTktJTkdfU09VVEhfT0ZGXzEsCiAgQkxJTktJTkdfU09VVEhfT05fMiwKICBCTElOS0lOR19TT1VUSF9PRkZfMiwKICBCTElOS0lOR19TT1VUSF9PTl8zLAogIEJMSU5LSU5HX1NPVVRIX09GRl8zLAogIFlFTExPV19TT1VUSCwKICBHUkVFTl9FQVNULAogIEJMSU5LSU5HX0VBU1RfT05fMSwKICBCTElOS0lOR19FQVNUX09GRl8xLAogIEJMSU5LSU5HX0VBU1RfT05fMiwKICBCTElOS0lOR19FQVNUX09GRl8yLAogIEJMSU5LSU5HX0VBU1RfT05fMywKICBCTElOS0lOR19FQVNUX09GRl8zLAogIFlFTExPV19FQVNULAogIEdSRUVOX1dFU1QsCiAgQkxJTktJTkdfV0VTVF9PTl8xLAogIEJMSU5LSU5HX1dFU1RfT0ZGXzEsCiAgQkxJTktJTkdfV0VTVF9PTl8yLAogIEJMSU5LSU5HX1dFU1RfT0ZGXzIsCiAgQkxJTktJTkdfV0VTVF9PTl8zLAogIEJMSU5LSU5HX1dFU1RfT0ZGXzMsCiAgWUVMTE9XX1dFU1QsCiAgU1RBVEVTX04KfSBjdXJyZW50X3N0YXRlOwoKc3RhdGljIGNvbnN0IHVpbnQzMl90IHRpY2tzID0gKDEuMCAvICgoMS4wIC8gKChkb3VibGUpIEZfQ1BVICogMTAyNC4wKSkgKiAyNTYuMCkpICsgMC41OwpzdGF0aWMgdWludDMyX3QgdCA9IDA7CnN0YXRpYyB1aW50MzJfdCBvdmVyZmxvd3MgPSAwOwoKc3RhdGljIHZvaWQgc2V0X25vcnRoX2dyZWVuX2xlZCh2b2lkKSB7CiAgUE9SVEEgfD0gX0JWKFBBMCk7Cn0KCnN0YXRpYyB2b2lkIHNldF9ub3J0aF95ZWxsb3dfbGVkKHZvaWQpIHsKICBQT1JUQSB8PSBfQlYoUEExKTsKfQoKc3RhdGljIHZvaWQgc2V0X25vcnRoX3JlZF9sZWQodm9pZCkgewogIFBPUlRBIHw9IF9CVihQQTIpOwp9CgpzdGF0aWMgdm9pZCByZXNldF9ub3J0aF9ncmVlbl9sZWQodm9pZCkgewogIFBPUlRBICY9IH4oX0JWKFBBMCkpOwp9CgpzdGF0aWMgdm9pZCByZXNldF9ub3J0aF95ZWxsb3dfbGVkKHZvaWQpIHsKICBQT1JUQSAmPSB+KF9CVihQQTEpKTsKfQoKc3RhdGljIHZvaWQgcmVzZXRfbm9ydGhfcmVkX2xlZCh2b2lkKSB7CiAgUE9SVEEgJj0gfihfQlYoUEEyKSk7Cn0KCnN0YXRpYyB2b2lkIHNldF9zb3V0aF9ncmVlbl9sZWQodm9pZCkgewogIFBPUlRBIHw9IF9CVihQQTMpOwp9CgpzdGF0aWMgdm9pZCBzZXRfc291dGhfeWVsbG93X2xlZCh2b2lkKSB7CiAgUE9SVEEgfD0gX0JWKFBBNCk7Cn0KCnN0YXRpYyB2b2lkIHNldF9zb3V0aF9yZWRfbGVkKHZvaWQpIHsKICBQT1JUQSB8PSBfQlYoUEE1KTsKfQoKc3RhdGljIHZvaWQgcmVzZXRfc291dGhfZ3JlZW5fbGVkKHZvaWQpIHsKICBQT1JUQSAmPSB+KF9CVihQQTMpKTsKfQoKc3RhdGljIHZvaWQgcmVzZXRfc291dGhfeWVsbG93X2xlZCh2b2lkKSB7CiAgUE9SVEEgJj0gfihfQlYoUEE0KSk7Cn0KCnN0YXRpYyB2b2lkIHJlc2V0X3NvdXRoX3JlZF9sZWQodm9pZCkgewogIFBPUlRBICY9IH4oX0JWKFBBNSkpOwp9CgpzdGF0aWMgdm9pZCBzZXRfZWFzdF9ncmVlbl9sZWQodm9pZCkgewogIFBPUlRBIHw9IF9CVihQQTYpOwp9CgpzdGF0aWMgdm9pZCBzZXRfZWFzdF95ZWxsb3dfbGVkKHZvaWQpIHsKICBQT1JUQSB8PSBfQlYoUEE3KTsKfQoKc3RhdGljIHZvaWQgc2V0X2Vhc3RfcmVkX2xlZCh2b2lkKSB7CiAgUE9SVEIgfD0gX0JWKFBCMCk7Cn0KCnN0YXRpYyB2b2lkIHJlc2V0X2Vhc3RfZ3JlZW5fbGVkKHZvaWQpIHsKICBQT1JUQSAmPSB+KF9CVihQQTYpKTsKfQoKc3RhdGljIHZvaWQgcmVzZXRfZWFzdF95ZWxsb3dfbGVkKHZvaWQpIHsKICBQT1JUQSAmPSB+KF9CVihQQTcpKTsKfQoKc3RhdGljIHZvaWQgcmVzZXRfZWFzdF9yZWRfbGVkKHZvaWQpIHsKICBQT1JUQiAmPSB+KF9CVihQQjApKTsKfQoKc3RhdGljIHZvaWQgc2V0X3dlc3RfZ3JlZW5fbGVkKHZvaWQpIHsKICBQT1JUQiB8PSBfQlYoUEIxKTsKfQoKc3RhdGljIHZvaWQgc2V0X3dlc3RfeWVsbG93X2xlZCh2b2lkKSB7CiAgUE9SVEIgfD0gX0JWKFBCMik7Cn0KCnN0YXRpYyB2b2lkIHNldF93ZXN0X3JlZF9sZWQodm9pZCkgewogIFBPUlRCIHw9IF9CVihQQjMpOwp9CgpzdGF0aWMgdm9pZCByZXNldF93ZXN0X2dyZWVuX2xlZCh2b2lkKSB7CiAgUE9SVEIgJj0gfihfQlYoUEIxKSk7Cn0KCnN0YXRpYyB2b2lkIHJlc2V0X3dlc3RfeWVsbG93X2xlZCh2b2lkKSB7CiAgUE9SVEIgJj0gfihfQlYoUEIyKSk7Cn0KCnN0YXRpYyB2b2lkIHJlc2V0X3dlc3RfcmVkX2xlZCh2b2lkKSB7CiAgUE9SVEIgJj0gfihfQlYoUEIzKSk7Cn0KCnN0YXRpYyB2b2lkIHNldF9ub3J0aF9vZmYodm9pZCkgewogIHJlc2V0X25vcnRoX2dyZWVuX2xlZCgpOwogIHJlc2V0X25vcnRoX3llbGxvd19sZWQoKTsKICByZXNldF9ub3J0aF9yZWRfbGVkKCk7Cn0KCnN0YXRpYyB2b2lkIHNldF9ub3J0aF9ncmVlbih2b2lkKSB7CiAgc2V0X25vcnRoX2dyZWVuX2xlZCgpOwogIHJlc2V0X25vcnRoX3llbGxvd19sZWQoKTsKICByZXNldF9ub3J0aF9yZWRfbGVkKCk7Cn0KCnN0YXRpYyB2b2lkIHNldF9ub3J0aF95ZWxsb3codm9pZCkgewogIHJlc2V0X25vcnRoX2dyZWVuX2xlZCgpOwogIHNldF9ub3J0aF95ZWxsb3dfbGVkKCk7CiAgcmVzZXRfbm9ydGhfcmVkX2xlZCgpOwp9CgpzdGF0aWMgdm9pZCBzZXRfbm9ydGhfcmVkKHZvaWQpIHsKICByZXNldF9ub3J0aF9ncmVlbl9sZWQoKTsKICByZXNldF9ub3J0aF95ZWxsb3dfbGVkKCk7CiAgc2V0X25vcnRoX3JlZF9sZWQoKTsKfQoKc3RhdGljIHZvaWQgc2V0X3NvdXRoX29mZih2b2lkKSB7CiAgcmVzZXRfc291dGhfZ3JlZW5fbGVkKCk7CiAgcmVzZXRfc291dGhfeWVsbG93X2xlZCgpOwogIHJlc2V0X3NvdXRoX3JlZF9sZWQoKTsKfQoKc3RhdGljIHZvaWQgc2V0X3NvdXRoX2dyZWVuKHZvaWQpIHsKICBzZXRfc291dGhfZ3JlZW5fbGVkKCk7CiAgcmVzZXRfc291dGhfeWVsbG93X2xlZCgpOwogIHJlc2V0X3NvdXRoX3JlZF9sZWQoKTsKfQoKc3RhdGljIHZvaWQgc2V0X3NvdXRoX3llbGxvdyh2b2lkKSB7CiAgcmVzZXRfc291dGhfZ3JlZW5fbGVkKCk7CiAgc2V0X3NvdXRoX3llbGxvd19sZWQoKTsKICByZXNldF9zb3V0aF9yZWRfbGVkKCk7Cn0KCnN0YXRpYyB2b2lkIHNldF9zb3V0aF9yZWQodm9pZCkgewogIHJlc2V0X3NvdXRoX2dyZWVuX2xlZCgpOwogIHJlc2V0X3NvdXRoX3llbGxvd19sZWQoKTsKICBzZXRfc291dGhfcmVkX2xlZCgpOwp9CgpzdGF0aWMgdm9pZCBzZXRfZWFzdF9vZmYodm9pZCkgewogIHJlc2V0X2Vhc3RfZ3JlZW5fbGVkKCk7CiAgcmVzZXRfZWFzdF95ZWxsb3dfbGVkKCk7CiAgcmVzZXRfZWFzdF9yZWRfbGVkKCk7Cn0KCnN0YXRpYyB2b2lkIHNldF9lYXN0X2dyZWVuKHZvaWQpIHsKICBzZXRfZWFzdF9ncmVlbl9sZWQoKTsKICByZXNldF9lYXN0X3llbGxvd19sZWQoKTsKICByZXNldF9lYXN0X3JlZF9sZWQoKTsKfQoKc3RhdGljIHZvaWQgc2V0X2Vhc3RfeWVsbG93KHZvaWQpIHsKICByZXNldF9lYXN0X2dyZWVuX2xlZCgpOwogIHNldF9lYXN0X3llbGxvd19sZWQoKTsKICByZXNldF9lYXN0X3JlZF9sZWQoKTsKfQoKc3RhdGljIHZvaWQgc2V0X2Vhc3RfcmVkKHZvaWQpIHsKICByZXNldF9lYXN0X2dyZWVuX2xlZCgpOwogIHJlc2V0X2Vhc3RfeWVsbG93X2xlZCgpOwogIHNldF9lYXN0X3JlZF9sZWQoKTsKfQoKc3RhdGljIHZvaWQgc2V0X3dlc3Rfb2ZmKHZvaWQpIHsKICByZXNldF93ZXN0X2dyZWVuX2xlZCgpOwogIHJlc2V0X3dlc3RfeWVsbG93X2xlZCgpOwogIHJlc2V0X3dlc3RfcmVkX2xlZCgpOwp9CgpzdGF0aWMgdm9pZCBzZXRfd2VzdF9ncmVlbih2b2lkKSB7CiAgc2V0X3dlc3RfZ3JlZW5fbGVkKCk7CiAgcmVzZXRfd2VzdF95ZWxsb3dfbGVkKCk7CiAgcmVzZXRfd2VzdF9yZWRfbGVkKCk7Cn0KCnN0YXRpYyB2b2lkIHNldF93ZXN0X3llbGxvdyh2b2lkKSB7CiAgcmVzZXRfd2VzdF9ncmVlbl9sZWQoKTsKICBzZXRfd2VzdF95ZWxsb3dfbGVkKCk7CiAgcmVzZXRfd2VzdF9yZWRfbGVkKCk7Cn0KCnN0YXRpYyB2b2lkIHNldF93ZXN0X3JlZCh2b2lkKSB7CiAgcmVzZXRfd2VzdF9ncmVlbl9sZWQoKTsKICByZXNldF93ZXN0X3llbGxvd19sZWQoKTsKICBzZXRfd2VzdF9yZWRfbGVkKCk7Cn0KCnN0YXRpYyB2b2lkIGJlZ2luX3B1bHNlKHVpbnQzMl90IHNlY29uZHMpIHsKICB0ID0gc2Vjb25kczsKICBUQ0NSMCA9IF9CVihDUzAyKSB8IF9CVihDUzAwKTsKICBUQ05UMCA9IDA7Cn0KCnN0YXRpYyB2b2lkIGVuZF9wdWxzZSh2b2lkKSB7CiAgVENDUjAgPSAwOwogIFRDTlQwID0gMDsKICB0ID0gMDsKfQoKc3RhdGljIHZvaWQgbmV4dF9zdGF0ZSh2b2lkKSB7CiAgY3VycmVudF9zdGF0ZSA9IChjdXJyZW50X3N0YXRlICE9IFNUQVRFU19OID8gY3VycmVudF9zdGF0ZSArIDEgOiAwKTsKfQoKSVNSKFRJTUVSMF9PVkZfdmVjdCkgewogIGlmICgrK292ZXJmbG93cyA+PSB0aWNrcyAqIHQpIHsKICAgIHN3aXRjaCAoY3VycmVudF9zdGF0ZSkgewogICAgY2FzZSBHUkVFTl9OT1JUSDoKICAgICAgYmVnaW5fcHVsc2UoMSk7CiAgICAgIGJyZWFrOwoKICAgIGNhc2UgQkxJTktJTkdfTk9SVEhfT05fMToKICAgICAgYmVnaW5fcHVsc2UoMSk7CiAgICAgIGJyZWFrOwoKICAgIGNhc2UgQkxJTktJTkdfTk9SVEhfT0ZGXzE6CiAgICAgIGJlZ2luX3B1bHNlKDEpOwogICAgICBicmVhazsKCiAgICBjYXNlIEJMSU5LSU5HX05PUlRIX09OXzI6CiAgICAgIGJlZ2luX3B1bHNlKDEpOwogICAgICBicmVhazsKCiAgICBjYXNlIEJMSU5LSU5HX05PUlRIX09GRl8yOgogICAgICBiZWdpbl9wdWxzZSgxKTsKICAgICAgYnJlYWs7CgogICAgY2FzZSBCTElOS0lOR19OT1JUSF9PTl8zOgogICAgICBiZWdpbl9wdWxzZSgxKTsKICAgICAgYnJlYWs7CgogICAgY2FzZSBCTElOS0lOR19OT1JUSF9PRkZfMzoKICAgICAgYmVnaW5fcHVsc2UoNSk7CiAgICAgIGJyZWFrOwoKICAgIGNhc2UgWUVMTE9XX05PUlRIOgogICAgICBiZWdpbl9wdWxzZSg1KTsKICAgICAgYnJlYWs7CgogICAgY2FzZSBHUkVFTl9TT1VUSDoKICAgICAgYmVnaW5fcHVsc2UoMSk7CiAgICAgIGJyZWFrOwoKICAgIGNhc2UgQkxJTktJTkdfU09VVEhfT05fMToKICAgICAgYmVnaW5fcHVsc2UoMSk7CiAgICAgIGJyZWFrOwoKICAgIGNhc2UgQkxJTktJTkdfU09VVEhfT0ZGXzE6CiAgICAgIGJlZ2luX3B1bHNlKDEpOwogICAgICBicmVhazsKCiAgICBjYXNlIEJMSU5LSU5HX1NPVVRIX09OXzI6CiAgICAgIGJlZ2luX3B1bHNlKDEpOwogICAgICBicmVhazsKCiAgICBjYXNlIEJMSU5LSU5HX1NPVVRIX09GRl8yOgogICAgICBiZWdpbl9wdWxzZSgxKTsKICAgICAgYnJlYWs7CgogICAgY2FzZSBCTElOS0lOR19TT1VUSF9PTl8zOgogICAgICBiZWdpbl9wdWxzZSgxKTsKICAgICAgYnJlYWs7CgogICAgY2FzZSBCTElOS0lOR19TT1VUSF9PRkZfMzoKICAgICAgYmVnaW5fcHVsc2UoNSk7CiAgICAgIGJyZWFrOwoKICAgIGNhc2UgWUVMTE9XX1NPVVRIOgogICAgICBiZWdpbl9wdWxzZSg1KTsKICAgICAgYnJlYWs7CgogICAgY2FzZSBHUkVFTl9FQVNUOgogICAgICBiZWdpbl9wdWxzZSgxKTsKICAgICAgYnJlYWs7CgogICAgY2FzZSBCTElOS0lOR19FQVNUX09OXzE6CiAgICAgIGJlZ2luX3B1bHNlKDEpOwogICAgICBicmVhazsKCiAgICBjYXNlIEJMSU5LSU5HX0VBU1RfT0ZGXzE6CiAgICAgIGJlZ2luX3B1bHNlKDEpOwogICAgICBicmVhazsKCiAgICBjYXNlIEJMSU5LSU5HX0VBU1RfT05fMjoKICAgICAgYmVnaW5fcHVsc2UoMSk7CiAgICAgIGJyZWFrOwoKICAgIGNhc2UgQkxJTktJTkdfRUFTVF9PRkZfMjoKICAgICAgYmVnaW5fcHVsc2UoMSk7CiAgICAgIGJyZWFrOwoKICAgIGNhc2UgQkxJTktJTkdfRUFTVF9PTl8zOgogICAgICBiZWdpbl9wdWxzZSgxKTsKICAgICAgYnJlYWs7CgogICAgY2FzZSBCTElOS0lOR19FQVNUX09GRl8zOgogICAgICBiZWdpbl9wdWxzZSg1KTsKICAgICAgYnJlYWs7CgogICAgY2FzZSBZRUxMT1dfRUFTVDoKICAgICAgYmVnaW5fcHVsc2UoNSk7CiAgICAgIGJyZWFrOwoKICAgIGNhc2UgR1JFRU5fV0VTVDoKICAgICAgYmVnaW5fcHVsc2UoMSk7CiAgICAgIGJyZWFrOwoKICAgIGNhc2UgQkxJTktJTkdfV0VTVF9PTl8xOgogICAgICBiZWdpbl9wdWxzZSgxKTsKICAgICAgYnJlYWs7CgogICAgY2FzZSBCTElOS0lOR19XRVNUX09GRl8xOgogICAgICBiZWdpbl9wdWxzZSgxKTsKICAgICAgYnJlYWs7CgogICAgY2FzZSBCTElOS0lOR19XRVNUX09OXzI6CiAgICAgIGJlZ2luX3B1bHNlKDEpOwogICAgICBicmVhazsKCiAgICBjYXNlIEJMSU5LSU5HX1dFU1RfT0ZGXzI6CiAgICAgIGJlZ2luX3B1bHNlKDEpOwogICAgICBicmVhazsKCiAgICBjYXNlIEJMSU5LSU5HX1dFU1RfT05fMzoKICAgICAgYmVnaW5fcHVsc2UoMSk7CiAgICAgIGJyZWFrOwoKICAgIGNhc2UgQkxJTktJTkdfV0VTVF9PRkZfMzoKICAgICAgYmVnaW5fcHVsc2UoNSk7CiAgICAgIGJyZWFrOwoKICAgIGNhc2UgWUVMTE9XX1dFU1Q6CiAgICAgIGJlZ2luX3B1bHNlKDUpOwogICAgICBicmVhazsKICAgIH0KICAgIG92ZXJmbG93cyA9IDA7CiAgICBuZXh0X3N0YXRlKCk7CiAgfQp9CgpzdGF0aWMgdm9pZCBpbml0aWFsaXplX2lvX3JlZ2lzdGVycyh2b2lkKSB7CiAgUE9SVEEgPSAweGZmOwogIFBPUlRCIHw9IChfQlYoUEIwKSB8IF9CVihQQjEpIHwgX0JWKFBCMikgfCBfQlYoUEIzKSk7Cn0KCnN0YXRpYyB2b2lkIGluaXRpYWxpemVfaW50ZXJydXB0X3JlZ2lzdGVycyh2b2lkKSB7CiAgVElNU0sgfD0gKF9CVihUT0lFMCkpOwogIHNlaSgpOwp9CgpzdGF0aWMgdm9pZCBpbml0aWFsaXplX3N0YXJ0X3N0YXRlKHZvaWQpIHsKICBjdXJyZW50X3N0YXRlID0gR1JFRU5fTk9SVEg7CiAgYmVnaW5fcHVsc2UoNSk7Cn0KCmludCBtYWluKHZvaWQpIHsKICBpbml0aWFsaXplX2lvX3JlZ2lzdGVycygpOwogIGluaXRpYWxpemVfaW50ZXJydXB0X3JlZ2lzdGVycygpOwogIGluaXRpYWxpemVfc3RhcnRfc3RhdGUoKTsKICBmb3IgKDs7KSB7CiAgICBzd2l0Y2ggKGN1cnJlbnRfc3RhdGUpIHsKICAgICAgY2FzZSBHUkVFTl9OT1JUSDoKICAgICAgICBzZXRfbm9ydGhfZ3JlZW4oKTsKICAgICAgICBzZXRfc291dGhfcmVkKCk7CiAgICAgICAgc2V0X2Vhc3RfcmVkKCk7CiAgICAgICAgc2V0X3dlc3RfcmVkKCk7CiAgICAgICAgYnJlYWs7CgogICAgICBjYXNlIEJMSU5LSU5HX05PUlRIX09OXzE6CiAgICAgICAgc2V0X25vcnRoX2dyZWVuKCk7CiAgICAgICAgc2V0X3NvdXRoX3JlZCgpOwogICAgICAgIHNldF9lYXN0X3JlZCgpOwogICAgICAgIHNldF93ZXN0X3JlZCgpOwogICAgICAgIGJyZWFrOwoKICAgICAgY2FzZSBCTElOS0lOR19OT1JUSF9PRkZfMToKICAgICAgICBzZXRfbm9ydGhfb2ZmKCk7CiAgICAgICAgc2V0X3NvdXRoX3JlZCgpOwogICAgICAgIHNldF9lYXN0X3JlZCgpOwogICAgICAgIHNldF93ZXN0X3JlZCgpOwogICAgICAgIGJyZWFrOwoKICAgICAgY2FzZSBCTElOS0lOR19OT1JUSF9PTl8yOgogICAgICAgIHNldF9ub3J0aF9ncmVlbigpOwogICAgICAgIHNldF9zb3V0aF9yZWQoKTsKICAgICAgICBzZXRfZWFzdF9yZWQoKTsKICAgICAgICBzZXRfd2VzdF9yZWQoKTsKICAgICAgICBicmVhazsKCiAgICAgIGNhc2UgQkxJTktJTkdfTk9SVEhfT0ZGXzI6CiAgICAgICAgc2V0X25vcnRoX29mZigpOwogICAgICAgIHNldF9zb3V0aF9yZWQoKTsKICAgICAgICBzZXRfZWFzdF9yZWQoKTsKICAgICAgICBzZXRfd2VzdF9yZWQoKTsKICAgICAgICBicmVhazsKCiAgICAgIGNhc2UgQkxJTktJTkdfTk9SVEhfT05fMzoKICAgICAgICBzZXRfbm9ydGhfZ3JlZW4oKTsKICAgICAgICBzZXRfc291dGhfcmVkKCk7CiAgICAgICAgc2V0X2Vhc3RfcmVkKCk7CiAgICAgICAgc2V0X3dlc3RfcmVkKCk7CiAgICAgICAgYnJlYWs7CgogICAgICBjYXNlIEJMSU5LSU5HX05PUlRIX09GRl8zOgogICAgICAgIHNldF9ub3J0aF9vZmYoKTsKICAgICAgICBzZXRfc291dGhfcmVkKCk7CiAgICAgICAgc2V0X2Vhc3RfcmVkKCk7CiAgICAgICAgc2V0X3dlc3RfcmVkKCk7CiAgICAgICAgYnJlYWs7CgogICAgICBjYXNlIFlFTExPV19OT1JUSDoKICAgICAgICBzZXRfbm9ydGhfeWVsbG93KCk7CiAgICAgICAgc2V0X3NvdXRoX3JlZCgpOwogICAgICAgIHNldF9lYXN0X3JlZCgpOwogICAgICAgIHNldF93ZXN0X3JlZCgpOwogICAgICAgIGJyZWFrOwoKICAgICAgY2FzZSBHUkVFTl9TT1VUSDoKICAgICAgICBzZXRfbm9ydGhfcmVkKCk7CiAgICAgICAgc2V0X3NvdXRoX2dyZWVuKCk7CiAgICAgICAgc2V0X2Vhc3RfcmVkKCk7CiAgICAgICAgc2V0X3dlc3RfcmVkKCk7CiAgICAgICAgYnJlYWs7CgogICAgICBjYXNlIEJMSU5LSU5HX1NPVVRIX09OXzE6CiAgICAgICAgc2V0X25vcnRoX3JlZCgpOwogICAgICAgIHNldF9zb3V0aF9ncmVlbigpOwogICAgICAgIHNldF9lYXN0X3JlZCgpOwogICAgICAgIHNldF93ZXN0X3JlZCgpOwogICAgICAgIGJyZWFrOwoKICAgICAgY2FzZSBCTElOS0lOR19TT1VUSF9PRkZfMToKICAgICAgICBzZXRfbm9ydGhfcmVkKCk7CiAgICAgICAgc2V0X3NvdXRoX29mZigpOwogICAgICAgIHNldF9lYXN0X3JlZCgpOwogICAgICAgIHNldF93ZXN0X3JlZCgpOwogICAgICAgIGJyZWFrOwoKICAgICAgY2FzZSBCTElOS0lOR19TT1VUSF9PTl8yOgogICAgICAgIHNldF9ub3J0aF9yZWQoKTsKICAgICAgICBzZXRfc291dGhfZ3JlZW4oKTsKICAgICAgICBzZXRfZWFzdF9yZWQoKTsKICAgICAgICBzZXRfd2VzdF9yZWQoKTsKICAgICAgICBicmVhazsKCiAgICAgIGNhc2UgQkxJTktJTkdfU09VVEhfT0ZGXzI6CiAgICAgICAgc2V0X25vcnRoX3JlZCgpOwogICAgICAgIHNldF9zb3V0aF9vZmYoKTsKICAgICAgICBzZXRfZWFzdF9yZWQoKTsKICAgICAgICBzZXRfd2VzdF9yZWQoKTsKICAgICAgICBicmVhazsKCiAgICAgIGNhc2UgQkxJTktJTkdfU09VVEhfT05fMzoKICAgICAgICBzZXRfbm9ydGhfcmVkKCk7CiAgICAgICAgc2V0X3NvdXRoX2dyZWVuKCk7CiAgICAgICAgc2V0X2Vhc3RfcmVkKCk7CiAgICAgICAgc2V0X3dlc3RfcmVkKCk7CiAgICAgICAgYnJlYWs7CgogICAgICBjYXNlIEJMSU5LSU5HX1NPVVRIX09GRl8zOgogICAgICAgIHNldF9ub3J0aF9yZWQoKTsKICAgICAgICBzZXRfc291dGhfb2ZmKCk7CiAgICAgICAgc2V0X2Vhc3RfcmVkKCk7CiAgICAgICAgc2V0X3dlc3RfcmVkKCk7CiAgICAgICAgYnJlYWs7CgogICAgICBjYXNlIFlFTExPV19TT1VUSDoKICAgICAgICBzZXRfbm9ydGhfcmVkKCk7CiAgICAgICAgc2V0X3NvdXRoX3llbGxvdygpOwogICAgICAgIHNldF9lYXN0X3JlZCgpOwogICAgICAgIHNldF93ZXN0X3JlZCgpOwogICAgICAgIGJyZWFrOwoKICAgICAgY2FzZSBHUkVFTl9FQVNUOgogICAgICAgIHNldF9ub3J0aF9yZWQoKTsKICAgICAgICBzZXRfc291dGhfcmVkKCk7CiAgICAgICAgc2V0X2Vhc3RfZ3JlZW4oKTsKICAgICAgICBzZXRfd2VzdF9yZWQoKTsKICAgICAgICBicmVhazsKCiAgICAgIGNhc2UgQkxJTktJTkdfRUFTVF9PTl8xOgogICAgICAgIHNldF9ub3J0aF9yZWQoKTsKICAgICAgICBzZXRfc291dGhfcmVkKCk7CiAgICAgICAgc2V0X2Vhc3RfZ3JlZW4oKTsKICAgICAgICBzZXRfd2VzdF9yZWQoKTsKICAgICAgICBicmVhazsKCiAgICAgIGNhc2UgQkxJTktJTkdfRUFTVF9PRkZfMToKICAgICAgICBzZXRfbm9ydGhfcmVkKCk7CiAgICAgICAgc2V0X3NvdXRoX3JlZCgpOwogICAgICAgIHNldF9lYXN0X29mZigpOwogICAgICAgIHNldF93ZXN0X3JlZCgpOwogICAgICAgIGJyZWFrOwoKICAgICAgY2FzZSBCTElOS0lOR19FQVNUX09OXzI6CiAgICAgICAgc2V0X25vcnRoX3JlZCgpOwogICAgICAgIHNldF9zb3V0aF9yZWQoKTsKICAgICAgICBzZXRfZWFzdF9ncmVlbigpOwogICAgICAgIHNldF93ZXN0X3JlZCgpOwogICAgICAgIGJyZWFrOwoKICAgICAgY2FzZSBCTElOS0lOR19FQVNUX09GRl8yOgogICAgICAgIHNldF9ub3J0aF9yZWQoKTsKICAgICAgICBzZXRfc291dGhfcmVkKCk7CiAgICAgICAgc2V0X2Vhc3Rfb2ZmKCk7CiAgICAgICAgc2V0X3dlc3RfcmVkKCk7CiAgICAgICAgYnJlYWs7CgogICAgICBjYXNlIEJMSU5LSU5HX0VBU1RfT05fMzoKICAgICAgICBzZXRfbm9ydGhfcmVkKCk7CiAgICAgICAgc2V0X3NvdXRoX3JlZCgpOwogICAgICAgIHNldF9lYXN0X2dyZWVuKCk7CiAgICAgICAgc2V0X3dlc3RfcmVkKCk7CiAgICAgICAgYnJlYWs7CgogICAgICBjYXNlIEJMSU5LSU5HX0VBU1RfT0ZGXzM6CiAgICAgICAgc2V0X25vcnRoX3JlZCgpOwogICAgICAgIHNldF9zb3V0aF9yZWQoKTsKICAgICAgICBzZXRfZWFzdF9vZmYoKTsKICAgICAgICBzZXRfd2VzdF9yZWQoKTsKICAgICAgICBicmVhazsKCiAgICAgIGNhc2UgWUVMTE9XX0VBU1Q6CiAgICAgICAgc2V0X25vcnRoX3JlZCgpOwogICAgICAgIHNldF9zb3V0aF9yZWQoKTsKICAgICAgICBzZXRfZWFzdF95ZWxsb3coKTsKICAgICAgICBzZXRfd2VzdF9yZWQoKTsKICAgICAgICBicmVhazsKCiAgICAgIGNhc2UgR1JFRU5fV0VTVDoKICAgICAgICBzZXRfbm9ydGhfcmVkKCk7CiAgICAgICAgc2V0X3NvdXRoX3JlZCgpOwogICAgICAgIHNldF9lYXN0X3JlZCgpOwogICAgICAgIHNldF93ZXN0X2dyZWVuKCk7CiAgICAgICAgYnJlYWs7CgogICAgICBjYXNlIEJMSU5LSU5HX1dFU1RfT05fMToKICAgICAgICBzZXRfbm9ydGhfcmVkKCk7CiAgICAgICAgc2V0X3NvdXRoX3JlZCgpOwogICAgICAgIHNldF9lYXN0X3JlZCgpOwogICAgICAgIHNldF93ZXN0X2dyZWVuKCk7CiAgICAgICAgYnJlYWs7CgogICAgICBjYXNlIEJMSU5LSU5HX1dFU1RfT0ZGXzE6CiAgICAgICAgc2V0X25vcnRoX3JlZCgpOwogICAgICAgIHNldF9zb3V0aF9yZWQoKTsKICAgICAgICBzZXRfZWFzdF9yZWQoKTsKICAgICAgICBzZXRfd2VzdF9vZmYoKTsKICAgICAgICBicmVhazsKCiAgICAgIGNhc2UgQkxJTktJTkdfV0VTVF9PTl8yOgogICAgICAgIHNldF9ub3J0aF9yZWQoKTsKICAgICAgICBzZXRfc291dGhfcmVkKCk7CiAgICAgICAgc2V0X2Vhc3RfcmVkKCk7CiAgICAgICAgc2V0X3dlc3RfZ3JlZW4oKTsKICAgICAgICBicmVhazsKCiAgICAgIGNhc2UgQkxJTktJTkdfV0VTVF9PRkZfMjoKICAgICAgICBzZXRfbm9ydGhfcmVkKCk7CiAgICAgICAgc2V0X3NvdXRoX3JlZCgpOwogICAgICAgIHNldF9lYXN0X3JlZCgpOwogICAgICAgIHNldF93ZXN0X29mZigpOwogICAgICAgIGJyZWFrOwoKICAgICAgY2FzZSBCTElOS0lOR19XRVNUX09OXzM6CiAgICAgICAgc2V0X25vcnRoX3JlZCgpOwogICAgICAgIHNldF9zb3V0aF9yZWQoKTsKICAgICAgICBzZXRfZWFzdF9yZWQoKTsKICAgICAgICBzZXRfd2VzdF9ncmVlbigpOwogICAgICAgIGJyZWFrOwoKICAgICAgY2FzZSBCTElOS0lOR19XRVNUX09GRl8zOgogICAgICAgIHNldF9ub3J0aF9yZWQoKTsKICAgICAgICBzZXRfc291dGhfcmVkKCk7CiAgICAgICAgc2V0X2Vhc3RfcmVkKCk7CiAgICAgICAgc2V0X3dlc3Rfb2ZmKCk7CiAgICAgICAgYnJlYWs7CgogICAgICBjYXNlIFlFTExPV19XRVNUOgogICAgICAgIHNldF9ub3J0aF9yZWQoKTsKICAgICAgICBzZXRfc291dGhfcmVkKCk7CiAgICAgICAgc2V0X2Vhc3RfcmVkKCk7CiAgICAgICAgc2V0X3dlc3RfeWVsbG93KCk7CiAgICAgICAgYnJlYWs7CiAgICB9CiAgfQogIHJldHVybiAwOwp9Cg==