Browse Source

Make the serial communication work

Aaron Fischer ago%!(EXTRA string=1 year %s)
parent
commit
ad792a9dcc
1 changed files with 55 additions and 26 deletions
  1. 55 26
      agent.go

+ 55 - 26
agent.go View File

@@ -1,36 +1,44 @@
1 1
 package main
2 2
 
3
-// Create a new virtual serial device:
4
-// socat PTY,link=/dev/ttyS10 PTY,link=/dev/ttyS11
5
-
6 3
 import (
7 4
 	"log"
8 5
 	"os"
9 6
 	"path"
7
+	"errors"
10 8
 
11 9
 	"github.com/fsnotify/fsnotify"
12
-	"github.com/tarm/serial"
13 10
 	"github.com/mkideal/cli"
11
+	"github.com/tarm/serial"
14 12
 )
15 13
 
16
-// TODO: Make the error code optional (as a parameter)
17
-func stop() {
14
+func stop(exitCode int) {
18 15
 	log.Println("Have a nice day.")
19
-	os.Exit(0)
16
+	os.Exit(exitCode)
20 17
 }
21 18
 
22
-func waitAndExecuteCommandsFromDevice(device string) {
23
-	config := &serial.Config{Name: device, Baud: 115200}
24
-	serial, err := serial.OpenPort(config)
19
+type message struct {
20
+	msgType byte
21
+	data []byte
22
+}
25 23
 
26
-	if err != nil {
27
-		log.Fatal(err)
24
+const (
25
+	MSG_TYPE_ANSWER_OK = 0x01
26
+	MSG_TYPE_ANSWER_NOOK = 0x02
27
+	MSG_TYPE_AGENTID = 0x03
28
+	MSG_TYPE_CONFIG = 0x04
29
+)
30
+
31
+func decodeByteString(bytes []byte, num int) (msg message, err error) {
32
+	if bytes[0] == 0x3c && bytes[1] == 0x3e &&
33
+		bytes[num-1] == 0x0A && bytes[num-2] == 0x0D {
34
+		return message{msgType: bytes[2], data: bytes[3:num-2]}, nil
28 35
 	}
29 36
 
30
-	log.Printf("Open the connection to the n3rdpad over %s", device)
37
+	return message{msgType: 0x00, data: make([]byte, 1)}, errors.New("Can't decode the byte array.")
38
+}
31 39
 
32
-	// Read from serial
33
-	buffer := make([]byte, 128)
40
+func waitAndExecuteCommandsFromDevice(serial *serial.Port) {
41
+	buffer := make([]byte, 40)
34 42
 	for {
35 43
 		num, err := serial.Read(buffer)
36 44
 
@@ -38,12 +46,21 @@ func waitAndExecuteCommandsFromDevice(device string) {
38 46
 			log.Fatal(err)
39 47
 		}
40 48
 
41
-		// TODO: Do something with the incomind commands
42
-		log.Printf("%q", buffer[:num])
49
+		input, err := decodeByteString(buffer, num)
50
+		if err != nil {
51
+			log.Fatal(err)
52
+		} else {
53
+			switch (input.msgType) {
54
+			case MSG_TYPE_AGENTID:
55
+				log.Printf("Key pressed: %d", input.data[0])
56
+			default:
57
+				log.Fatal("Can't recognize the message type.")
58
+			}
59
+		}
43 60
 	}
44 61
 }
45 62
 
46
-func watchForConfigChanges(configFile string) {
63
+func watchForConfigChanges(configFile string, serial *serial.Port) {
47 64
 	watcher, err := fsnotify.NewWatcher()
48 65
 	if err != nil {
49 66
 		log.Fatal(err)
@@ -72,7 +89,7 @@ func watchForConfigChanges(configFile string) {
72 89
 					}
73 90
 				}
74 91
 
75
-				// Some editors have a feature calles "swap save" (like vim), which
92
+				// Some editors have a feature called "swap save" (like vim), which
76 93
 				// will trigger a simple WRITE event, instead it wil trigger RENAME
77 94
 				// -> CHMOD -> REMOVE in that order. So we lost track of the file.
78 95
 				// To prevent this, we add the file again, if it exist after a
@@ -82,13 +99,13 @@ func watchForConfigChanges(configFile string) {
82 99
 						watcher.Add(event.Name)
83 100
 					} else {
84 101
 						log.Fatal("Lost the configuration file. We stop now.")
85
-						stop()
102
+						stop(1)
86 103
 					}
87 104
 				}
88 105
 			case err := <-watcher.Errors:
89 106
 				log.Println("We have the following problem with the configuration file: ", err)
90 107
 				log.Println("Try the fix this problem by yourself and restart the agent.")
91
-				stop()
108
+				stop(2)
92 109
 			}
93 110
 		}
94 111
 	}()
@@ -103,7 +120,7 @@ func watchForConfigChanges(configFile string) {
103 120
 type argT struct {
104 121
 	cli.Helper
105 122
 	ConfigFile string `cli:"c,config" usage:"specify a keymap config file"`
106
-	Device string `cli:"d,device" usage:"specify the serial port, the n3rdpad is hooked to"`
123
+	Device     string `cli:"d,device" usage:"specify the serial port, the n3rdpad is hooked to"`
107 124
 }
108 125
 
109 126
 func main() {
@@ -117,16 +134,28 @@ func main() {
117 134
 		}
118 135
 		if args.Device == "" {
119 136
 			log.Fatal("You need to specify the serial device with the --device parameter.")
120
-			stop();
137
+			stop(3)
121 138
 		}
122 139
 
123 140
 		if !args.Help {
124 141
 			// Start up the application
125 142
 			log.Println("Using the configuration file", configFile)
126
-			go watchForConfigChanges(configFile)
127
-			waitAndExecuteCommandsFromDevice(args.Device)
128 143
 
129
-			stop()
144
+			// Open the serial connection
145
+			config := &serial.Config{Name: args.Device, Baud: 115200}
146
+			serial, err := serial.OpenPort(config)
147
+
148
+			if err != nil {
149
+				log.Fatal(err)
150
+				return nil
151
+			}
152
+
153
+			log.Printf("Open the connection to the n3rdpad over %s", args.Device)
154
+
155
+			go watchForConfigChanges(configFile, serial)
156
+			waitAndExecuteCommandsFromDevice(serial)
157
+
158
+			stop(0)
130 159
 		}
131 160
 
132 161
 		return nil