-
Notifications
You must be signed in to change notification settings - Fork 0
Commit
This commit does not belong to any branch on this repository, and may belong to a fork outside of the repository.
- Loading branch information
dazhou
committed
Jan 3, 2019
1 parent
574b253
commit 0fd9e90
Showing
5 changed files
with
363 additions
and
0 deletions.
There are no files selected for viewing
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
Original file line number | Diff line number | Diff line change |
---|---|---|
@@ -0,0 +1,34 @@ | ||
package hidlikewindows | ||
|
||
import ( | ||
"sync" | ||
|
||
"github.com/sirupsen/logrus" | ||
"github.com/tarm/serial" | ||
) | ||
|
||
type SerialDevice struct { | ||
Path string | ||
Port *serial.Port | ||
|
||
readSetup sync.Once | ||
readErr error | ||
readCh chan []byte | ||
} | ||
|
||
func OpenSerialPort(path string) (obj *SerialDevice, e error) { | ||
obj = &SerialDevice{} | ||
if path == "" { | ||
path = "/dev/ttyAMA0" | ||
} | ||
obj.Path = path | ||
Baud := 4000000 | ||
//logrus.Info("Open serial port: " + obj.Path + ".") | ||
obj.Port, e = serial.OpenPort(&serial.Config{Name: obj.Path, Baud: Baud}) | ||
if e != nil { | ||
logrus.Error("Can not open serial port with error :", e) | ||
return nil, e | ||
} | ||
logrus.WithFields(logrus.Fields{"Baud": Baud, "Port": path}).Info("Serialport ready:") | ||
return obj, nil | ||
} |
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
Original file line number | Diff line number | Diff line change |
---|---|---|
@@ -0,0 +1,147 @@ | ||
package main | ||
|
||
import ( | ||
"bufio" | ||
"hidlikewindows" | ||
"regexp" | ||
"sync" | ||
"time" | ||
|
||
evdev "github.com/gvalkov/golang-evdev" | ||
"github.com/radovskyb/watcher" | ||
"github.com/sirupsen/logrus" | ||
) | ||
|
||
type Host struct { | ||
Debug bool | ||
DevicesMap sync.Map | ||
serialDevice *hidlikewindows.SerialDevice | ||
InputEventCH chan *evdev.InputEvent | ||
} | ||
|
||
func NewHost() (obj *Host, e error) { | ||
obj = &Host{} | ||
obj.InputEventCH = make(chan *evdev.InputEvent, 10) | ||
obj.serialDevice, e = hidlikewindows.OpenSerialPort("") | ||
if e != nil { | ||
return | ||
} | ||
|
||
return obj, nil | ||
} | ||
|
||
func (obj *Host) Run() error { | ||
go obj.readserial() | ||
go obj.send2serial() | ||
|
||
w := watcher.New() | ||
defer w.Close() | ||
//w.SetMaxEvents(1) | ||
w.FilterOps(watcher.Create, watcher.Remove) | ||
w.AddFilterHook(watcher.RegexFilterHook(regexp.MustCompile("/dev/input/event.*"), true)) | ||
if err := w.Add("/dev/input/"); err != nil { | ||
return err | ||
} | ||
go func() { | ||
for { | ||
select { | ||
case event := <-w.Event: | ||
if event.Op == watcher.Remove { | ||
obj.DevicesMap.Delete(event.Path) | ||
} | ||
if event.Op == watcher.Create { | ||
if device, e := evdev.Open(event.Path); e == nil { | ||
obj.DevicesMap.Store(event.Path, OpenInputDevice(device, obj.InputEventCH)) | ||
} | ||
|
||
} | ||
case <-w.Closed: | ||
return | ||
} | ||
} | ||
}() | ||
|
||
inputDevices, _ := evdev.ListInputDevices() | ||
for _, device := range inputDevices { | ||
obj.DevicesMap.Store(device.Fn, OpenInputDevice(device, obj.InputEventCH)) | ||
} | ||
|
||
err := w.Start(time.Millisecond * 100) | ||
return err | ||
} | ||
|
||
func (obj *Host) send2serial() { | ||
var sendBuff = []byte{0, 0, 0, 0, 0, 0} | ||
for { | ||
e := <-obj.InputEventCH | ||
|
||
if e.Type == evdev.EV_KEY { | ||
if e.Value == 2 { //repeat key | ||
continue | ||
} | ||
//keyboard event | ||
sendBuff = []byte{0, 0, 0, 0, 0, 0} | ||
sendBuff[0] = uint8(e.Type) | ||
sendBuff[1] = byte(uint16(e.Code)) | ||
sendBuff[2] = byte(uint16(e.Code) >> 8) | ||
sendBuff[3] = byte(uint16(e.Value)) | ||
sendBuff[4] = byte(uint16(e.Value) >> 8) | ||
sendBuff[5] = byte('\n') | ||
|
||
_, err := obj.serialDevice.Port.Write(sendBuff) | ||
if err != nil { | ||
logrus.Error(err) | ||
} | ||
if obj.Debug { | ||
name := "" | ||
if v, ok := evdev.KEY[int(e.Code)]; ok { | ||
name = v | ||
} | ||
logrus.WithFields(logrus.Fields{"[01]Type": e.Type, "[23]Code": e.Code, "[4567]" + name: e.Value}).Info(sendBuff) | ||
} | ||
|
||
} else if e.Type == evdev.EV_REL { //mouse event | ||
sendBuff = []byte{0, 0, 0, 0, 0, 0} | ||
sendBuff[0] = uint8(e.Type) | ||
sendBuff[1] = byte(uint16(e.Code)) | ||
sendBuff[2] = byte(uint16(e.Code) >> 8) | ||
sendBuff[3] = byte(uint16(e.Value)) | ||
sendBuff[4] = byte(uint16(e.Value) >> 8) | ||
sendBuff[5] = byte('\n') | ||
_, err := obj.serialDevice.Port.Write(sendBuff) | ||
if err != nil { | ||
logrus.Error(err) | ||
} | ||
if obj.Debug { | ||
name := "" | ||
if v, ok := evdev.REL[int(e.Code)]; ok { | ||
name = v | ||
} | ||
logrus.WithFields(logrus.Fields{"[01]Type": e.Type, "[23]Code": e.Code, "[4567]" + name: e.Value}).Info(sendBuff) | ||
} | ||
} //else { | ||
|
||
// if e.Type == 4 { | ||
// if devices.Debug { | ||
// //logrus.Infof("- MSC : %+v \t %s", e, evdev.MSC[int(e.Code)]) | ||
// } | ||
// } else if e.Type == 0 { | ||
// //logrus.Infof("- SYN: %+v \t %s", e, evdev.SYN[int(e.Code)]) | ||
// } else { | ||
// logrus.Infof("??? : %+v \t", e) | ||
// } | ||
// } | ||
|
||
} | ||
} | ||
|
||
func (obj *Host) readserial() { | ||
var serialReader = bufio.NewReader(obj.serialDevice.Port) | ||
for { | ||
d, e := serialReader.ReadByte() | ||
if e == nil { | ||
logrus.Infof("LED Change : %x", d) | ||
} | ||
} | ||
|
||
} |
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
Original file line number | Diff line number | Diff line change |
---|---|---|
@@ -0,0 +1,39 @@ | ||
package main | ||
|
||
import ( | ||
evdev "github.com/gvalkov/golang-evdev" | ||
"github.com/sirupsen/logrus" | ||
) | ||
|
||
type InputDevice struct { | ||
Path string | ||
Name string | ||
Dev *evdev.InputDevice | ||
|
||
outCH chan *evdev.InputEvent | ||
} | ||
|
||
func OpenInputDevice(dev *evdev.InputDevice, outch chan *evdev.InputEvent) (obj *InputDevice) { | ||
obj = &InputDevice{} | ||
obj.Path = dev.Fn | ||
obj.Name = dev.Name | ||
obj.outCH = outch | ||
obj.Dev = dev | ||
go obj.readLoop() | ||
logrus.Info("Input Plugin:", obj.Path, ",", obj.Name) | ||
return obj | ||
} | ||
|
||
func (obj *InputDevice) readLoop() { | ||
defer func() { | ||
defer obj.Dev.Release() | ||
logrus.Info("Input Removed:", obj.Path, ",", obj.Name) | ||
}() | ||
for { | ||
n, err := obj.Dev.ReadOne() | ||
if err != nil { | ||
return | ||
} | ||
obj.outCH <- n | ||
} | ||
} |
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
Original file line number | Diff line number | Diff line change |
---|---|---|
@@ -0,0 +1,138 @@ | ||
package main | ||
|
||
import ( | ||
"bytes" | ||
"os" | ||
"os/exec" | ||
"path/filepath" | ||
"runtime" | ||
|
||
"github.com/kardianos/service" | ||
|
||
"github.com/sirupsen/logrus" | ||
) | ||
|
||
const APP_NAME = "hlw_host" | ||
const APP_DisplayName = "HLW HOST" | ||
const APP_Description = "github.com/dazhoudotnet/hidlikewindows" | ||
|
||
func main() { | ||
logrus.SetLevel(logrus.DebugLevel) | ||
svcConfig := &service.Config{ | ||
Name: APP_NAME, | ||
DisplayName: APP_DisplayName, | ||
Description: APP_Description, | ||
} | ||
prg := &program{} | ||
s, _ := service.New(prg, svcConfig) | ||
|
||
if len(os.Args) > 1 { | ||
var err error | ||
verb := os.Args[1] | ||
switch verb { | ||
case "install": | ||
err = s.Install() | ||
if err != nil { | ||
logrus.Errorln("Installation failed:", err) | ||
logrus.Exit(1) | ||
return | ||
} | ||
logrus.Infoln(s.String(), "Successful installation.") | ||
case "uninstall": | ||
case "remove": | ||
err = s.Uninstall() | ||
if err != nil { | ||
logrus.Errorln("Uninstall failed:", err) | ||
logrus.Exit(1) | ||
return | ||
} | ||
logrus.Infoln(s.String(), "Successfully removed.") | ||
case "start": | ||
err = s.Start() | ||
if err != nil { | ||
logrus.Errorln(s.String(), "Startup failed:", err) | ||
return | ||
} | ||
logrus.Infoln(s.String(), "Successful startup. pid=", os.Getpid()) | ||
case "stop": | ||
err = s.Stop() | ||
if err != nil { | ||
logrus.Errorln(s.String(), "Stop failed:", err) | ||
return | ||
} | ||
logrus.Infoln(s.String(), "Successfully stopped.") | ||
return | ||
} | ||
} else { | ||
err := s.Run() | ||
if err != nil { | ||
logrus.Errorln("Failed to run:", s.String()) | ||
logrus.Exit(1) | ||
return | ||
} | ||
} | ||
|
||
} | ||
|
||
type program struct{} | ||
|
||
func (p *program) Start(s service.Service) error { | ||
go p.run() | ||
return nil | ||
} | ||
func (p *program) run() { | ||
doWork() | ||
} | ||
func (p *program) Stop(s service.Service) error { | ||
return nil | ||
} | ||
|
||
func doWork() { | ||
defer func() { | ||
if e := recover(); e != nil { | ||
logrus.Errorln(APP_NAME, "WTF!!!") | ||
logrus.Errorln(e) | ||
logrus.Exit(1) | ||
return | ||
} | ||
}() | ||
runtime.GOMAXPROCS(runtime.NumCPU()) | ||
|
||
{ | ||
//systemctl disable [email protected] | ||
cmd := exec.Command("/usr/sbin/service", "getty@tty1", "stop") | ||
var out bytes.Buffer | ||
cmd.Stdout = &out | ||
cmd.Stderr = &out | ||
if e := cmd.Run(); e != nil { | ||
logrus.Error(out.String()) | ||
logrus.Error(e) | ||
logrus.Exit(1) | ||
} | ||
} | ||
|
||
{ //remap keyboard ignore ctrl+alt+del (reboot) | ||
cmd := exec.Command("/bin/loadkeys", CurrentDir()+"disablekeyboard.kmap") | ||
var out bytes.Buffer | ||
cmd.Stdout = &out | ||
cmd.Stderr = &out | ||
if e := cmd.Run(); e != nil { | ||
logrus.Error(out.String()) | ||
logrus.Error(e) | ||
logrus.Exit(1) | ||
} | ||
} | ||
|
||
host, e := NewHost() | ||
if e != nil { | ||
logrus.Fatal(e) | ||
} | ||
go host.Run() | ||
logrus.Info("HLW Host started.") | ||
select {} | ||
} | ||
|
||
func CurrentDir() string { | ||
dir, _ := filepath.Abs(filepath.Dir(os.Args[0])) | ||
return dir + string(os.PathSeparator) | ||
} |
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
Original file line number | Diff line number | Diff line change |
---|---|---|
@@ -0,0 +1,5 @@ | ||
package main | ||
|
||
func main(){ | ||
|
||
} |