source: pacpussensors/trunk/Sick/SickLDMRSSensor.h@ 148

Last change on this file since 148 was 73, checked in by DHERBOMEZ Gérald, 10 years ago

deletion of bad include file

File size: 9.6 KB
Line 
1/*********************************************************************
2// created: 2014/02/02 - 10:48
3// filename: SickLDMRSSensor.h
4//
5// author: Cyril Fougeray
6// Copyright Heudiasyc UMR UTC/CNRS 6599
7//
8// version: $Id: $
9//
10// purpose: Definition of the SickLDMRSSensor class
11*********************************************************************/
12
13
14
15
16#ifndef SICKLDMRSSENSOR_H
17#define SICKLDMRSSENSOR_H
18
19#include "Pacpus/kernel/ComponentBase.h"
20#include "Pacpus/kernel/DbiteFile.h"
21
22#include "AbstractSickSensor.h"
23#include "SickLDMRSData.h"
24#include <fstream>
25#include <string>
26
27// Constants for Sick LDMRS
28static const uint32_t DATA_HEADER_SIZE = 24; // in bytes
29static const uint32_t SCAN_HEADER_SIZE = 44; // in bytes
30static const uint32_t MEASURED_POINT_DATA_SIZE = 10; // in bytes
31// @12.5Hz, the sensor has a multiresolution:
32// - lateral range (50 to 30 degrees and -30 to -60 degrees): 0.5 degrees
33// - medium range (30 to 10 degrees and -10 to -30 degrees): 0.25 degrees
34// - central range (10 to -10 degrees): 0.125 degrees
35// So theorically, the max number of points per layer is (20+30)/0.5 + (20+20)/0.25 + 20/0.125 + 1 = 321
36static const uint32_t MAX_SCAN_POINT_PER_LAYER = 321;
37static const uint32_t MAX_SCAN_POINT = 4 * MAX_SCAN_POINT_PER_LAYER; // 4 layers sensor
38static const uint32_t BODY_MAX_SIZE = DATA_HEADER_SIZE + SCAN_HEADER_SIZE + MEASURED_POINT_DATA_SIZE * MAX_SCAN_POINT; // 12 908
39
40// Export macro for SickLDMRS DLL for Windows only
41#ifdef WIN32
42# ifdef SICKLDMRS_EXPORTS
43 // make DLL
44# define SICKLDMRS_API __declspec(dllexport)
45# else
46 // use DLL
47# define SICKLDMRS_API __declspec(dllimport)
48# endif
49#else
50 // On other platforms, simply ignore this
51# define SICKLDMRS_API
52#endif
53
54class QEvent;
55
56namespace pacpus {
57
58class ShMem;
59class SickComponent;
60
61
62
63/// The class carrying Sick LDMRS message.
64/** This class is used so that we can store every information sent by a Sick LDMRS sensor.
65 * First, the raw data is stored in \c body.
66 * These data are then decoded and general information about the message is stored in DataHeader and ScanHeader
67 * (Object data decoding is not implemented yet).
68 * Then, the body field is replaced by a ScanPoint or ScanObject array in order to be stored in DBT/UTC files.
69 */
70class SICKLDMRS_API MessageLDMRS
71{
72public:
73 /// Constructor.
74 MessageLDMRS()
75 {
76 time = 0;
77 timerange = 0;
78 memset(&hData,0,sizeof(hData));
79 memset(&hScan,0,sizeof(hScan));
80 }
81
82 /// Destructor.
83 ~MessageLDMRS(){}
84
85 //! An instance of DataHeader.
86 DataHeader hData;
87
88 //! An instance of ScanHeader (if data type is scan points).
89 ScanHeader hScan;
90
91 //! An array of characters : raw data then array of points or objects, depending on data type.
92 /** This array pointer points to allocated in memory (basically, in heap (malloc)) and then must be freed (free) when the whole message is decoded and stored. */
93 char body[BODY_MAX_SIZE];
94
95 //! Time when the message is received.
96 road_time_t time;
97
98 //! Timerange : roughly, time between measurement of a point and the processing step (not implemented).
99 road_timerange_t timerange;
100};
101
102
103
104//! The class implenting receiving, decoding and storing process of Sick LD-MRS data.
105/**
106 * This class can be used as a particular thread to acquire data from Sick LDMRS sensors.
107 * The Ethernet interface is used to get data from the sensor. Thus, the goal of this class is to
108 * get packets and decode them. Also, it offers the possibility to store all relevant information in
109 * two files (.dbt and .utc).
110 * It can be managed by SickComponent objects.
111 */
112class SickLDMRSSensor : public AbstractSickSensor
113{
114 Q_OBJECT
115public:
116 /// Constructor
117 SickLDMRSSensor(QObject *parent);
118
119 /**
120 * @brief SickLDMRSSensor constructor.
121 * @param parent Basically, a SickComponent object.
122 * @param name Name of the sensor in order to write on .dbt and .utc files and to recognize every sensors used.
123 * @param ip The IP address of the remote Sick LDMRS sensor.
124 * @param port The port of the remote Sick LDMRS sensor.
125 * @param recording If \c true, data is recorded into dbt + utc files. Data is not recorded otherwise.
126 */
127 SickLDMRSSensor(QObject *parent, QString name, QString ip, int port, int recording);
128
129 /// Destructor
130 ~SickLDMRSSensor();
131
132
133 void stopActivity(); /*!< To stop the processing thread */
134 void startActivity(); /*!< To start the processing thread */
135
136 /**
137 * @brief splitPacket reconstitute incoming data and find messages.
138 * @param packet Raw data coming from the sensor.
139 * @param length Length of the data.
140 * @param time Time of the last received data.
141 *
142 * Analyse the ethernet packet received from the Sick sensor and try to find a
143 * complete message (scan data message or object message)
144 * If a message has been found it is added at the end of the message list
145 * else the pending bytes are stored to be analyzed by further incoming data.
146 */
147 void splitPacket(const char * packet, const int length, road_time_t time);
148
149
150 /**
151 * @brief Process/decode a message.
152 * @param msg The message is encapsulated into a MessageLDMRS
153 * @return Type of the message
154 *
155 * Process the raw data of the message and update the MessageLDMRS object passed : it fills the 2 headers (message and scan)
156 * and replace the body field of the MessageLDRMS object by an array of ScanPoint.
157 * - @b Warning : the process of object data type is not implemented yet !
158 */
159 unsigned long processMessage(MessageLDMRS & msg);
160
161 //! Find the position of the magic word into the array and returns this index.
162 /*!
163 * \param message Array of characters, raw data received from sensor.
164 * \param length Length of the array.
165 * \return
166 * - @b -1 if no magic word is found
167 * - @b position of the magic word otherwise
168 */
169 uint32_t findMagicWord(const char * message, const unsigned length);
170
171 /**
172 * @brief getMessageSize get the message size of the entire message.
173 * @param message Raw data of the message.
174 * @param length Length of the raw data received.
175 * @param magicWordIndex First element of the message, used to get the size of the message.
176 * @return The @b size of the whole message.
177 *
178 * The size of the message is found inside the message thanks to an offset after the index of the Magic Word.
179 * - The first header of the message that contains the size of the message is in \b Big \b Endian format !
180 *
181 */
182 uint32_t getMessageSize(const char * message, const unsigned length, const long magicWordIndex);
183
184 /**
185 * @brief isMessageComplete compare the size of the message read into the message and the length of the received data.
186 * @param length Length of the received data.
187 * @param size Size of the message read. See getMessageSize.
188 * @return @b true if the message is complete, @b false otherwise
189 */
190 bool isMessageComplete(const unsigned length, const long size);
191
192public Q_SLOTS:
193 /**
194 * @brief customEvent allows to receive the incoming data and store them into known structures.
195 * @param e Event that carries the Ethernet packets and receiving time.
196 */
197 void customEvent(QEvent * e);
198
199 /**
200 * @brief Configure the object, not used for the moment.
201 */
202 void configure();
203
204public:
205 /**
206 * @brief S_socket, used to receive and send data to the remote sensor.
207 */
208 SickSocket * S_socket;
209
210signals:
211 void refreshDisplay();
212
213private:
214 /// Name is used to recognize between several sensors and store data into .dbt and utc files.
215 QString name_;
216
217 /// The IP address of the remote Sick LDMRS sensor we are connected to.
218 QString ipaddr_;
219
220 /// The SickLDMRS port
221 int port_;
222
223 /// Enable storing in DBT + UTC files
224 bool recording_;
225
226 /// List of messages to process.
227 std::list<MessageLDMRS> msgList;
228
229 /// Received raw data is appended into this MessagePacket.
230 MessagePacket pendingBytes;
231
232 /// Append new data into the private MessagePacket @b pendingBytes.
233 void storePendingBytes(road_time_t time);
234
235 /**
236 * @brief fillDataHeader fills the message header of the message
237 * @param msg
238 * - @b Warning:
239 * - the body field of the message have to be completed before
240 * - Data header format is @b Big @b Endian
241 */
242 void fillDataHeader(MessageLDMRS& msg);
243
244
245 /**
246 * @brief fillScanHeader fill the scan header of the message
247 * @param msg Raw data must be stored into the body field of the message
248 * - @b Warning
249 * - the body field of the message have to be completed before
250 * - Scan header format is @b Little @b Endian
251 */
252 void fillScanHeader(MessageLDMRS& msg);
253
254 /**
255 * @brief Write data into .dbt + .utc files.
256 * @param msg
257 *
258 * SickLDMRS_dbt structure is filled and stored into the DBT file.
259 * The array of ScanPoint is then stored into the UTC file.
260 */
261 void writeData(MessageLDMRS &msg);
262
263 std::string kSickDbtFileName; //!< Name of the DBT file.
264 std::string kSickUtcFileName; //!< Name of the UTC file.
265
266 pacpus::DbiteFile dbtFile_; //!< DBT file.
267 std::ofstream dataFile_; //!< UTC file.
268
269#ifdef SICKLDMRS_SH_MEM
270 ShMem * shmem_;
271 SickLDMRS_shMem sickData;
272#endif
273
274};
275
276} // namespace pacpus
277
278#endif // SICKLDMRSSENSOR_H
Note: See TracBrowser for help on using the repository browser.