X-Git-Url: https://git.ucc.asn.au/?a=blobdiff_plain;f=ROM2%2Fmotors.c;h=e7cb6b50db87f90bf36d531d081b34f9e76e484f;hb=c1fd53d73bce8779c822e3ed74de94f40714f9ca;hp=4bb216b273158616e047e2669a4ed9b1f1f2f223;hpb=c99662693a4d79f65d406473647debbd33ec521e;p=uccvend-snackrom.git diff --git a/ROM2/motors.c b/ROM2/motors.c index 4bb216b..e7cb6b5 100644 --- a/ROM2/motors.c +++ b/ROM2/motors.c @@ -1,50 +1,155 @@ #include "motors.h" #include "vend.h" +const u8 motor_lookup[80] = +{ 1,12,23,34,46,57,68,79, + 11,22,33,44,56,67,78,89, + 21,32,43,54,66,77,88,99, + 31,42,53,64,76,87,98, + 9,41,52,63,74,86,97, + 8,19,51,62,73,84,96, + 7,18,29,61,72,83,94, + 6,17,28,39,71,82,93, + 4,16,27,38,49,81,92, + 3,14,26,37,48,59,91, + 2,13,24,36,47,58,69, +}; + +void motor_shift_send(u8 data) { + u8 i; + /* load it in, MSB first */ + for (i = 0; i < 8; i++) { + if (data & 0x80) + bset_misc_output(A3800_MOTOR_DATA); + else + bclr_misc_output(A3800_MOTOR_DATA); + + delay(1); + + /* clock pulse */ + bset((void*)&_io_ports[M6811_PORTA], PORTA_MOTOR_CLOCK); + delay(1); + bclr((void*)&_io_ports[M6811_PORTA], PORTA_MOTOR_CLOCK); + delay(1); + + data = data << 1; + } +} + void motor_on(u8 slot) { - /* from jump34 */ + u8 row, col; + row = slot%10; + col = slot/10; + if (row >= 5) row--; + + /* loads up the shift register with the right bits */ + bclr_misc_output(A3800_MOTOR_COL8_ENABLE|A3800_MOTOR_COL9_ENABLE); + switch (col) { + case 8: + bset_misc_output(A3800_MOTOR_COL8_ENABLE); + motor_shift_send(0); + break; + case 9: + bset_misc_output(A3800_MOTOR_COL9_ENABLE); + motor_shift_send(0); + break; + default: /* < 8 */ + motor_shift_send(1 << col); /* cols from 0..7 */ + bclr((void*)&_io_ports[M6811_PORTA], PORTA_MOTOR_COL_DISABLE); + } + + motor_shift_send(1 << (row-1)); /* rows from 1..8 here */ + + bclr((void*)&_io_ports[M6811_PORTA], PORTA_MOTOR_CLOCK); + bclr_changer_output(A3000_MOTOR_ROW_DISABLE); } void motors_off() { - bset_changer_output(A3000_MOTOR_ROW_ENABLE); /* XXX active low? */ + bset_changer_output(A3000_MOTOR_ROW_DISABLE); delay(10); /* XXX cf motors_off */ bset((void*)&_io_ports[M6811_PORTA], PORTA_MOTOR_COL_DISABLE); bclr_misc_output(A3800_MOTOR_COL8_ENABLE | A3800_MOTOR_COL9_ENABLE); } bool motor_here(u8 slot) { - int i, c = 0; - motor_on(slot); + u8 i, c = 0; for (i=0; i < 8; i++) { - if (_io_ports[M6811_PORTE] & PORTE_MOTOR_OVERVOLTAGE) { + motor_on(slot); + delay(5); + if ((_io_ports[M6811_PORTE] & PORTE_MOTOR_OVERVOLTAGE) == 0) { c++; - if (c == 0xff) { + if (c == 3) { motors_off(); return 1; - } else - continue; + } } + motors_off(); } - motors_off(); return 0; } bool is_motor(u8 slot) { - /* FIXME */ - return 1; + /* FIXME - does more need to be done? */ + return motor_here(slot); } -u8 dispense_motor(u8 slot) { - if (!is_motor(slot)) { - return MOTOR_NOSLOT; +bool start_motor(u8 slot) { + u16 i; + u8 r = slot%10; + if (r >= 5) r--; + r = 1 << (r-1); + motor_on(slot); + delay(100); + for (i = 0; i < 1000; i++) { + if ((home_sensors & r) != 0) return 1; + delay(1); + } + /* it never left */ + motors_off(); + return 0; +} + +bool back_home(u8 slot) { + u8 i, r = slot%10; + if (r >= 5) r--; + r = 1 << (r-1); + + for (i = 0; i < 5; i++) { + if ((home_sensors & r) == 0) return 1; + delay(1); } - motor_on(slot); - /* FIXME */ - return MOTOR_SUCCESS; + /* it never arrived */ + return 0; +} + +#define is_overcurrent() ((_io_ports[M6811_PORTE] & PORTE_MOTOR_NOT_OVERCURRENT)==0) +bool motor_overcurrent() { + u8 good_passes = 0, t; + for (t = 0; t < 8; t++) { + delay(1); + if (is_overcurrent()) continue; + t = 0; + good_passes++; + if (good_passes == 5) return 0; + } + return 1; } -void scan_motors() { - /* FIXME */ +u8 dispense_motor(u8 slot) { + if (!is_motor(slot)) return MOTOR_NOSLOT; + if (!start_motor(slot)) return MOTOR_HOME_FAIL; + + while (1) { + if (motor_overcurrent()) { + motors_off(); + return MOTOR_CURRENT_FAIL; + } + /* something should call motor_here? */ + if (back_home(slot)) { + motors_off(); + return MOTOR_SUCCESS; + } + } }