source: trunk/MagicSoft/Cosy/candrv/network.cc@ 2278

Last change on this file since 2278 was 2278, checked in by tbretz, 21 years ago
*** empty log message ***
File size: 9.7 KB
Line 
1/* ======================================================================== *\
2!
3! *
4! * This file is part of Stesy, the MAGIC Steering System
5! * Software. It is distributed to you in the hope that it can be a useful
6! * and timesaving tool in analysing Data of imaging Cerenkov telescopes.
7! * It is distributed WITHOUT ANY WARRANTY.
8! *
9! * Permission to use, copy, modify and distribute this software and its
10! * documentation for any purpose is hereby granted without fee,
11! * provided that the above copyright notice appear in all copies and
12! * that both that copyright notice and this permission notice appear
13! * in supporting documentation. It is provided "as is" without express
14! * or implied warranty.
15! *
16!
17!
18! Author(s): Thomas Bretz <mailto:tbretz@uni-sw.gwdg.de>, 2001
19!
20! Copyright: MAGIC Software Development, 2000-2001
21!
22!
23\* ======================================================================== */
24
25///////////////////////////////////////////////////////////////////////
26//
27// Network
28//
29// is a collection of nodes which coordinates the network
30//
31///////////////////////////////////////////////////////////////////////
32#include "network.h"
33
34#include <iostream.h> // cout
35#include <iomanip.h> // setw, setfill
36
37ClassImp(Network);
38
39// --------------------------------------------------------------------------
40//
41// Start the canopen module
42// Initialize all nodes (calling NodeDrv::Init()
43//
44void Network::Start()
45{
46 lout << "- Starting network." << endl;
47
48 VmodIcan::Start();
49 InitNodes();
50
51 lout << "- Network started." << endl;
52}
53
54// --------------------------------------------------------------------------
55//
56// Stop all nodes, stop the can module
57//
58void Network::Stop()
59{
60 lout << "- Stopping network." << endl;
61
62 StopNodes();
63 VmodIcan::Stop();
64
65 lout << "- Network stopped." << endl;
66}
67
68// --------------------------------------------------------------------------
69//
70// Initialize the network, set all nodes to NULL (n/a)
71//
72Network::Network(const char *dev, const int baud, MLog &out) : CanOpen(dev, baud, out)
73{
74 for (int i=0; i<32; i++)
75 fNodes[i] = NULL;
76
77 lout << "- Network initialized." << endl;
78}
79
80// --------------------------------------------------------------------------
81//
82// Distributes the received SDO messages to the addressed nodes.
83// Depending on the received command either HandleSDO, HandleSDOOK or
84// HandleSDOError called.
85// HandleSDO: Handles a received value
86// HandleSDOOK: Handles the acknoledgment of a trasmitted SDO
87// HandleSDOError: Handles error occursion (see CanOpen standard)
88//
89void Network::HandleSDO(BYTE_t node, BYTE_t cmd, WORD_t idx, BYTE_t subidx, LWORD_t data, timeval_t *tv)
90{
91 if (fNodes[node])
92 switch (cmd)
93 {
94 case kSDO_TX4: // answer to 0x40 with 4 bytes of data
95 fNodes[node]->HandleSDO(idx, subidx, data, tv);
96 return;
97
98 case kSDO_TX3: // answer to 0x40 with 2 bytes of data
99 fNodes[node]->HandleSDO(idx, subidx, data&0xffff, tv);
100 return;
101
102 case kSDO_TX1: // answer to 0x40 with 1 byte of data
103 fNodes[node]->HandleSDO(idx, subidx, data&0xff, tv);
104 return;
105
106 case kSDO_TX_OK: // answer to a SDO_TX message
107 fNodes[node]->HandleSDOOK(idx, subidx, data, tv);
108 return;
109
110 case kSDO_TX_ERROR: // error message (instead of 0x60)
111 fNodes[node]->HandleSDOError(data);
112 return;
113 }
114
115 cout << dec << setfill('0');
116 cout << "Network::HandleSDO: Node=" << (int)node << " Cmd=0x" << hex << (int)cmd << ": ";
117 cout << "Sdo=" << idx << "/" << (int)subidx << ": 0x" << setw(8) << data;
118 cout << endl;
119}
120
121// --------------------------------------------------------------------------
122//
123// Distributes PDO1 messages to the correspoding node calling HandlePDO1
124//
125void Network::HandlePDO1(BYTE_t node, BYTE_t *data, timeval_t *tv)
126{
127 if (!fNodes[node])
128 {
129 cout << "Network::HandlePDO1: Node #" << dec << (int)node << " not found - PDO1: " << hex;
130 for (int i=0; i<8; i++)
131 cout << " 0x" << (int)data[i];
132 cout << endl;
133 return;
134 }
135
136 fNodes[node]->HandlePDO1(data, tv);
137}
138
139// --------------------------------------------------------------------------
140//
141// Distributes PDO2 messages to the correspoding node calling HandlePDO2
142//
143void Network::HandlePDO2(BYTE_t node, BYTE_t *data, timeval_t *tv)
144{
145 if (!fNodes[node])
146 {
147 cout << "Network::HandlePDO2: Node #" << dec << (int)node << " not found - PDO2: " << hex;
148 for (int i=0; i<8; i++)
149 cout << " 0x" << (int)data[i];
150 cout << endl;
151 return;
152 }
153
154 fNodes[node]->HandlePDO2(data, tv);
155}
156
157// --------------------------------------------------------------------------
158//
159// Distributes PDO3 messages to the correspoding node calling HandlePDO3
160//
161void Network::HandlePDO3(BYTE_t node, BYTE_t *data, timeval_t *tv)
162{
163 if (!fNodes[node])
164 {
165 cout << "Network::HandlePDO3: Node #" << dec << (int)node << " not found - PDO3: " << hex;
166 for (int i=0; i<8; i++)
167 cout << " 0x" << (int)data[i];
168 cout << endl;
169 return;
170 }
171
172 fNodes[node]->HandlePDO3(data, tv);
173}
174
175// --------------------------------------------------------------------------
176//
177// Distributes PDO4 messages to the correspoding node calling HandlePDO4
178//
179void Network::HandlePDO4(BYTE_t node, BYTE_t *data, timeval_t *tv)
180{
181 if (!fNodes[node])
182 {
183 cout << "Network::HandlePDO4: Node #" << dec << (int)node << " not found - PDO4: " << hex;
184 for (int i=0; i<8; i++)
185 cout << " 0x" << (int)data[i];
186 cout << endl;
187 return;
188 }
189
190 fNodes[node]->HandlePDO4(data, tv);
191}
192
193// --------------------------------------------------------------------------
194//
195// Distributes Nodeguard messages to the correspoding node calling
196// HandleNodeguard
197//
198void Network::HandleNodeguard(BYTE_t node, timeval_t *tv)
199{
200 if (!fNodes[node])
201 {
202 cout << "Network::HandleNodeguard: Node #" << dec << (int)node << " not found: Nodeguard." << endl;
203 return;
204 }
205
206 fNodes[node]->HandleNodeguard(tv);
207}
208
209// --------------------------------------------------------------------------
210//
211// Distributes Emergency messages to the correspoding node calling
212// HandleEmergency
213//
214void Network::HandleEmergency(BYTE_t node, timeval_t *tv)
215{
216 if (!fNodes[node])
217 {
218 cout << "Network::HandleEmergency: Node #" << dec << (int)node << " not found: Emergency." << endl;
219 return;
220 }
221
222 fNodes[node]->HandleEmergency(tv);
223}
224
225
226// --------------------------------------------------------------------------
227//
228// Sets a node to a given nodedrv. The id is requested from the drv object.
229//
230void Network::SetNode(NodeDrv *drv)
231{
232 const BYTE_t nodeid = drv->GetId();
233
234 if (nodeid>31)
235 {
236 cout << "SetNode - Error: Only node Numbers < 32 are allowed"<< endl;
237 return;
238 }
239
240 fNodes[nodeid] = drv;
241}
242
243// --------------------------------------------------------------------------
244//
245// Initializes all nodes calling InitDevice
246//
247void Network::InitNodes()
248{
249 for (int i=0; i<32; i++)
250 if (fNodes[i])
251 {
252 lout << "- Setting up Node #" << dec << i << " (";
253 lout << fNodes[i]->GetNodeName() << ")" << endl;
254 if (fNodes[i]->InitDevice(this))
255 fNodeInitialized[i] = TRUE;
256 else
257 lout << "- " << fNodes[i]->GetNodeName() << ": InitDevice failed." << endl;
258 }
259 lout << "- All Nodes setup." << endl;
260}
261
262// --------------------------------------------------------------------------
263//
264// Stop all nodes calling StopDevice
265//
266void Network::StopNodes()
267{
268 for (int i=0; i<32; i++)
269 if (fNodes[i] && fNodeInitialized[i])
270 {
271 lout << "- Stopping Node #" << dec << i << endl;
272 fNodes[i]->StopDevice();
273 }
274 lout << "- All Nodes stopped." << endl;
275}
276
277// --------------------------------------------------------------------------
278//
279// returns true if one of the nodes has the error-flag set (HasError).
280//
281bool Network::HasError() const
282{
283 bool rc = false;
284
285 for (int i=0; i<32; i++)
286 {
287 if (!fNodes[i])
288 continue;
289
290 if (!fNodes[i]->HasError())
291 continue;
292
293 rc = true;
294
295 if (fNodes[i]->GetError() <= 0)
296 continue;
297
298 //lout << "- Node #" << dec << i << " '" << fNodes[i]->GetNodeName();
299 //lout << "' has error #" << fNodes[i]->GetError() << endl;
300 }
301
302 return rc;
303}
304
305// --------------------------------------------------------------------------
306//
307// returns true if one of the nodes is a zombie node
308//
309bool Network::HasZombie() const
310{
311 for (int i=0; i<32; i++)
312 if (fNodes[i])
313 if (fNodes[i]->IsZombieNode())
314 return true;
315
316 return false;
317}
318
319// --------------------------------------------------------------------------
320//
321// try to reboot all zombie nodes to get them working again. all other
322// nodes are left untouched.
323//
324bool Network::RebootZombies()
325{
326 bool rc = true;
327
328 lout << "- Trying to reboot all Zombies..." << endl;
329 for (int i=0; i<32; i++)
330 if (fNodes[i])
331 if (fNodes[i]->IsZombieNode())
332 if (!fNodes[i]->Reboot())
333 {
334 lout << "- Failed to reboot " << fNodes[i]->GetNodeName() << "." << endl;
335 rc = false;
336 }
337
338 if (rc)
339 lout << "- All Zombies rebooted." << endl;
340
341 return rc;
342}
343
344// --------------------------------------------------------------------------
345//
346// Check the connections to all nodes. (This can also mean: Validate
347// the correct setup, etc)
348//
349void Network::CheckConnections()
350{
351 for (int i=0; i<32; i++)
352 if (fNodes[i])
353 fNodes[i]->CheckConnection();
354}
355
Note: See TracBrowser for help on using the repository browser.