1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17 package net.sourceforge.jarduino.message;
18
19 import java.util.ArrayList;
20 import java.util.HashMap;
21 import java.util.List;
22 import java.util.Map;
23 import java.util.Objects;
24
25 import net.sourceforge.jarduino.ArduinoException;
26 import net.sourceforge.jarduino.message.ArduinoAttribute.ArduinoAttrObject;
27 import net.sourceforge.jarduino.message.ArduinoParser.ArduinoParserException;
28
29
30
31
32 public class ArduinoNode
33 implements ArduinoNamedObject, ArduinoAttrObject {
34
35
36
37 static final String MARKER = "BU_";
38
39
40
41
42 static final String MARKER_TX = ArduinoMessage.MARKER + "TX_" + MARKER;
43
44
45
46
47 public static final String NULL_NODE = "Vector__XXX";
48
49
50
51
52 private final ArduinoSystem theOwner;
53
54
55
56
57 private final String theName;
58
59
60
61
62 private final List<ArduinoMessage> theMessages;
63
64
65
66
67 private final List<ArduinoMessage> theBorrowed;
68
69
70
71
72 private final Map<ArduinoAttribute, Object> theAttributes;
73
74
75
76
77 private final Map<ArduinoAttribute, Map<ArduinoAttrObject, Object>> theRelations;
78
79
80
81
82
83
84 ArduinoNode(final ArduinoSystem pOwner,
85 final String pName) {
86
87 theOwner = pOwner;
88 theName = pName;
89
90
91 theMessages = new ArrayList<>();
92 theBorrowed = new ArrayList<>();
93 theAttributes = new HashMap<>();
94 theRelations = new HashMap<>();
95 }
96
97
98
99
100
101 public ArduinoSystem getOwner() {
102 return theOwner;
103 }
104
105 @Override
106 public String getName() {
107 return theName;
108 }
109
110
111
112
113
114 void addMessage(final ArduinoMessage pMessage) {
115 theMessages.add(pMessage);
116 }
117
118
119
120
121
122 public List<ArduinoMessage> getMessages() {
123 return theMessages;
124 }
125
126
127
128
129
130 void addBorrowedMessage(final ArduinoMessage pMessage) {
131
132 if (!theMessages.contains(pMessage)) {
133 theBorrowed.add(pMessage);
134 }
135 }
136
137
138
139
140
141 public List<ArduinoMessage> getBorrowed() {
142 return theBorrowed;
143 }
144
145
146
147
148
149
150
151 void setAttrValue(final ArduinoAttribute pAttr,
152 final Object pValue) throws ArduinoParserException {
153
154 if (theAttributes.containsKey(pAttr)) {
155 throw new ArduinoParserException("Duplicate Attribute", pAttr.getName());
156 }
157
158
159 theAttributes.put(pAttr, pValue);
160 }
161
162 @Override
163 public Object getAttrValue(final ArduinoAttribute pAttr) {
164 final Object myValue = theAttributes.get(pAttr);
165 return myValue == null ? pAttr.getDefault() : myValue;
166 }
167
168
169
170
171
172
173
174
175 void setRelationValue(final ArduinoAttribute pAttr,
176 final ArduinoAttrObject pRelation,
177 final Object pValue) throws ArduinoParserException {
178
179 final Map<ArduinoAttrObject, Object> myMap = theRelations.computeIfAbsent(pAttr, a -> new HashMap<>());
180
181
182 if (myMap.containsKey(pRelation)) {
183 throw new ArduinoParserException("Duplicate Relation Attribute", pAttr.getName());
184 }
185
186
187 myMap.put(pRelation, pValue);
188 }
189
190
191
192
193
194
195
196 public Object getRelationValue(final ArduinoAttribute pAttr,
197 final ArduinoAttrObject pRelation) {
198 final Map<ArduinoAttrObject, Object> myMap = theRelations.get(pAttr);
199 final Object myValue = myMap == null ? null : myMap.get(pRelation);
200 return myValue == null ? pAttr.getDefault() : myValue;
201 }
202
203
204
205
206
207
208 ArduinoMessage findMessageById(final String pId) {
209
210 for (ArduinoMessage myMessage : theMessages) {
211 if (myMessage.getId().equals(pId)) {
212 return myMessage;
213 }
214 }
215 return null;
216 }
217
218
219
220
221
222
223 public boolean sendsMessage(final ArduinoMessage pMessage) {
224
225 return theMessages.contains(pMessage)
226 || theBorrowed.contains(pMessage);
227 }
228
229
230
231
232
233
234 public boolean sendsSignal(final ArduinoSignal pSignal) {
235
236 final ArduinoMessage myMessage = pSignal.getOwner();
237 return sendsMessage(myMessage);
238 }
239
240
241
242
243
244
245 public boolean receivesMessage(final ArduinoMessage pMessage) {
246
247 for (ArduinoSignal mySignal : pMessage.getAllSignals()) {
248
249 if (receivesSignal(mySignal)) {
250 return true;
251 }
252 }
253
254
255 return false;
256 }
257
258
259
260
261
262
263 public boolean receivesSignal(final ArduinoSignal pSignal) {
264
265 return pSignal.getReceivers().contains(this);
266 }
267
268
269
270
271
272
273
274 static void parseXmitNodes(final ArduinoSystem pSystem,
275 final String pXmitDef) throws ArduinoException {
276
277 int myIndex = pXmitDef.indexOf(ArduinoChar.COLON);
278 if (myIndex == -1) {
279 throw new ArduinoException("Missing " + ArduinoChar.COLON + " separator", pXmitDef);
280 }
281 final String myHdr = pXmitDef.substring(0, myIndex);
282 String myXmitters = pXmitDef.substring(myIndex + 1).trim();
283
284
285 final String myMarker = ArduinoParser.nextToken(myHdr);
286 final String myMsgId = ArduinoParser.stripToken(myHdr, myMarker);
287 if (!myMarker.equals(MARKER_TX)) {
288 throw new ArduinoException("Invalid marker", pXmitDef);
289 }
290
291
292 final int myLen = myXmitters.length();
293 if (myXmitters.length() == 0 || myXmitters.charAt(myLen - 1) != ArduinoChar.SEMICOLON) {
294 throw new ArduinoException("Missing Attr terminator", pXmitDef);
295 }
296 myXmitters = myXmitters.substring(0, myLen - 1);
297
298
299 try {
300
301 final ArduinoMessage myMessage = pSystem.findMessageById(myMsgId);
302
303
304 while (myXmitters.length() > 0) {
305
306 myIndex = myXmitters.indexOf(ArduinoChar.COMMA);
307 if (myIndex == -1) {
308 pSystem.findNodeByName(myXmitters.trim()).addBorrowedMessage(myMessage);
309 return;
310 }
311 final String myNode = myXmitters.substring(0, myIndex).trim();
312 pSystem.findNodeByName(myNode).addBorrowedMessage(myMessage);
313 myXmitters = myXmitters.substring(myIndex + 1);
314 }
315
316
317 } catch (ArduinoParserException e) {
318 throw new ArduinoException(e.getMessage() + ArduinoChar.COLON + e.getDetail(), pXmitDef);
319 }
320 }
321
322 @Override
323 public boolean equals(final Object pThat) {
324
325 if (pThat == this) {
326 return true;
327 } else if (!(pThat instanceof ArduinoNode)) {
328 return false;
329 }
330
331
332 final ArduinoNode/../../net/sourceforge/jarduino/message/ArduinoNode.html#ArduinoNode">ArduinoNode myThat = (ArduinoNode) pThat;
333
334
335 return theName.equals(myThat.getName())
336 && theOwner.equals(myThat.getOwner());
337 }
338
339 @Override
340 public int hashCode() {
341 return Objects.hash(theName, theOwner);
342 }
343
344 @Override
345 public String toString() {
346 return theName;
347 }
348 }