Rearrange, comment.

This commit is contained in:
Phil Hagelberg 2019-07-01 22:27:33 -07:00
parent 6ded72a729
commit 5b0d2c2a41
2 changed files with 46 additions and 26 deletions

View file

@ -6,23 +6,14 @@
(define columns (list 0 1 2 3 4 5 6 7 8 9 10))
(define column-pins (vector 6 5 9 8 7 4 10 19 18 12 11))
(define max-keys 6)
(define max-keys 6) ; a single USB frame can only send 6 keycodes plus modifiers
(define (init)
(for-each-vector output row-pins)
(for-each-vector high row-pins)
(for-each-vector input column-pins)
(for-each-vector high column-pins) ; activate pullup resistors
(call-c-func "usb_init")
(pause 200))
;;; matrix
(define (offset-for row col)
(+ col (* row (length columns))))
(define (usb-send modifiers key1 key2 key3 key4 key5 key6)
(call-c-func "usb_send" modifiers key1 key2 key3 key4 key5 key6))
(define (scan-key keys-pressed key-count row col)
;; pullup resistors mean a closed circuit is low rather than high
(if (low? (vector-ref column-pins col))
@ -36,7 +27,8 @@
(define (scan-column keys-pressed key-count row columns-left)
(if (= (length columns-left) 0)
key-count
(let ((key-count (scan-key keys-pressed key-count row (car columns-left))))
(let ((key-count (scan-key keys-pressed key-count
row (car columns-left))))
(scan-column keys-pressed key-count row (cdr columns-left)))))
(define (activate-row row)
@ -51,18 +43,19 @@
(car rows-left) columns)))
(scan-matrix keys-pressed key-count (cdr rows-left)))))
(define (layout-lookup key-position)
(vector-ref layout key-position))
;;; layout
(define (keycode-for keys-pressed key-count keycodes)
(let ((code (vector-ref layout (vector-ref keys-pressed key-count))))
;; (printf "keycode ~s ~s~n" code key-count)
(define (keycode-for keys-pressed which-key keycodes)
(let ((code (vector-ref layout (vector-ref keys-pressed which-key))))
;; (printf "keycode ~s ~s~n" code which-key)
(if (modifier? code)
(begin (vector-set! keycodes 0 (+ (vector-ref keycodes 0)
(unmodify code)))
#f)
code)))
;; translate key numbers into specific USB keycodes
(define (keycodes-for keys-pressed key-count keycodes)
(if (= 0 key-count)
(vector->list keycodes)
@ -72,13 +65,30 @@
#f)
(keycodes-for keys-pressed (- key-count 1) keycodes))))
;;; showtime
(define (init)
(for-each-vector output row-pins)
(for-each-vector high row-pins)
(for-each-vector input column-pins)
(for-each-vector high column-pins) ; activate pullup resistors
(call-c-func "usb_init")
(pause 200))
(define (usb-send modifiers key1 key2 key3 key4 key5 key6)
(call-c-func "usb_send" modifiers key1 key2 key3 key4 key5 key6))
(define (loop)
(free! (let ((keys-pressed (vector 0 0 0 0 0 0 0)))
;; scanning the matrix tells us only which physical keys were
;; pressed and how many; it doesn't tell us which keycodes to
;; send yet.
(let ((key-count (scan-matrix keys-pressed 1 rows)))
(apply usb-send (keycodes-for keys-pressed (- key-count 1)
(vector 0 0 0 0 0 0 0))))))
(loop))
;;; showtime!
(init)
(loop)

View file

@ -1,24 +1,29 @@
#lang racket
;; this file simulates the hardware necessary to test the keyboard firmware,
;; because doing actual development on an atmega32u4 is nightmarishly tedious.
(define pins (make-vector 20))
(define keys (make-vector 44 #f))
(define output void)
(define output void) ; don't bother to simulate pin modes
(define input void)
(define pause void)
(define (high pin) (vector-set! pins pin #t))
(define (low pin) (vector-set! pins pin #f))
;; microscheme has this as a separate form but it's just for
(define (for-each-vector f v) (for ([x v]) (f x)))
(define last-usb-frame #f)
(define last-usb-frame #f) ; save this off so we can test it
(define (call-c-func f-name . args)
;; (printf "FFI ~s~n" args)
(set! last-usb-frame args))
(define (active-row)
;; hypothetically we could have multiple active rows but we just assume one
(for/first ([pin row-pins]
[row (range (length rows))]
#:when (not (vector-ref pins pin)))
@ -48,24 +53,29 @@
(define test-data (make-test-data))
(define failures 0)
(define failures '())
(define (fail expected actual)
(set! failures (add1 failures))
(printf "Expected ~s, got ~s~n" expected actual))
(printf "F")
(set! failures
(cons (format "Expected ~s, got ~s~n" expected actual) failures)))
(define (finish)
(printf (string-join failures "~n" #:before-first "~n" #:after-last "~n"))
(exit (if (empty? failures) 0 1)))
;; we can perform our checks here and make changes to the pin state.
(define-syntax free!
(syntax-rules ()
[(free! body) (if (empty? test-data)
(exit (if (= 0 failures) 0 1))
(finish)
(let ([test-case (car test-data)])
(for ([i (vector-length keys)])
(vector-set! keys i
(and (member i (car test-case)) #t)))
body
(if (equal? (cdr test-case) last-usb-frame)
(printf ".~n")
(printf ".")
(fail (cdr test-case) last-usb-frame))
(set! test-data (cdr test-data))))]))