blob: f9bc31a883cb039643a3ef16727e4143a93405f5 (
plain)
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
75
76
77
78
79
80
81
82
83
84
85
86
87
88
89
90
91
92
93
94
95
96
97
98
|
#lang racket/base
(require (only-in racket/bool false?)
"../3rdparty/bzlib/parseq/main.ss")
(define-logger ebus2)
(define ebus-const-syn #xaa) ;; SYN
(define ebus-const-escape #xa9) ;; Escape-Sequence Start
(define ebus-const-ackok #x00) ;; ACK
(define ebus-const-broadcastaddr #xfe) ;; Broadcast Address
(struct ebus-body-broadcast (crc) #:transparent)
(struct ebus-body-mastermaster (crc) #:transparent)
(struct ebus-body-masterslave
(crc payloadSlaveLength payloadSlave crcSlave)
#:transparent)
(struct ebus-paket
(source destination primaryCommand secondaryCommand payloadLength payload body)
#:transparent)
;; single, maybe escaped, payload data byte
(define ebus-payload
(choice (seq escape-seq <- ebus-const-escape
escape-code <- (byte-in (list 0 1))
(return (cond
((= escape-code 0) ebus-const-escape)
((= escape-code 1) bytes ebus-const-syn))))
any-byte
))
(define parse-ebus-broadcast
(token (seq crc <- any-byte
syn <- ebus-const-syn
(return (ebus-body-broadcast crc)))))
(define parse-ebus-mastermaster
(token (seq crc <- any-byte
ack <- ebus-const-ackok ;; ACK des Empfängers
syn <- ebus-const-syn ;; SYN des Senders
(return (ebus-body-mastermaster crc)))))
(define parse-ebus-masterslave
(token (seq crc <- any-byte
ack <- ebus-const-ackok ;; ACK des Empfängers
payloadSlaveLength <- any-byte
payloadSlave <- (repeat ebus-payload payloadSlaveLength payloadSlaveLength)
crcSlave <- any-byte
ackSlave <- ebus-const-ackok ;; ACK des Senders
synSlave <- ebus-const-syn ;; SYN des Senders
(return (ebus-body-masterslave crc payloadSlaveLength payloadSlave crcSlave)))))
(define parse-ebus-paket
(token (seq source <- any-byte
destination <- any-byte
primaryCommand <- any-byte
secondaryCommand <- any-byte
payloadLength <- any-byte
payload <- (repeat ebus-payload payloadLength payloadLength)
body <- (cond ((= destination ebus-const-broadcastaddr) parse-ebus-broadcast)
(else (choice parse-ebus-mastermaster
parse-ebus-masterslave)))
(return (ebus-paket source
destination
primaryCommand
secondaryCommand
payloadLength
payload
body)))))
(define ebus-sync (tokens syncs <- (seq (repeat (string->bytes/latin-1 "\xaa")))
(return (length syncs))))
;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;
(define (read-ebus input-port)
(define syn ((make-reader ebus-sync #:sof? #f #:eof? #f) input-port))
(define paket ((make-reader parse-ebus-paket #:sof? #f #:eof? #f) input-port))
(cond ((not (false? syn)) (log-ebus2-debug "dropped ~a x SYN (~a)" syn ebus-const-syn)))
(cond ((not (false? paket)) paket)
((eof-object? (peek-byte input-port)) eof)
(else
;; skip one byte
(let ([byte (read-byte input-port)])
(log-ebus2-debug "drop ~s 0x~x" byte byte))
(read-ebus input-port))))
(provide
;; Read Layer Ebus-Paket `ebus-paket`
read-ebus
;; Expose datastructures
(struct-out ebus-paket)
(struct-out ebus-body-broadcast)
(struct-out ebus-body-mastermaster)
(struct-out ebus-body-masterslave))
|