00001
00002
00003
00004
00005
00006
00007
00008
00009
00010
00011
00012
00013
00014
00015
00016
00017 #ifndef MuscleMessage_h
00018 #define MuscleMessage_h
00019
00020 #include "support/Point.h"
00021 #include "support/Rect.h"
00022 #include "util/ByteBuffer.h"
00023 #include "util/String.h"
00024 #include "util/Hashtable.h"
00025
00026 BEGIN_NAMESPACE(muscle);
00027
00028 class Message;
00029 typedef Ref<Message> MessageRef;
00030
00035 const Message & GetEmptyMessage();
00036
00038 const MessageRef & GetEmptyMessageRef();
00039
00044 MessageRef::ItemPool * GetMessagePool();
00045
00050 MessageRef GetMessageFromPool(uint32 what = 0L);
00051
00057 MessageRef GetMessageFromPool(ObjectPool<Message> & pool, uint32 what = 0L);
00058
00063 MessageRef GetMessageFromPool(const Message & copyMe);
00064
00070 MessageRef GetMessageFromPool(ObjectPool<Message> & pool, const Message & copyMe);
00071
00072
00073 class AbstractDataArray;
00074
00078 class MessageFieldNameIterator : private HashtableIterator<String, GenericRef>
00079 {
00080 public:
00084 MessageFieldNameIterator() : _typeCode(B_ANY_TYPE) {}
00085
00093 MessageFieldNameIterator(const Message & msg, uint32 type = B_ANY_TYPE, uint32 flags = 0);
00094
00096 ~MessageFieldNameIterator() {}
00097
00099 void operator++(int) {(void) GetNextFieldNameString();}
00100
00102 void operator--(int) {bool b = IsBackwards(); SetBackwards(!b); (void) GetNextFieldNameString(); SetBackwards(b);}
00103
00105 bool HasMoreFieldNames() const {return (PeekNextFieldNameString() != NULL);}
00106
00111 const String & GetFieldName() const {return *PeekNextFieldNameString();}
00112
00118 status_t GetNextFieldName(String & name);
00119
00125 const char * GetNextFieldName() {const String * r = GetNextFieldNameString(); return r ? r->Cstr() : NULL;}
00126
00131 const String * GetNextFieldNameString();
00132
00138 status_t PeekNextFieldName(String & name) const;
00139
00145 const char * PeekNextFieldName() const {const String * r = PeekNextFieldNameString(); return r ? r->Cstr() : NULL;}
00146
00151 const String * PeekNextFieldNameString() const;
00152
00153 private:
00154 friend class Message;
00155 MessageFieldNameIterator(const HashtableIterator<String, GenericRef> & iter, uint32 tc) : HashtableIterator<String, GenericRef>(iter), _typeCode(tc) {}
00156
00157 uint32 _typeCode;
00158 };
00159
00160
00161
00162
00163
00164 #define OLDEST_SUPPORTED_PROTOCOL_VERSION 1347235888 // 'PM00'
00165 #define CURRENT_PROTOCOL_VERSION 1347235888 // 'PM00'
00166
00174 class Message : public FlatCountable
00175 {
00176 public:
00178 uint32 what;
00179
00181 Message() : what(0) {}
00182
00186 Message(uint32 what) : what(what) {}
00187
00189 Message(const Message & copyMe) : FlatCountable() {*this = copyMe;}
00190
00192 virtual ~Message() {}
00193
00195 Message &operator=(const Message &msg);
00196
00201 bool operator ==(const Message & rhs) const;
00202
00204 bool operator !=(const Message & rhs) const {return !(*this == rhs);}
00205
00213 status_t GetInfo(const String & name, uint32 *type, uint32 *c = NULL, bool *fixed_size = NULL) const;
00214
00219 uint32 CountNames(uint32 type = B_ANY_TYPE) const;
00220
00225 bool HasNames(uint32 type = B_ANY_TYPE) const {return (CountNames(type) > 0);}
00226
00228 bool IsEmpty() const {return (_entries.IsEmpty());}
00229
00234 void PrintToStream(bool recursive = true, int indentLevel = 0) const;
00235
00239 String ToString(bool recursive = true, int indentLevel = 0) const;
00240
00244 void AddToString(String & s, bool recursive = true, int indentLevel = 0) const;
00245
00252 status_t Rename(const String & old_entry, const String & new_entry);
00253
00255 virtual bool IsFixedSize() const {return false;}
00256
00258 virtual uint32 TypeCode() const {return B_MESSAGE_TYPE;}
00259
00261 virtual uint32 FlattenedSize() const;
00262
00268 virtual void Flatten(uint8 *buffer) const;
00269
00278 virtual status_t Unflatten(const uint8 *buf, uint32 size);
00279
00285 status_t AddString(const String & name, const String & val);
00286
00292 status_t AddInt8(const String & name, int8 val);
00293
00299 status_t AddInt16(const String & name, int16 val);
00300
00306 status_t AddInt32(const String & name, int32 val);
00307
00313 status_t AddInt64(const String & name, int64 val);
00314
00320 status_t AddBool(const String & name, bool val);
00321
00327 status_t AddFloat(const String & name, float val);
00328
00334 status_t AddDouble(const String & name, double val);
00335
00344 status_t AddMessage(const String & name, const Message & msg) {return AddMessage(name, GetMessageFromPool(msg));}
00345
00354 status_t AddMessage(const String & name, const MessageRef & msgRef);
00355
00361 status_t AddPointer(const String & name, const void * ptr);
00362
00368 status_t AddPoint(const String & name, const Point & point);
00369
00375 status_t AddRect(const String & name, const Rect & rect);
00376
00383 status_t AddFlat(const String & name, const Flattenable &obj);
00384
00390 status_t AddFlat(const String & name, const FlatCountableRef & ref);
00391
00397 status_t AddFlat(const String & name, const ByteBufferRef & ref)
00398 {
00399 FlatCountableRef fcRef;
00400 fcRef.SetFromGenericUnchecked(ref.GetGeneric());
00401 return AddFlat(name, fcRef);
00402 }
00403
00412 status_t AddTag(const String & name, const GenericRef & tagRef);
00413
00430 status_t AddData(const String & name, uint32 type, const void *data, uint32 numBytes) {return AddDataAux(name, data, numBytes, type, false);}
00431
00437 status_t PrependString(const String & name, const String & val);
00438
00444 status_t PrependInt8(const String & name, int8 val);
00445
00451 status_t PrependInt16(const String & name, int16 val);
00452
00458 status_t PrependInt32(const String & name, int32 val);
00459
00465 status_t PrependInt64(const String & name, int64 val);
00466
00472 status_t PrependBool(const String & name, bool val);
00473
00479 status_t PrependFloat(const String & name, float val);
00480
00486 status_t PrependDouble(const String & name, double val);
00487
00495 status_t PrependMessage(const String & name, const Message & msg) {return PrependMessage(name, GetMessageFromPool(msg));}
00496
00505 status_t PrependMessage(const String & name, const MessageRef & msgRef);
00506
00512 status_t PrependPointer(const String & name, const void * ptr);
00513
00519 status_t PrependPoint(const String & name, const Point & point);
00520
00526 status_t PrependRect(const String & name, const Rect & rect);
00527
00535 status_t PrependFlat(const String & name, const Flattenable &obj);
00536
00542 status_t PrependFlat(const String & name, const FlatCountableRef & flatRef);
00543
00549 status_t PrependFlat(const String & name, const ByteBufferRef & ref)
00550 {
00551 FlatCountableRef fcRef;
00552 fcRef.SetFromGenericUnchecked(ref.GetGeneric());
00553 return PrependFlat(name, fcRef);
00554 }
00555
00564 status_t PrependTag(const String & name, const GenericRef & tagRef);
00565
00582 status_t PrependData(const String & name, uint32 type, const void *data, uint32 numBytes) {return AddDataAux(name, data, numBytes, type, true);}
00583
00590 status_t RemoveData(const String & name, uint32 index = 0);
00591
00596 status_t RemoveName(const String & name);
00597
00602 void Clear(bool releaseCachedBuffers = false) {_entries.Clear(releaseCachedBuffers);}
00603
00610 status_t FindString(const String & name, uint32 index, const String ** setMe) const;
00611
00613 status_t FindString(const String & name, const String ** setMe) const {return FindString(name, 0, setMe);}
00614
00621 status_t FindString(const String & name, uint32 index, const char ** setMe) const;
00622
00624 status_t FindString(const String & name, const char ** setMe) const {return FindString(name, 0, setMe);}
00625
00632 status_t FindString(const String & name, uint32 index, String & setMe) const;
00633
00635 status_t FindString(const String & name, String & setMe) const {return FindString(name, 0, setMe);}
00636
00643 status_t FindInt8(const String & name, uint32 index, int8 *val) const {return FindDataItemAux(name, index, B_INT8_TYPE, val, sizeof(int8));}
00644
00646 status_t FindInt8(const String & name, int8 *value) const {return FindInt8(name, 0, value);}
00647
00654 status_t FindInt16(const String & name, uint32 index, int16 *val) const {return FindDataItemAux(name, index, B_INT16_TYPE, val, sizeof(int16));}
00655
00657 status_t FindInt16(const String & name, int16 *value) const {return FindInt16(name, 0, value);}
00658
00665 status_t FindInt32(const String & name, uint32 index, int32 *val) const {return FindDataItemAux(name, index, B_INT32_TYPE, val, sizeof(int32));}
00666
00668 status_t FindInt32(const String & name, int32 *value) const {return FindInt32(name, 0, value);}
00669
00676 status_t FindInt64(const String & name, uint32 index, int64 *val) const {return FindDataItemAux(name, index, B_INT64_TYPE, val, sizeof(int64));}
00677
00679 status_t FindInt64(const String & name, int64 *value) const {return FindInt64(name, 0, value);}
00680
00687 status_t FindBool(const String & name, uint32 index, bool *val) const {return FindDataItemAux(name, index, B_BOOL_TYPE, val, sizeof(bool));}
00688
00690 status_t FindBool(const String & name, bool *value) const {return FindBool(name, 0, value);}
00691
00698 status_t FindFloat(const String & name, uint32 index, float *val) const {return FindDataItemAux(name, index, B_FLOAT_TYPE, val, sizeof(float));}
00699
00701 status_t FindFloat(const String & name, float *f) const {return FindFloat(name, 0, f);}
00702
00709 status_t FindDouble(const String & name, uint32 index, double * val) const {return FindDataItemAux(name, index, B_DOUBLE_TYPE, val, sizeof(double));}
00710
00712 status_t FindDouble(const String & name, double *d) const {return FindDouble(name, 0, d);}
00713
00722 status_t FindMessage(const String & name, uint32 index, Message &msg) const;
00723
00725 status_t FindMessage(const String & name, Message &msg) const {return FindMessage(name, 0, msg);}
00726
00735 status_t FindMessage(const String & name, uint32 index, MessageRef &msgRef) const;
00736
00738 status_t FindMessage(const String & name, MessageRef &msgRef) const {return FindMessage(name, 0, msgRef);}
00739
00746 status_t FindPointer(const String & name, uint32 index, void ** val) const {return FindDataItemAux(name, index, B_POINTER_TYPE, val, sizeof(void *));}
00747
00749 status_t FindPointer(const String & name, void ** ptr) const {return FindPointer(name, 0, ptr);}
00750
00757 status_t FindPoint(const String & name, uint32 index, Point & point) const;
00758
00760 status_t FindPoint(const String & name, Point & point) const {return FindPoint(name, 0, point);}
00761
00768 status_t FindRect(const String & name, uint32 index, Rect & rect) const;
00769
00771 status_t FindRect(const String & name, Rect & rect) const {return FindRect(name, 0, rect);}
00772
00779 status_t FindFlat(const String & name, uint32 index, Flattenable &obj) const;
00780
00782 status_t FindFlat(const String & name, Flattenable &obj) const {return FindFlat(name, 0, obj);}
00783
00790 status_t FindFlat(const String & name, uint32 index, FlatCountableRef & ref) const;
00791
00793 status_t FindFlat(const String & name, FlatCountableRef &ref) const {return FindFlat(name, 0, ref);}
00794
00798 status_t FindFlat(const String & name, uint32 index, ByteBufferRef & ref) const
00799 {
00800 FlatCountableRef fcRef;
00801 return (FindFlat(name, index, fcRef) == B_NO_ERROR) ? ref.SetFromGeneric(fcRef.GetGeneric()) : B_ERROR;
00802 }
00803
00805 status_t FindFlat(const String & name, ByteBufferRef &ref) const {return FindFlat(name, 0, ref);}
00806
00813 status_t FindTag(const String & name, uint32 index, GenericRef & tagRef) const;
00814
00816 status_t FindTag(const String & name, GenericRef &tagRef) const {return FindTag(name, 0, tagRef);}
00817
00829 status_t FindData(const String & name, uint32 type, uint32 index, const void **data, uint32 *numBytes) const;
00830
00832 status_t FindData(const String & name, uint32 type, const void **data, uint32 *numBytes) const {return FindData(name, type, 0, data, numBytes);}
00833
00839 status_t FindDataPointer(const String & name, uint32 type, uint32 index, void **data, uint32 *numBytes) const;
00840
00842 status_t FindDataPointer(const String & name, uint32 type, void **data, uint32 *numBytes) const {return FindDataPointer(name, type, 0, data, numBytes);}
00843
00851 status_t ReplaceString(bool okayToAdd, const String & name, uint32 index, const String & newString);
00852
00854 status_t ReplaceString(bool okayToAdd, const String & name, const String & newString) {return ReplaceString(okayToAdd, name, 0, newString);}
00855
00863 status_t ReplaceInt8(bool okayToAdd, const String & name, uint32 index, int8 val);
00864
00866 status_t ReplaceInt8(bool okayToAdd, const String & name, int8 val) {return ReplaceInt8(okayToAdd, name, 0, val);}
00867
00875 status_t ReplaceInt16(bool okayToAdd, const String & name, uint32 index, int16 val);
00876
00878 status_t ReplaceInt16(bool okayToAdd, const String & name, int16 val) {return ReplaceInt16(okayToAdd, name, 0, val);}
00879
00887 status_t ReplaceInt32(bool okayToAdd, const String & name, uint32 index, int32 val);
00888
00890 status_t ReplaceInt32(bool okayToAdd, const String & name, int32 val) {return ReplaceInt32(okayToAdd, name, 0, val);}
00891
00899 status_t ReplaceInt64(bool okayToAdd, const String & name, uint32 index, int64 val);
00900
00902 status_t ReplaceInt64(bool okayToAdd, const String & name, int64 val) {return ReplaceInt64(okayToAdd, name, 0, val);}
00903
00911 status_t ReplaceBool(bool okayToAdd, const String & name, uint32 index, bool val);
00912
00914 status_t ReplaceBool(bool okayToAdd, const String & name, bool val) {return ReplaceBool(okayToAdd, name, 0, val);}
00915
00923 status_t ReplaceFloat(bool okayToAdd, const String & name, uint32 index, float val);
00924
00926 status_t ReplaceFloat(bool okayToAdd, const String & name, float val) {return ReplaceFloat(okayToAdd, name, 0, val);}
00927
00935 status_t ReplaceDouble(bool okayToAdd, const String & name, uint32 index, double val);
00936
00938 status_t ReplaceDouble(bool okayToAdd, const String & name, double val) {return ReplaceDouble(okayToAdd, name, 0, val);}
00939
00947 status_t ReplacePointer(bool okayToAdd, const String & name, uint32 index, const void * ptr);
00948
00950 status_t ReplacePointer(bool okayToAdd, const String & name, const void * ptr) {return ReplacePointer(okayToAdd, name, 0, ptr);}
00951
00959 status_t ReplacePoint(bool okayToAdd, const String & name, uint32 index, const Point & point);
00960
00962 status_t ReplacePoint(bool okayToAdd, const String & name, const Point & point) {return ReplacePoint(okayToAdd, name, 0, point);}
00963
00971 status_t ReplaceRect(bool okayToAdd, const String & name, uint32 index, const Rect & rect);
00972
00974 status_t ReplaceRect(bool okayToAdd, const String & name, const Rect & rect) {return ReplaceRect(okayToAdd, name, 0, rect);}
00975
00983 status_t ReplaceMessage(bool okayToAdd, const String & name, uint32 index, const Message &msg) {return ReplaceMessage(okayToAdd, name, index, GetMessageFromPool(msg));}
00984
00986 status_t ReplaceMessage(bool okayToAdd, const String & name, const Message &msg) {return ReplaceMessage(okayToAdd, name, 0, msg);}
00987
00995 status_t ReplaceMessage(bool okayToAdd, const String & name, uint32 index, const MessageRef & msgRef);
00996
00998 status_t ReplaceMessage(bool okayToAdd, const String & name, const MessageRef & msgRef) {return ReplaceMessage(okayToAdd, name, 0, msgRef);}
00999
01007 status_t ReplaceFlat(bool okayToAdd, const String & name, uint32 index, const Flattenable &obj);
01008
01010 status_t ReplaceFlat(bool okayToAdd, const String & name, const Flattenable &obj) {return ReplaceFlat(okayToAdd, name, 0, obj);}
01011
01019 status_t ReplaceFlat(bool okayToAdd, const String & name, uint32 index, const FlatCountableRef & ref);
01020
01022 status_t ReplaceFlat(bool okayToAdd, const String & name, FlatCountableRef &ref) {return ReplaceFlat(okayToAdd, name, 0, ref);}
01023
01025 status_t ReplaceFlat(bool okayToAdd, const String & name, uint32 index, const ByteBufferRef & ref)
01026 {
01027 FlatCountableRef fcRef;
01028 fcRef.SetFromGenericUnchecked(ref.GetGeneric());
01029 return ReplaceFlat(okayToAdd, name, index, fcRef);
01030 }
01031
01033 status_t ReplaceFlat(bool okayToAdd, const String & name, ByteBufferRef &ref) {return ReplaceFlat(okayToAdd, name, 0, ref);}
01034
01042 status_t ReplaceTag(bool okayToAdd, const String & name, uint32 index, const GenericRef & tag);
01043
01045 status_t ReplaceTag(bool okayToAdd, const String & name, const GenericRef & tag) {return ReplaceTag(okayToAdd, name, 0, tag);}
01046
01059 status_t ReplaceData(bool okayToAdd, const String & name, uint32 type, uint32 index, const void *data, uint32 numBytes);
01060
01062 status_t ReplaceData(bool okayToAdd, const String & name, uint32 type, const void *data, uint32 numBytes) {return ReplaceData(okayToAdd, name, type, 0, data, numBytes);}
01063
01070 const String * GetFirstFieldNameString(uint32 optTypeCode = B_ANY_TYPE) const {return GetExtremeFieldNameStringAux(optTypeCode, false);}
01071
01078 const String * GetLastFieldNameString(uint32 optTypeCode = B_ANY_TYPE) const {return GetExtremeFieldNameStringAux(optTypeCode, true);}
01079
01085 bool HasName(const String & fieldName, uint32 type = B_ANY_TYPE) const {return (GetArray(fieldName, type) != NULL);}
01086
01093 uint32 GetNumValuesInName(const String & fieldName, uint32 type = B_ANY_TYPE) const;
01094
01101 status_t MoveName(const String & name, Message &moveTo);
01102
01110 status_t CopyName(const String & name, Message ©To) const;
01111
01117 void SwapContents(Message & swapWith);
01118
01129 uint32 CalculateChecksum(bool countNonFlattenableFields = false) const;
01130
01140 MessageFieldNameIterator GetFieldNameIterator(uint32 type = B_ANY_TYPE, uint32 flags = 0) const {return MessageFieldNameIterator(_entries.GetIterator(flags), type);}
01141
01151 MessageFieldNameIterator GetFieldNameIteratorAt(const String & startFieldName, uint32 type = B_ANY_TYPE, uint32 flags = 0) const {return MessageFieldNameIterator(_entries.GetIteratorAt(startFieldName, flags), type);}
01152
01153 protected:
01155 virtual status_t CopyFromImplementation(const Flattenable & copyFrom);
01156
01157 private:
01158
01159 status_t AddDataAux(const String &name, uint32 type, const void *data, uint32 numBytes, bool prepend);
01160
01161
01162
01163 uint32 GetElementSize(uint32 type) const;
01164
01165 GenericRef GetArrayRef(const String & arrayName, uint32 etc) const;
01166 AbstractDataArray * GetArray(const String & arrayName, uint32 etc) const;
01167 AbstractDataArray * GetOrCreateArray(const String & arrayName, uint32 tc);
01168
01169 status_t AddFlatBuffer(const String & name, const Flattenable & flat, uint32 etc, bool prepend);
01170 status_t AddFlatRef(const String & name, const FlatCountableRef & flat, uint32 etc, bool prepend);
01171 status_t AddDataAux(const String & name, const void * data, uint32 size, uint32 etc, bool prepend);
01172
01173 status_t FindFlatAux(const String & name, uint32 index, Flattenable & flat) const;
01174 status_t FindDataItemAux(const String & name, uint32 index, uint32 tc, void * setValue, uint32 valueSize) const;
01175
01176 status_t ReplaceFlatItemBuffer(bool okayToAdd, const String & name, uint32 index, const Flattenable & flat, uint32 tc);
01177 status_t ReplaceDataAux(bool okayToAdd, const String & name, uint32 index, void * dataBuf, uint32 bufSize, uint32 tc);
01178
01179 bool FieldsAreSubsetOf(const Message & rhs, bool compareData) const;
01180
01181 const String * GetExtremeFieldNameStringAux(uint32 optTypeCode, bool isLast) const
01182 {
01183 return (optTypeCode == B_ANY_TYPE) ? (isLast ? _entries.GetLastKey() : _entries.GetFirstKey())
01184 : MessageFieldNameIterator(*this, optTypeCode, HTIT_FLAG_NOREGISTER|(isLast?HTIT_FLAG_BACKWARDS:0)).GetNextFieldNameString();
01185 }
01186
01187
01188 friend class MessageFieldNameIterator;
01189 Hashtable<String, GenericRef> _entries;
01190 };
01191
01192 inline MessageFieldNameIterator :: MessageFieldNameIterator(const Message & msg, uint32 type, uint32 flags) : HashtableIterator<String, GenericRef>(msg._entries.GetIterator(flags)), _typeCode(type) {}
01193
01194 END_NAMESPACE(muscle);
01195
01196 #endif
01197