1 (display "Loading flash iface client...")
4 (use-modules (srfi srfi-1) (ice-9 format) (ice-9 rw))
6 (define STX-s (string #\stx))
7 (define RS-s (string #\rs))
8 (define ETX-s (string #\etx))
10 (define STX-i (char->integer #\stx))
11 (define RS-i (char->integer #\rs))
12 (define ETX-i (char->integer #\etx))
14 (define STX-u8v (make-u8vector 1 STX-i))
15 (define RS-u8v (make-u8vector 1 RS-i))
16 (define ETX-u8v (make-u8vector 1 ETX-i))
18 (define SENDBUF-SIZE 2048)
20 (define (list-ref-with-default lst n def)
21 (if (< n (length lst))
26 (define (string->u8vector s)
27 (let ((result (make-u8vector (string-length s))))
28 (array-map! result char->integer s)
32 (define (u8vector->string v)
33 (let ((result (make-string (u8vector-length v))))
34 (array-map! result integer->char v)
38 (define (integer->u8vector i)
42 (define (char->u8vector c)
43 (integer->u8vector (char->integer c))
46 ;(define (uniform-vector-append! dst . srcs)
47 ; (define dst-len (uniform-vector-length dst))
48 ; (define (do-uniform-vector-append!)
51 ; (while (and (not (null? rest)) (< new-index dst-len))
52 ; (let ((current-item (car rest))
53 ; (current-length (uniform-vector-length (car rest))))
54 ; (uniform-vector-move! current-item 0 (min current-length (- dst-len new-index)) dst new-index)
55 ; (set! new-index (+ new-index current-length))
57 ; (set! rest (cdr rest))
61 ; (do-uniform-vector-append!)
64 (define (uniform-vector-append! dst . srcs)
65 (define dst-len (uniform-vector-length dst))
66 (define (do-uniform-vector-append! new-index rest)
67 (if (and (not (null? rest)) (< new-index dst-len))
68 (let ((current-item (car rest))
69 (current-length (uniform-vector-length (car rest))))
70 (uniform-vector-move! current-item 0 (min current-length (- dst-len new-index)) dst new-index)
71 (do-uniform-vector-append! (+ new-index current-length) (cdr rest)))
74 (do-uniform-vector-append! 0 srcs)
77 (define (u8vector-append . srcs)
78 (let ((res (make-u8vector (fold (lambda (v1 sum) (+ (uniform-vector-length v1) sum)) 0 srcs))))
79 (apply uniform-vector-append! (cons res srcs))
84 (define (parse-command cmd)
85 (define cmd-len (u8vector-length cmd))
86 (define (find-rs-idx idx)
88 (if (equal? RS-i (u8vector-ref cmd idx))
90 (find-rs-idx (1+ idx)))
93 (define (sub-vector v s cnt)
94 (make-shared-array v (lambda (i) (cons (+ s i) '())) cnt)
97 (if (and (equal? (u8vector-ref cmd 0) STX-i) (equal? (u8vector-ref cmd (1- cmd-len)) ETX-i))
98 (let ((rs-idx (find-rs-idx 0)))
99 (if (equal? rs-idx #f)
100 (cons (u8vector->string (sub-vector cmd 1 (- cmd-len 2))) '())
101 (cons (u8vector->string (sub-vector cmd 1 (1- rs-idx))) (sub-vector cmd (1+ rs-idx) (- cmd-len (1+ rs-idx) 1)))))
102 (throw 'protocol-error "invalid phone answer"))
105 (define (create-command cmd . args)
106 (let ((par (list-ref-with-default args 0 #f)))
107 (u8vector-append STX-u8v (string->u8vector cmd)
110 (u8vector-append RS-u8v par)
118 (define (checksum lst)
119 (modulo (fold (lambda (c sum) (+ sum c)) 0 lst)
122 (define (checksum-u8vector v)
123 (checksum (u8vector->list v))
126 (define (checksum-string s)
127 (checksum (map char->integer (string->list s)))
130 (define (addr-with-checksum addr)
131 (let ((str-addr (format #f "~:@(~8,'0X~)" addr)))
132 (format #f "~:@(~A~2,'0X~)" str-addr (checksum-string str-addr))
136 (define (create-addr-command addr)
137 (create-command "ADDR" (string->u8vector (addr-with-checksum addr)))
140 (define (create-jump-command addr)
141 (create-command "JUMP" (string->u8vector (addr-with-checksum addr)))
144 (define (create-bin-command block size)
145 (create-command "BIN" (u8vector-append
146 (list->u8vector (map (lambda (fun) (fun size 256)) (list quotient remainder)))
148 (integer->u8vector (checksum-u8vector block))
153 (define (send-recv-command iface cmd)
155 (write-flash-iface iface cmd)
156 (read-flash-iface iface)
160 (define (send-block iface block size addr)
162 (send-recv-command iface (create-addr-command addr))
163 (send-recv-command iface (create-bin-command (make-shared-array block list size) size))
168 (define (send-data-from-port iface addr)
169 (define (do-send-data-from-port addr buf)
170 (let ((ret (uniform-vector-read! buf)))
171 (if (or (equal? ret 0) (equal? ret #f))
174 (send-block iface buf ret addr)
175 (do-send-data-from-port (+ addr ret) buf)
180 (- (do-send-data-from-port addr (make-u8vector SENDBUF-SIZE)) addr)
183 (define (send-loader-from-port iface addr jaddr)
185 (send-data-from-port iface addr)
186 (send-recv-command iface (create-jump-command jaddr))
190 (define (send-loader-from-file iface fname addr jaddr)
191 (with-input-from-file fname (lambda () (send-loader-from-port iface addr jaddr)))