00001
00002
00003
00004
00005
00006
00007
00008
00009
00010
00011
00012
00013
00014
00015
00016
00017
00018
00019
00020
00021
00022
00023
00024
00025
00026
00027
00028
00029
00030
00031
00032
00033
00034
00035
00036
00037
00038
00039
00040
00041
00042
00043
00044
00045
00046 #ifndef MESSAGE_H
00047 #define MESSAGE_H
00048
00049 #include <pthread.h>
00050
00051 #include <libplayercore/player.h>
00052
00053 class MessageQueue;
00054
00061 class QueuePointer
00062 {
00063 public:
00065 QueuePointer();
00067 QueuePointer(bool _Replace, size_t _Maxlen);
00069 ~QueuePointer();
00071 QueuePointer(const QueuePointer & CopyFrom);
00072
00074 QueuePointer & operator = (const QueuePointer & rhs);
00076 MessageQueue * operator -> ();
00078 MessageQueue * get() const;
00080 MessageQueue & operator * ();
00082 bool operator == (const QueuePointer & rhs);
00084 bool operator == (void * pointer);
00086 bool operator != (const QueuePointer & rhs);
00088 bool operator != (void * pointer);
00089
00090 private:
00092 void DecRef();
00093
00095 MessageQueue * Queue;
00096
00098 unsigned int * RefCount;
00099
00101 pthread_mutex_t * Lock;
00102 };
00103
00104
00105
00120 class Message
00121 {
00122 public:
00125 Message(const struct player_msghdr & Header,
00126 void* data,
00127 bool copy = true);
00128
00131 Message(const struct player_msghdr & Header,
00132 void* data,
00133 QueuePointer &_queue,
00134 bool copy = true);
00135
00137 Message(const Message & rhs);
00138
00140 ~Message();
00141
00147 static bool MatchMessage(player_msghdr_t* hdr,
00148 int type,
00149 int subtype,
00150 player_devaddr_t addr)
00151 {
00152 return(((type < 0) || (hdr->type == (uint8_t)type)) &&
00153 ((subtype < 0) || (hdr->subtype == (uint8_t)subtype)) &&
00154 (hdr->addr.host == addr.host) &&
00155 (hdr->addr.robot == addr.robot) &&
00156 (hdr->addr.interf == addr.interf) &&
00157 (hdr->addr.index == addr.index));
00158 }
00159
00165 static bool MatchMessage(player_msghdr_t* hdr,
00166 int type,
00167 int subtype)
00168 {
00169 return(((type < 0) || (hdr->type == (uint8_t)type)) &&
00170 ((subtype < 0) || (hdr->subtype == (uint8_t)subtype)));
00171 }
00172
00174 player_msghdr_t * GetHeader() {return &Header;};
00176 void* GetPayload() {return (void*)Data;};
00178 unsigned int GetDataSize() {return Header.size;};
00180 bool Compare(Message &other);
00182 void DecRef();
00183
00185 QueuePointer Queue;
00186
00188 unsigned int * RefCount;
00189
00190 private:
00191 void CreateMessage(const struct player_msghdr & Header,
00192 void* data,
00193 bool copy = true);
00194
00196 player_msghdr_t Header;
00198 uint8_t * Data;
00200 pthread_mutex_t * Lock;
00201 };
00202
00206 class MessageQueueElement
00207 {
00208 public:
00210 MessageQueueElement();
00212 ~MessageQueueElement();
00213
00215 Message* msg;
00216 private:
00218 MessageQueueElement * prev;
00220 MessageQueueElement * next;
00221
00222 friend class MessageQueue;
00223 };
00224
00231 class MessageReplaceRule
00232 {
00233 private:
00234
00235
00236 int host, robot, interf, index;
00237
00238 int type, subtype;
00239 public:
00240 MessageReplaceRule(int _host, int _robot, int _interf, int _index,
00241 int _type, int _subtype, int _replace) :
00242 host(_host), robot(_robot), interf(_interf), index(_index),
00243 type(_type), subtype(_subtype), replace(_replace), next(NULL) {}
00244
00245 bool Match(player_msghdr_t* hdr)
00246 {
00247 return(((this->host < 0) ||
00248 ((uint32_t)this->host == hdr->addr.host)) &&
00249 ((this->robot < 0) ||
00250 ((uint32_t)this->robot == hdr->addr.robot)) &&
00251 ((this->interf < 0) ||
00252 ((uint16_t)this->interf == hdr->addr.interf)) &&
00253 ((this->index < 0) ||
00254 ((uint16_t)this->index == hdr->addr.index)) &&
00255 ((this->type < 0) ||
00256 ((uint8_t)this->type == hdr->type)) &&
00257 ((this->subtype < 0) ||
00258 ((uint8_t)this->subtype == hdr->subtype)));
00259 }
00260
00261 bool Equivalent (int _host, int _robot, int _interf, int _index, int _type, int _subtype)
00262 {
00263 return (host == _host && robot == _robot && interf ==_interf && index == _index &&
00264 type == _type && subtype == _subtype);
00265 }
00266
00267
00268
00269 int replace;
00270
00271 MessageReplaceRule* next;
00272 };
00273
00325 class MessageQueue
00326 {
00327 public:
00329 MessageQueue(bool _Replace, size_t _Maxlen);
00331 ~MessageQueue();
00333 bool Empty() { return(this->head == NULL); }
00336 bool Push(Message& msg);
00337
00342 void PushFront(Message & msg, bool haveLock);
00343
00348 void PushBack(Message & msg, bool haveLock);
00349
00353 Message* Pop();
00357 void SetReplace(bool _Replace) { this->Replace = _Replace; };
00364 void AddReplaceRule(int _host, int _robot, int _interf, int _index,
00365 int _type, int _subtype, int _replace);
00371 void AddReplaceRule(const player_devaddr_t &device,
00372 int _type, int _subtype, int _replace);
00375 int CheckReplace(player_msghdr_t* hdr);
00382 bool Wait(double TimeOut=0.0);
00385 void DataAvailable(void);
00387 bool Filter(Message& msg);
00389 void ClearFilter(void);
00391 void SetFilter(int host, int robot, int interf, int index,
00392 int type, int subtype);
00394 void SetPull (bool _pull) { this->pull = _pull; }
00395
00397 size_t GetLength(void);
00398
00400 void SetDataRequested(bool d, bool haveLock);
00401
00402 private:
00404 void Lock() {pthread_mutex_lock(&lock);};
00406 void Unlock() {pthread_mutex_unlock(&lock);};
00409 void Remove(MessageQueueElement* el);
00411 MessageQueueElement* head;
00413 MessageQueueElement* tail;
00415 pthread_mutex_t lock;
00417 size_t Maxlen;
00419 MessageReplaceRule* replaceRules;
00422 bool Replace;
00424 size_t Length;
00428 pthread_cond_t cond;
00430 pthread_mutex_t condMutex;
00432 bool filter_on;
00433 int filter_host, filter_robot, filter_interf,
00434 filter_index, filter_type, filter_subtype;
00437 bool pull;
00440 bool data_requested;
00442 bool data_delivered;
00444 bool drop_count;
00445 };
00446
00447
00448
00449
00450 #endif