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
|
package main
import (
"encoding/binary"
"encoding/hex"
"flag"
"log"
"strconv"
"time"
"pm3.dev/cvend"
)
var wait = flag.Duration("w", 5*time.Second, "how long to wait for a response")
var follow = flag.Bool("f", false, "don't exit after response")
func main() {
flag.Parse()
log.SetFlags(log.Lshortfile | log.Ldate | log.Ltime | log.Lmicroseconds)
log.Println("start")
wc := make(chan struct{}, 1)
cv, err := cvend.Open(cvend.Path, func(msgType byte, msgData []byte) {
switch msgType {
case 0x07:
log.Printf("Heartbeat(%s)", hex.EncodeToString(msgData))
case 0x0f:
log.Printf("Startup(%s)", hex.EncodeToString(msgData))
case 0xed:
if len(msgData) == 0 {
log.Printf("Log()")
} else {
log.Printf("Log(%d) %q", msgData[0], string(msgData[1:]))
}
case 0xbe:
if len(msgData) < 22 || len(msgData) < 22+int(msgData[21]) {
log.Printf("PICCRead(short)\n%s", hex.Dump(msgData))
} else {
_ = msgData[:11] // unknown
uid := msgData[11:18]
atqa := binary.LittleEndian.Uint16(msgData[18:20])
sak := msgData[20]
atrLen := msgData[21]
atr := msgData[22 : 22+atrLen]
_ = msgData[22+atrLen:] // unknown
log.Printf("PICCRead(uid %s atqa 0x%04x sak %02x atr %s)\n%s", hex.EncodeToString(uid), atqa, sak, hex.EncodeToString(atr), hex.Dump(msgData))
}
case 0xd1:
log.Printf("EMVTransactionSuccessUnk\n%s", hex.Dump(msgData))
default:
log.Printf("ipp %02x\n%s", msgType, hex.Dump(msgData))
}
select {
case wc <- struct{}{}:
default:
}
})
if err != nil {
panic(err)
}
defer cv.Close()
for i := 0; i < flag.NArg(); i += 2 {
var msgType byte
var msgData []byte
if n, err := strconv.ParseUint(flag.Arg(i), 0, 8); err != nil {
panic(err)
} else {
msgType = byte(n)
}
if bs, err := hex.DecodeString(flag.Arg(i + 1)); err != nil {
panic(err)
} else {
msgData = bs
}
if err := cv.SendIPP(msgType, msgData); err != nil {
panic(err)
}
if *wait > 0 {
select {
case <-wc:
case <-time.After(*wait):
}
}
}
if *follow || flag.NArg() == 0 {
select {}
}
}
|