]> git.tdb.fi Git - r2c2.git/blob - source/libr2c2/centralstation.h
Pass sensor events through blocks
[r2c2.git] / source / libr2c2 / centralstation.h
1 /* $Id$
2
3 This file is part of R²C²
4 Copyright © 2010  Mikkosoft Productions, Mikko Rasa
5 Distributed under the GPL
6 */
7
8 #ifndef LIBR2C2_CENTRALSTATION_H_
9 #define LIBR2C2_CENTRALSTATION_H_
10
11 #include <msp/net/streamsocket.h>
12 #include <msp/time/timestamp.h>
13 #include "driver.h"
14
15 namespace R2C2 {
16
17 class CentralStation: public Driver
18 {
19 private:
20         struct Tag
21         {
22                 std::string type;
23                 unsigned code;
24                 std::string value;
25
26                 Tag();
27
28                 operator bool() const;
29         };
30
31         struct Message
32         {
33                 typedef std::map<std::string, std::string> AttribMap;
34                 typedef std::map<unsigned, AttribMap> ObjectMap;
35         
36                 Tag header;
37                 ObjectMap content;
38                 Tag footer;
39
40                 operator bool() const;
41         };
42
43         enum Error
44         {
45                 OK,
46                 NERROR_UNKNOWNCOMMAND = 10,
47                 NERROR_UNKNOWNARG = 11,
48                 NERROR_UNKNOWNPARAM = 12,
49                 NERROR_UNKNOWNID = 15,
50                 NERROR_SIZE = 20,
51                 NERROR_NOTALLOWED = 22,
52                 NERROR_NOCONTROL = 25,
53                 NERROR_NOCREATE = 28,
54                 NERROR_NOARG = 29
55         };
56
57         enum Protocol
58         {
59                 MM,
60                 MM_27,
61                 MFX
62         };
63
64         struct Locomotive
65         {
66                 std::string name;
67                 Protocol protocol;
68                 unsigned address;
69                 unsigned speed;
70                 bool reverse;
71                 unsigned funcs;
72                 bool control;
73
74                 Locomotive();
75         };
76
77         struct Turnout
78         {
79                 enum Symbol
80                 {
81                         LEFT,
82                         RIGHT,
83                         THREEWAY,
84                         DOUBLESLIP
85                 };
86
87                 unsigned address;
88                 unsigned symbol;
89                 unsigned state;
90                 unsigned bits;
91                 bool synced;
92
93                 Turnout();
94         };
95
96         struct Sensor
97         {
98                 bool state;
99
100                 Sensor();
101         };
102
103         typedef std::map<unsigned, unsigned> AddressMap;
104         typedef std::map<unsigned, Locomotive> LocoMap;
105         typedef std::map<unsigned, Turnout> TurnoutMap;
106         typedef std::map<unsigned, Sensor> SensorMap;
107
108         Msp::Net::StreamSocket socket;
109         std::list<std::string> cmd_queue;
110         unsigned pending_commands;
111         bool power;
112         bool halted;
113         std::string in_buffer;
114         LocoMap locos;
115         AddressMap loco_addr;
116         bool locos_synced;
117         TurnoutMap turnouts;
118         AddressMap turnout_addr;
119         bool turnouts_synced;
120         SensorMap sensors;
121         std::vector<unsigned> s88;
122         bool sensors_synced;
123
124 public:
125         CentralStation(const std::string &);
126         ~CentralStation();
127
128         virtual void set_power(bool);
129         virtual bool get_power() const { return power; }
130         virtual void halt(bool);
131         virtual bool is_halted() const { return halted; }
132
133         virtual const char *enumerate_protocols(unsigned) const;
134         virtual unsigned get_protocol_speed_steps(const std::string &) const;
135
136         virtual void add_loco(unsigned, const std::string &, const VehicleType &);
137         virtual void set_loco_speed(unsigned, unsigned);
138         virtual void set_loco_reverse(unsigned, bool);
139         virtual void set_loco_function(unsigned, unsigned, bool);
140
141         virtual void add_turnout(unsigned, const TrackType &);
142         virtual void set_turnout(unsigned, unsigned);
143         virtual unsigned get_turnout(unsigned) const;
144
145         virtual void add_sensor(unsigned);
146         virtual void set_sensor(unsigned, bool) { }
147         virtual bool get_sensor(unsigned) const;
148
149         virtual void tick();
150         virtual void flush();
151
152 private:
153         void command(const std::string &, bool = false);
154         Message receive();
155         void process_reply(const Message &);
156         void process_event(const Message &);
157         void process_object(unsigned, const Message::AttribMap &);
158         Protocol map_protocol(const std::string &) const;
159         template<typename T>
160         unsigned map_address(const std::map<unsigned, T> &, const AddressMap &, unsigned) const;
161         void skip(std::string::iterator &, const std::string::iterator &, const std::string &) const;
162         std::string parse_token(std::string::iterator &, const std::string::iterator &, const std::string &) const;
163         Tag parse_tag(std::string::iterator &, const std::string::iterator &) const;
164         Message parse_message(std::string::iterator &, const std::string::iterator &) const;
165 };
166
167 } // namespace R2C2
168
169 #endif