Пример #1
0
func PgnDefServer() {
	socket, _ := zmq.NewSocket(zmq.REP)
	defer socket.Close()
	socket.Bind("tcp://*:5556")

	for {
		msg, _ := socket.Recv(0)

		tok := strings.Split(string(msg), ":")

		if tok[0] == "get" {
			pgn, _ := strconv.ParseUint(tok[1], 10, 32)
			pgnDef := nmea2k.PgnList[pgn]
			b, _ := msgpack.Marshal(pgnDef)
			socket.SendBytes(b, 0)
		}
	}
}
Пример #2
0
func main() {
	// Command line flags are defined here
	debug := flag.Bool("d", false, "Debug mode, extra logging information shown on stderr")
	verbose := flag.Bool("v", false, "Verbose mode, be chatty")
	help := flag.Bool("h", false, "This help message")
	pgn := flag.Int("pgn", 0, "Display only this PGN")
	src := flag.Int("source", 255, "Display PGNs from this source only")
	quiet := flag.Bool("q", false, "Don't display PGN data")
	addr := flag.String("addr", ":8081", "http service address")
	stats := flag.Bool("s", false, "Display live statistics")
	dev_type := flag.String("dev", "actisense", "Choose type of device: actisense, canusb")
	no_server := flag.Bool("no-server", false, "Don't start Web Sockets or ZeroMQ")
	map_file := flag.String("map", "map.xml", "File to use for mapping between input and Signal K")
	device := "/dev/ttyUSB0"

	flag.Parse()

	if *dev_type != "canusb" && *dev_type != "actisense" {
		log.Fatalln("expected either canusb or actisense, got", *dev_type)
	}

	switch flag.NArg() {
	case 0:
		// Use default device
	case 1:
		device = flag.Arg(0)
	default:
		log.Fatalln("expected max 1 arg for the serial port device, default is", device)
	}

	if *help {
		flag.PrintDefaults()
		return
	}

	if *debug {
		log.Println("opening", device)
	}

	txch := make(chan nmea2k.ParsedMessage)
	cmdch := make(chan CommandRequest)

	statLog := make(map[uint32]uint64)
	var statPgns UintSlice

	data, err := ioutil.ReadFile(*map_file)
	if err != nil {
		log.Fatalln("could not read XML map file:", err, *map_file)
	}

	map_data := Mappings{}

	err = xml.Unmarshal(data, &map_data)
	if err != nil {
		log.Fatalln("could not parse XML map file:", err, *map_file)
	}

	port, err := sio.Open(device, syscall.B230400)

	if err != nil {
		log.Fatalln("open: %s", err)
	}

	var canport can.ReadWriter

	socket := new(zmq.Socket)
	if !*no_server {

		// Start up the WebSockets hub
		go h.run()

		socket, _ = zmq.NewSocket(zmq.PUB)
		defer socket.Close()
		socket.Bind("tcp://*:5555")

		// PgnDefServer causes invalid heap pointer error
		//go PgnDefServer()

		go WebSocketServer(addr)

		go ApiServer(cmdch)
	}

	// Print and transmit received messages
	go func() {
		for {
			res := <-txch

			if (*pgn == 0 || int(res.Header.Pgn) == *pgn) &&
				(*src == 255 || int(res.Header.Source) == *src) &&
				(*quiet == false) && (*stats == false) {
				if *debug {
					fmt.Println(res.Header.Print(*verbose))
				}
				fmt.Println(res.Print(*verbose))
			}

			if *stats {
				if _, ok := statLog[res.Header.Pgn]; ok {
					statLog[res.Header.Pgn]++
				} else {
					statLog[res.Header.Pgn] = 1
					statPgns = append(statPgns, res.Header.Pgn)
					sort.Sort(statPgns)
				}
				terminal.Stdout.Clear()
				for _, k := range statPgns {
					fmt.Println(k, "=>", statLog[k])
				}
			}

			if !*no_server {
				//bm := res.MsgPack()
				//socket.SendBytes(bm, 0)

				bj, err := map_data.Delta(&res)
				if err == nil {
					bytes, err := json.Marshal(bj)
					if err == nil {
						h.broadcast <- bytes
					}
				}
			}
		}
	}()

	// Set up hardware
	if *debug {
		fmt.Println(*dev_type)
	}
	if *dev_type == "canusb" {
		if *debug {
			fmt.Println("Adding Fast Packets")
		}
		for _, p := range nmea2k.PgnList {
			if p.Size > 8 {
				if *debug {
					log.Println("Adding PGN:", p.Pgn)
				}
				canusb.AddFastPacket(p.Pgn)
			}
		}

		if *debug {
			fmt.Println("Opening Channel")
		}
		canport, _ = canusb.OpenChannel(port, 221)
	} else {
		canport, _ = actisense.OpenChannel(port)
		time.Sleep(2)
	}

	// Handle command requests
	go func() {
		for {
			req := <-cmdch

			if req.RequestType == "iso" {
				b0 := (byte)(req.RequestedPgn) & 0xFF
				b1 := (byte)(req.RequestedPgn>>8) & 0xFF
				b2 := (byte)(req.RequestedPgn>>16) & 0xFF
				if canport != nil {
					canport.Write([]byte{0x03, 0x00, 0xEA, 0x00, 0xFF, 0x03, b0, b1, b2})
				} else {
					log.Println("canport is nil")
				}
			}
		}
	}()

	// Read from hardware
	if *dev_type == "canusb" {
		for {
			raw, err := canport.Read()
			if err == nil {
				txch <- *(nmea2k.ParsePacket(raw))
			}
		}
	} else {
		for {
			raw, err := canport.Read()
			if err == nil {
				txch <- *(nmea2k.ParsePacket(raw))
			}
		}
	}
}