kopia lustrzana https://github.com/cyoung/stratux
commit
ceb9a7dc1a
Plik binarny nie jest wyświetlany.
2
Makefile
2
Makefile
|
@ -15,7 +15,7 @@ all:
|
||||||
|
|
||||||
xgen_gdl90:
|
xgen_gdl90:
|
||||||
go get -t -d -v ./main ./godump978 ./uatparse ./sensors
|
go get -t -d -v ./main ./godump978 ./uatparse ./sensors
|
||||||
go build $(BUILDINFO) -p 4 main/gen_gdl90.go main/traffic.go main/gps.go main/network.go main/managementinterface.go main/sdr.go main/ping.go main/uibroadcast.go main/monotonic.go main/datalog.go main/equations.go main/sensors.go main/cputemp.go
|
go build $(BUILDINFO) -p 4 main/gen_gdl90.go main/traffic.go main/gps.go main/network.go main/managementinterface.go main/sdr.go main/ping.go main/uibroadcast.go main/monotonic.go main/datalog.go main/equations.go main/sensors.go main/cputemp.go main/lowpower_uat.go
|
||||||
|
|
||||||
fancontrol:
|
fancontrol:
|
||||||
go get -t -d -v ./main
|
go get -t -d -v ./main
|
||||||
|
|
|
@ -12,6 +12,10 @@ SUBSYSTEMS=="usb", ATTRS{idVendor}=="1546", ATTRS{idProduct}=="01a6", SYMLINK+="
|
||||||
#SUBSYSTEMS=="usb", ATTRS{idVendor}=="1546", ATTRS{idProduct}=="01a7", SYMLINK+="vk172"
|
#SUBSYSTEMS=="usb", ATTRS{idVendor}=="1546", ATTRS{idProduct}=="01a7", SYMLINK+="vk172"
|
||||||
#SUBSYSTEMS=="usb", ATTRS{idVendor}=="1546", ATTRS{idProduct}=="01a6", SYMLINK+="vk162"
|
#SUBSYSTEMS=="usb", ATTRS{idVendor}=="1546", ATTRS{idProduct}=="01a6", SYMLINK+="vk162"
|
||||||
|
|
||||||
|
# Stratux uatradio.
|
||||||
|
# 0403:7028 (Stratux UATRadio)
|
||||||
|
ATTRS{idProduct}=="7028", ATTRS{idVendor}=="0403", RUN+="/sbin/modprobe -q ftdi_sio" RUN+="/bin/sh -c 'echo 0403 7028 > /sys/bus/usb-serial/drivers/ftdi_sio/new_id'", OWNER="root", MODE="0666", SYMLINK+="uatradio"
|
||||||
|
|
||||||
|
|
||||||
|
|
||||||
# pl2303 devices are indistinguishable using idVendor and idProduct.
|
# pl2303 devices are indistinguishable using idVendor and idProduct.
|
||||||
|
|
|
@ -1132,6 +1132,7 @@ type status struct {
|
||||||
UAT_traffic_targets_tracking uint16
|
UAT_traffic_targets_tracking uint16
|
||||||
ES_traffic_targets_tracking uint16
|
ES_traffic_targets_tracking uint16
|
||||||
Ping_connected bool
|
Ping_connected bool
|
||||||
|
UATRadio_connected bool
|
||||||
GPS_satellites_locked uint16
|
GPS_satellites_locked uint16
|
||||||
GPS_satellites_seen uint16
|
GPS_satellites_seen uint16
|
||||||
GPS_satellites_tracked uint16
|
GPS_satellites_tracked uint16
|
||||||
|
@ -1573,6 +1574,9 @@ func main() {
|
||||||
globalStatus.CPUTemp = cpuTemp
|
globalStatus.CPUTemp = cpuTemp
|
||||||
})
|
})
|
||||||
|
|
||||||
|
// Start reading from serial UAT radio.
|
||||||
|
initUATRadioSerial()
|
||||||
|
|
||||||
reader := bufio.NewReader(os.Stdin)
|
reader := bufio.NewReader(os.Stdin)
|
||||||
|
|
||||||
if *replayFlag == true {
|
if *replayFlag == true {
|
||||||
|
|
|
@ -0,0 +1,155 @@
|
||||||
|
package main
|
||||||
|
|
||||||
|
import (
|
||||||
|
"encoding/hex"
|
||||||
|
"fmt"
|
||||||
|
"github.com/stratux/serial"
|
||||||
|
"log"
|
||||||
|
"os"
|
||||||
|
"time"
|
||||||
|
"unsafe"
|
||||||
|
)
|
||||||
|
|
||||||
|
/*
|
||||||
|
|
||||||
|
#cgo LDFLAGS: -ldump978
|
||||||
|
|
||||||
|
#include <stdint.h>
|
||||||
|
#include "../dump978/fec.h"
|
||||||
|
|
||||||
|
*/
|
||||||
|
import "C"
|
||||||
|
|
||||||
|
var radioSerialConfig *serial.Config
|
||||||
|
var radioSerialPort *serial.Port
|
||||||
|
|
||||||
|
func initUATRadioSerial() error {
|
||||||
|
// Init for FEC routines.
|
||||||
|
C.init_fec()
|
||||||
|
go func() {
|
||||||
|
watchTicker := time.NewTicker(1 * time.Second)
|
||||||
|
for {
|
||||||
|
<-watchTicker.C
|
||||||
|
// Watch for the radio or change in settings.
|
||||||
|
if !globalSettings.UAT_Enabled || globalStatus.UATRadio_connected {
|
||||||
|
// UAT not enabled or radio already set up. Continue.
|
||||||
|
continue
|
||||||
|
}
|
||||||
|
if _, err := os.Stat("/dev/uatradio"); err != nil {
|
||||||
|
// Device not connected.
|
||||||
|
continue
|
||||||
|
}
|
||||||
|
log.Printf("===== UAT Device Name : UATRadio v1.0 =====\n")
|
||||||
|
|
||||||
|
// Initialize port at 2Mbaud.
|
||||||
|
radioSerialConfig = &serial.Config{Name: "/dev/uatradio", Baud: 2000000}
|
||||||
|
p, err := serial.OpenPort(radioSerialConfig)
|
||||||
|
if err != nil {
|
||||||
|
log.Printf("\tUAT Open Failed: %s\n", err.Error())
|
||||||
|
continue
|
||||||
|
}
|
||||||
|
|
||||||
|
log.Printf("\tUATRadio init success.\n")
|
||||||
|
|
||||||
|
radioSerialPort = p
|
||||||
|
globalStatus.UATRadio_connected = true
|
||||||
|
|
||||||
|
// Start a goroutine to watch the serial port.
|
||||||
|
go radioSerialPortReader(radioSerialPort)
|
||||||
|
}
|
||||||
|
}()
|
||||||
|
return nil
|
||||||
|
}
|
||||||
|
|
||||||
|
/*
|
||||||
|
radioSerialPortReader().
|
||||||
|
Loop to read data from the radio serial port.
|
||||||
|
*/
|
||||||
|
var radioMagic = []byte{0x0a, 0xb0, 0xcd, 0xe0}
|
||||||
|
|
||||||
|
func radioSerialPortReader(serialPort *serial.Port) {
|
||||||
|
defer func() {
|
||||||
|
globalStatus.UATRadio_connected = false
|
||||||
|
serialPort.Close()
|
||||||
|
}()
|
||||||
|
tmpBuf := make([]byte, 1024) // Read buffer.
|
||||||
|
var buf []byte // Message buffer.
|
||||||
|
for {
|
||||||
|
n, err := serialPort.Read(tmpBuf)
|
||||||
|
if err != nil {
|
||||||
|
log.Printf("serial port err, shutting down radio: %s\n", err.Error())
|
||||||
|
return
|
||||||
|
}
|
||||||
|
buf = append(buf, tmpBuf[:n]...)
|
||||||
|
bufLen := len(buf)
|
||||||
|
var finBuf []byte // Truncated buffer, with processed messages extracted.
|
||||||
|
var numMessages int // Number of messages extracted.
|
||||||
|
// Search for a suitable message to extract.
|
||||||
|
for i := 0; i < bufLen-6; i++ {
|
||||||
|
if (buf[i] == radioMagic[0]) && (buf[i+1] == radioMagic[1]) && (buf[i+2] == radioMagic[2]) && (buf[i+3] == radioMagic[3]) {
|
||||||
|
// Found the magic sequence. Get the length.
|
||||||
|
msgLen := int(uint16(buf[i+4])+(uint16(buf[i+5])<<8)) + 5 // 5 bytes for RSSI and TS.
|
||||||
|
// Check if we've read enough to finish this message.
|
||||||
|
if bufLen < i+6+msgLen {
|
||||||
|
break // Wait for more of the message to come in.
|
||||||
|
}
|
||||||
|
// Message is long enough.
|
||||||
|
processRadioMessage(buf[i+6 : i+6+msgLen])
|
||||||
|
// Remove everything in the buffer before this message.
|
||||||
|
finBuf = buf[i+6+msgLen:]
|
||||||
|
numMessages++
|
||||||
|
}
|
||||||
|
}
|
||||||
|
if numMessages > 0 {
|
||||||
|
buf = finBuf
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
/*
|
||||||
|
processRadioMessage().
|
||||||
|
Processes a single message from the radio. De-interleaves (when necessary), checks Reed-Solomon, passes to main process.
|
||||||
|
*/
|
||||||
|
|
||||||
|
func processRadioMessage(msg []byte) {
|
||||||
|
// RSSI and message timestamp are prepended to the actual packet.
|
||||||
|
|
||||||
|
// RSSI
|
||||||
|
rssiRaw := int8(msg[0])
|
||||||
|
//rssiAdjusted := int16(rssiRaw) - 132 // -132 dBm, calculated minimum RSSI.
|
||||||
|
//rssiDump978 := int16(1000 * (10 ^ (float64(rssiAdjusted) / 20)))
|
||||||
|
rssiDump978 := rssiRaw
|
||||||
|
|
||||||
|
//_ := uint32(msg[1]) + (uint32(msg[2]) << 8) + (uint32(msg[3]) << 16) + (uint32(msg[4]) << 24) // Timestamp. Currently unused.
|
||||||
|
|
||||||
|
msg = msg[5:]
|
||||||
|
|
||||||
|
var toRelay string
|
||||||
|
var rs_errors int
|
||||||
|
switch len(msg) {
|
||||||
|
case 552:
|
||||||
|
to := make([]byte, 552)
|
||||||
|
C.correct_uplink_frame((*C.uint8_t)(unsafe.Pointer(&msg[0])), (*C.uint8_t)(unsafe.Pointer(&to[0])), (*C.int)(unsafe.Pointer(&rs_errors)))
|
||||||
|
toRelay = fmt.Sprintf("+%s;ss=%d;", hex.EncodeToString(to[:432]), rssiDump978)
|
||||||
|
case 48:
|
||||||
|
to := make([]byte, 48)
|
||||||
|
copy(to, msg)
|
||||||
|
i := int(C.correct_adsb_frame((*C.uint8_t)(unsafe.Pointer(&to[0])), (*C.int)(unsafe.Pointer(&rs_errors))))
|
||||||
|
if i == 1 {
|
||||||
|
// Short ADS-B frame.
|
||||||
|
toRelay = fmt.Sprintf("-%s;ss=%d;", hex.EncodeToString(to[:18]), rssiDump978)
|
||||||
|
} else if i == 2 {
|
||||||
|
// Long ADS-B frame.
|
||||||
|
toRelay = fmt.Sprintf("-%s;ss=%d;", hex.EncodeToString(to[:34]), rssiDump978)
|
||||||
|
}
|
||||||
|
default:
|
||||||
|
log.Printf("processRadioMessage(): unhandled message size %d\n", len(msg))
|
||||||
|
}
|
||||||
|
|
||||||
|
if len(toRelay) > 0 && rs_errors != 9999 {
|
||||||
|
o, msgtype := parseInput(toRelay)
|
||||||
|
if o != nil && msgtype != 0 {
|
||||||
|
relayMessage(msgtype, o)
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
|
@ -522,7 +522,11 @@ func sdrWatcher() {
|
||||||
esEnabled := globalSettings.ES_Enabled
|
esEnabled := globalSettings.ES_Enabled
|
||||||
uatEnabled := globalSettings.UAT_Enabled
|
uatEnabled := globalSettings.UAT_Enabled
|
||||||
count := rtl.GetDeviceCount()
|
count := rtl.GetDeviceCount()
|
||||||
atomic.StoreUint32(&globalStatus.Devices, uint32(count))
|
interfaceCount := count
|
||||||
|
if globalStatus.UATRadio_connected {
|
||||||
|
interfaceCount++
|
||||||
|
}
|
||||||
|
atomic.StoreUint32(&globalStatus.Devices, uint32(interfaceCount))
|
||||||
|
|
||||||
// support up to two dongles
|
// support up to two dongles
|
||||||
if count > 2 {
|
if count > 2 {
|
||||||
|
|
Ładowanie…
Reference in New Issue