OpenCPN Partial API docs
Loading...
Searching...
No Matches
comm_drv_file.cpp
1/***************************************************************************
2 *
3 * Project: OpenCPN
4 * Purpose: Implement comm_drv_file.h -- driver reading/writing to/from files
5 * Author: David Register, Alec Leamas
6 *
7 ***************************************************************************
8 * Copyright (C) 2022 by David Register, Alec Leamas *
9 * *
10 * This program is free software; you can redistribute it and/or modify *
11 * it under the terms of the GNU General Public License as published by *
12 * the Free Software Foundation; either version 2 of the License, or *
13 * (at your option) any later version. *
14 * *
15 * This program is distributed in the hope that it will be useful, *
16 * but WITHOUT ANY WARRANTY; without even the implied warranty of *
17 * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the *
18 * GNU General Public License for more details. *
19 * *
20 * You should have received a copy of the GNU General Public License *
21 * along with this program; if not, write to the *
22 * Free Software Foundation, Inc., *
23 * 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA. *
24 **************************************************************************/
25
26 // For compilers that support precompilation, includes "wx.h".
27#include <wx/wxprec.h>
28
29#ifndef WX_PRECOMP
30#include <wx/wx.h>
31#endif // precompiled headers
32
33#include <iostream>
34#include <fstream>
35#include <string>
36
37#include <wx/log.h>
38
39#include "comm_driver.h"
40#include "comm_drv_registry.h"
41#include "comm_drv_file.h"
42#include "ocpn_utils.h"
43
46 virtual void Notify(std::shared_ptr<const NavMsg> message) {}
47 virtual void Notify(const AbstractCommDriver& driver) {}
48};
49
50static VoidDriverListener kVoidDriverListener;
51
52using namespace std;
53
54FileCommDriver::FileCommDriver(const string& opath, const string& ipath,
56 : AbstractCommDriver(NavAddr::Bus::TestBus, opath),
57 output_path(opath),
58 input_path(ipath),
59 listener(l) {}
60
61FileCommDriver::FileCommDriver(const string& opath)
62 : FileCommDriver(opath, "", kVoidDriverListener) {}
63
64std::shared_ptr<NavAddr> FileCommDriver::GetAddress() {
65 return std::make_shared<NavAddr>(NavAddrTest(output_path));
66}
67
68bool FileCommDriver::SendMessage(std::shared_ptr<const NavMsg> msg,
69 std::shared_ptr<const NavAddr> addr) {
70 ofstream f;
71 f.open(output_path, ios::app);
72 if (!f.is_open()) {
73 wxLogWarning("Cannot open file %s for writing", output_path.c_str());
74 return false;
75 }
76 f << msg->to_string();
77 f.close();
78 return true;
79}
80
81static vector<unsigned char> HexToChar(string hex) {
82 if (hex.size() % 2 == 1) hex = string("0") + hex;
83 vector<unsigned char> chars;
84 for (size_t i = 0; i < hex.size(); i += 2) {
85 istringstream ss(hex.substr(i, 2));
86 unsigned ival;
87 ss >> std::hex >> ival;
88 chars.push_back(static_cast<unsigned char>(ival));
89 }
90 return chars;
91}
92
93static shared_ptr<const NavMsg> LineToMessage(const string& line,
94 std::shared_ptr<NavAddr> src) {
95 auto words = ocpn::split(line.c_str(), " ");
96 NavAddr::Bus bus = NavAddr::StringToBus(words[0]);
97 switch (bus) {
98 case NavAddr::Bus::N2000:
99 if (true) { // Create a separate scope.
100 N2kName name(N2kName::Parse(words[2]));
101 vector<unsigned char> payload(HexToChar(words[3]));
102// FIXME (Leamas)
103// return make_shared<Nmea2000Msg>(name, payload, src);
104 return make_shared<NullNavMsg>();
105 }
106 break;
107 case NavAddr::Bus::N0183:
108 if (true) { // Create a separate scope.
109 const string id(words[2]);
110 return make_shared<Nmea0183Msg>(id, words[3], src);
111 }
112 break;
113 default:
114 std::cerr << "Cannot parse line: \"" << line << "\"\n" << flush;
115 return make_shared<NullNavMsg>();
116 break;
117 }
118 return make_shared<NullNavMsg>(); // for the compiler.
119}
120
122 CommDriverRegistry::GetInstance().Activate(shared_from_this());
123 if (input_path != "") {
124 ifstream f(input_path);
125 string line;
126 while (getline(f, line)) {
127 auto msg = LineToMessage(line, GetAddress());
128 if (msg->bus != NavAddr::Bus::Undef) listener.Notify(msg);
129 }
130 }
131}
Common interface for all drivers.
Definition: comm_driver.h:58
void Activate(DriverPtr driver)
Add driver to list of active drivers.
Interface implemented by transport layer and possible other parties like test code which should handl...
Definition: comm_driver.h:47
virtual void Notify(std::shared_ptr< const NavMsg > message)=0
Handle a received message.
Read and write data to/from files test driver
Definition: comm_drv_file.h:38
FileCommDriver(const std::string &opath, const std::string &ipath, DriverListener &l)
An instance which can write to file and play data from another.
void Activate() override
Register driver in the driver Registry.
Dummy test address.
Definition: comm_navmsg.h:184
Where messages are sent to or received from.
Definition: comm_navmsg.h:136
Test driver listener sink.
N2k uses CAN which defines the basic properties of messages.
Definition: comm_navmsg.h:62