From da0f338e876e2a1878343444f9fa9099f7295ac6 Mon Sep 17 00:00:00 2001 From: Michael Lotz Date: Wed, 27 Jun 2007 20:33:51 +0000 Subject: [PATCH] * Ported over a simplified version (no message sending) of the current BMessage implementation to the build libbe * Also ported over the new MessageAdapter class * Removed old BMessage implementation prototypes that apparently were left in the private folder git-svn-id: file:///srv/svn/repos/haiku/haiku/trunk@21515 a95241bf-73f2-0310-859d-f6bbb57e9c96 --- headers/build/os/app/Message.h | 599 ++-- headers/build/private/app/Message2.h | 454 --- headers/build/private/app/Message3.h | 368 --- headers/build/private/app/MessageAdapter.h | 51 + headers/build/private/app/MessageBody.h | 255 -- headers/build/private/app/MessageBody2.h | 87 - headers/build/private/app/MessageBody3.h | 103 - headers/build/private/app/MessageField.h | 791 ----- headers/build/private/app/MessageField2.h | 96 - headers/build/private/app/MessageField3.h | 120 - headers/build/private/app/MessagePrivate.h | 203 +- headers/build/private/app/MessageUtils.h | 262 +- headers/build/private/app/MessageUtils2.h | 222 -- headers/build/private/app/MessageUtils3.h | 230 -- src/build/libbe/app/Jamfile | 3 +- src/build/libbe/app/Message.cpp | 3095 ++++++++++---------- src/build/libbe/app/MessageAdapter.cpp | 705 +++++ src/build/libbe/app/MessageBody.cpp | 412 --- src/build/libbe/app/MessageField.cpp | 50 - src/build/libbe/app/MessageUtils.cpp | 82 +- src/build/libbe/app/Messenger.cpp | 1 + 21 files changed, 2852 insertions(+), 5337 deletions(-) delete mode 100644 headers/build/private/app/Message2.h delete mode 100644 headers/build/private/app/Message3.h create mode 100644 headers/build/private/app/MessageAdapter.h delete mode 100644 headers/build/private/app/MessageBody.h delete mode 100644 headers/build/private/app/MessageBody2.h delete mode 100644 headers/build/private/app/MessageBody3.h delete mode 100644 headers/build/private/app/MessageField.h delete mode 100644 headers/build/private/app/MessageField2.h delete mode 100644 headers/build/private/app/MessageField3.h delete mode 100644 headers/build/private/app/MessageUtils2.h delete mode 100644 headers/build/private/app/MessageUtils3.h create mode 100644 src/build/libbe/app/MessageAdapter.cpp delete mode 100644 src/build/libbe/app/MessageBody.cpp delete mode 100644 src/build/libbe/app/MessageField.cpp diff --git a/headers/build/os/app/Message.h b/headers/build/os/app/Message.h index 11f0d22a29..3055eb6719 100644 --- a/headers/build/os/app/Message.h +++ b/headers/build/os/app/Message.h @@ -1,76 +1,33 @@ -//------------------------------------------------------------------------------ -// Copyright (c) 2001-2002, OpenBeOS -// -// Permission is hereby granted, free of charge, to any person obtaining a -// copy of this software and associated documentation files (the "Software"), -// to deal in the Software without restriction, including without limitation -// the rights to use, copy, modify, merge, publish, distribute, sublicense, -// and/or sell copies of the Software, and to permit persons to whom the -// Software is furnished to do so, subject to the following conditions: -// -// The above copyright notice and this permission notice shall be included in -// all copies or substantial portions of the Software. -// -// THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR -// IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY, -// FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE -// AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER -// LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING -// FROM, OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER -// DEALINGS IN THE SOFTWARE. -// -// File Name: Message.h -// Author(s): Erik Jaesler (erik@cgsoftware.com) -// DarkWyrm -// Description: BMessage class creates objects that store data and that -// can be processed in a message loop. BMessage objects -// are also used as data containers by the archiving and -// the scripting mechanisms. -//------------------------------------------------------------------------------ - +/* + * Copyright 2005-2007, Haiku Inc. All Rights Reserved. + * Distributed under the terms of the MIT License. + * + * Authors: + * Michael Lotz + */ #ifndef _MESSAGE_H #define _MESSAGE_H -// Standard Includes ----------------------------------------------------------- - -// System Includes ------------------------------------------------------------- #include -#include -#include #include #include +#include +#include #include /* For convenience */ #include /* For convenience */ -// Project Includes ------------------------------------------------------------ - -// Local Includes -------------------------------------------------------------- - -// Local Defines --------------------------------------------------------------- - -// Globals --------------------------------------------------------------------- +class BBlockCache; +class BMessenger; +class BHandler; +class BString; - -class BBlockCache; -class BMessenger; -class BHandler; -class BString; - -// Private or reserved --------------------------------------------------------- -extern "C" void _msg_cache_cleanup_(); -extern "C" int _init_message_(); -extern "C" int _delete_message_(); -//------------------------------------------------------------------------------ - - -// Name lengths and Scripting specifiers --------------------------------------- +// Name lengths and Scripting specifiers #define B_FIELD_NAME_LENGTH 255 #define B_PROPERTY_NAME_LENGTH 255 -enum -{ +enum { B_NO_SPECIFIER = 0, B_DIRECT_SPECIFIER = 1, B_INDEX_SPECIFIER, @@ -81,359 +38,245 @@ enum B_ID_SPECIFIER, B_SPECIFIERS_END = 128 - // app-defined specifiers start at B_SPECIFIERS_END+1 + // app-defined specifiers start at B_SPECIFIERS_END + 1 }; -namespace BPrivate { - class BMessageBody; -} +class BMessage { + public: + uint32 what; -// BMessage class -------------------------------------------------------------- -class BMessage -{ -public: - uint32 what; + BMessage(); + BMessage(uint32 what); + BMessage(const BMessage &other); + virtual ~BMessage(); - BMessage(); - BMessage(uint32 what); - BMessage(const BMessage &a_message); -virtual ~BMessage(); + BMessage &operator=(const BMessage &other); - BMessage &operator=(const BMessage &msg); + // Statistics and misc info + status_t GetInfo(type_code typeRequested, int32 index, + char **nameFound, type_code *typeFound, + int32 *countFound = NULL) const; + status_t GetInfo(const char *name, type_code *typeFound, + int32 *countFound = NULL) const; + status_t GetInfo(const char *name, type_code *typeFound, + bool *fixedSize) const; -// Statistics and misc info - status_t GetInfo(type_code typeRequested, int32 which, char **name, - type_code *typeReturned, int32 *count = NULL) const; + int32 CountNames(type_code type) const; + bool IsEmpty() const; + bool IsSystem() const; + bool IsReply() const; + void PrintToStream() const; - status_t GetInfo(const char *name, type_code *type, int32 *c = 0) const; - status_t GetInfo(const char *name, type_code *type, bool *fixed_size) const; + status_t Rename(const char *oldEntry, const char *newEntry); - int32 CountNames(type_code type) const; - bool IsEmpty() const; - bool IsSystem() const; - bool IsReply() const; - void PrintToStream() const; - - status_t Rename(const char *old_entry, const char *new_entry); - -// Delivery info - bool WasDelivered() const; - bool IsSourceWaiting() const; - BMessenger ReturnAddress() const; + // Delivery info + bool WasDelivered() const; + bool IsSourceWaiting() const; + BMessenger ReturnAddress() const; const BMessage *Previous() const; - bool WasDropped() const; - BPoint DropPoint(BPoint *offset = NULL) const; + bool WasDropped() const; + BPoint DropPoint(BPoint *offset = NULL) const; -// Flattening data - ssize_t FlattenedSize() const; - status_t Flatten(char *buffer, ssize_t size) const; - status_t Flatten(BDataIO *stream, ssize_t *size = NULL) const; - status_t Unflatten(const char *flat_buffer); - status_t Unflatten(BDataIO *stream); + // Flattening data + ssize_t FlattenedSize() const; + status_t Flatten(char *buffer, ssize_t size) const; + status_t Flatten(BDataIO *stream, ssize_t *size = NULL) const; + status_t Unflatten(const char *flatBuffer); + status_t Unflatten(BDataIO *stream); + // Specifiers (scripting) + status_t AddSpecifier(const char *property); + status_t AddSpecifier(const char *property, int32 index); + status_t AddSpecifier(const char *property, int32 index, int32 range); + status_t AddSpecifier(const char *property, const char *name); + status_t AddSpecifier(const BMessage *specifier); -// Specifiers (scripting) - status_t AddSpecifier(const char *property); - status_t AddSpecifier(const char *property, int32 index); - status_t AddSpecifier(const char *property, int32 index, int32 range); - status_t AddSpecifier(const char *property, const char *name); - status_t AddSpecifier(const BMessage *specifier); + status_t SetCurrentSpecifier(int32 index); + status_t GetCurrentSpecifier(int32 *index, + BMessage *specifier = NULL, int32 *what = NULL, + const char **property = NULL) const; + bool HasSpecifiers() const; + status_t PopSpecifier(); - status_t SetCurrentSpecifier(int32 index); - status_t GetCurrentSpecifier(int32 *index, BMessage *specifier = NULL, - int32 *form = NULL, const char **property = NULL) const; - bool HasSpecifiers() const; - status_t PopSpecifier(); + // Adding data + status_t AddRect(const char *name, BRect aRect); + status_t AddPoint(const char *name, BPoint aPoint); + status_t AddString(const char *name, const char *aString); + status_t AddString(const char *name, const BString &aString); + status_t AddInt8(const char *name, int8 value); + status_t AddInt16(const char *name, int16 value); + status_t AddInt32(const char *name, int32 value); + status_t AddInt64(const char *name, int64 value); + status_t AddBool(const char *name, bool aBoolean); + status_t AddFloat(const char *name, float aFloat); + status_t AddDouble(const char *name, double aDouble); + status_t AddPointer(const char *name, const void *aPointer); + status_t AddMessenger(const char *name, BMessenger messenger); + status_t AddRef(const char *name, const entry_ref *ref); + status_t AddMessage(const char *name, const BMessage *message); + status_t AddFlat(const char *name, BFlattenable *object, + int32 count = 1); + status_t AddData(const char *name, type_code type, + const void *data, ssize_t numBytes, + bool isFixedSize = true, int32 count = 1); -// Adding data - status_t AddRect(const char *name, BRect a_rect); - status_t AddPoint(const char *name, BPoint a_point); - status_t AddString(const char *name, const char *a_string); - status_t AddString(const char *name, const BString& a_string); - status_t AddInt8(const char *name, int8 val); - status_t AddInt16(const char *name, int16 val); - status_t AddInt32(const char *name, int32 val); - status_t AddInt64(const char *name, int64 val); - status_t AddBool(const char *name, bool a_boolean); - status_t AddFloat(const char *name, float a_float); - status_t AddDouble(const char *name, double a_double); - status_t AddPointer(const char *name, const void *ptr); - status_t AddMessenger(const char *name, BMessenger messenger); - status_t AddRef(const char *name, const entry_ref *ref); - status_t AddMessage(const char *name, const BMessage *msg); - status_t AddFlat(const char *name, BFlattenable *obj, int32 count = 1); - status_t AddData(const char *name, type_code type, const void *data, - ssize_t numBytes, bool is_fixed_size = true, int32 count = 1); + // Removing data + status_t RemoveData(const char *name, int32 index = 0); + status_t RemoveName(const char *name); + status_t MakeEmpty(); -// Removing data - status_t RemoveData(const char *name, int32 index = 0); - status_t RemoveName(const char *name); - status_t MakeEmpty(); - -// Finding data - status_t FindRect(const char *name, BRect *rect) const; - status_t FindRect(const char *name, int32 index, BRect *rect) const; - status_t FindPoint(const char *name, BPoint *pt) const; - status_t FindPoint(const char *name, int32 index, BPoint *pt) const; - status_t FindString(const char *name, const char **str) const; - status_t FindString(const char *name, int32 index, const char **str) const; - status_t FindString(const char *name, BString *str) const; - status_t FindString(const char *name, int32 index, BString *str) const; - status_t FindInt8(const char *name, int8 *value) const; - status_t FindInt8(const char *name, int32 index, int8 *val) const; - status_t FindInt16(const char *name, int16 *value) const; - status_t FindInt16(const char *name, int32 index, int16 *val) const; - status_t FindInt32(const char *name, int32 *value) const; - status_t FindInt32(const char *name, int32 index, int32 *val) const; - status_t FindInt64(const char *name, int64 *value) const; - status_t FindInt64(const char *name, int32 index, int64 *val) const; - status_t FindBool(const char *name, bool *value) const; - status_t FindBool(const char *name, int32 index, bool *value) const; - status_t FindFloat(const char *name, float *f) const; - status_t FindFloat(const char *name, int32 index, float *f) const; - status_t FindDouble(const char *name, double *d) const; - status_t FindDouble(const char *name, int32 index, double *d) const; - status_t FindPointer(const char *name, void **ptr) const; - status_t FindPointer(const char *name, int32 index, void **ptr) const; - status_t FindMessenger(const char *name, BMessenger *m) const; - status_t FindMessenger(const char *name, int32 index, BMessenger *m) const; - status_t FindRef(const char *name, entry_ref *ref) const; - status_t FindRef(const char *name, int32 index, entry_ref *ref) const; - status_t FindMessage(const char *name, BMessage *msg) const; - status_t FindMessage(const char *name, int32 index, BMessage *msg) const; - status_t FindFlat(const char *name, BFlattenable *obj) const; - status_t FindFlat(const char *name, int32 index, BFlattenable *obj) const; - status_t FindData(const char *name, type_code type, + // Finding data + status_t FindRect(const char *name, BRect *rect) const; + status_t FindRect(const char *name, int32 index, BRect *rect) const; + status_t FindPoint(const char *name, BPoint *point) const; + status_t FindPoint(const char *name, int32 index, BPoint *point) const; + status_t FindString(const char *name, const char **string) const; + status_t FindString(const char *name, int32 index, const char **string) const; + status_t FindString(const char *name, BString *string) const; + status_t FindString(const char *name, int32 index, BString *string) const; + status_t FindInt8(const char *name, int8 *value) const; + status_t FindInt8(const char *name, int32 index, int8 *value) const; + status_t FindInt16(const char *name, int16 *value) const; + status_t FindInt16(const char *name, int32 index, int16 *value) const; + status_t FindInt32(const char *name, int32 *value) const; + status_t FindInt32(const char *name, int32 index, int32 *value) const; + status_t FindInt64(const char *name, int64 *value) const; + status_t FindInt64(const char *name, int32 index, int64 *value) const; + status_t FindBool(const char *name, bool *value) const; + status_t FindBool(const char *name, int32 index, bool *value) const; + status_t FindFloat(const char *name, float *value) const; + status_t FindFloat(const char *name, int32 index, float *value) const; + status_t FindDouble(const char *name, double *value) const; + status_t FindDouble(const char *name, int32 index, double *value) const; + status_t FindPointer(const char *name, void **pointer) const; + status_t FindPointer(const char *name, int32 index, void **pointer) const; + status_t FindMessenger(const char *name, BMessenger *messenger) const; + status_t FindMessenger(const char *name, int32 index, BMessenger *messenger) const; + status_t FindRef(const char *name, entry_ref *ref) const; + status_t FindRef(const char *name, int32 index, entry_ref *ref) const; + status_t FindMessage(const char *name, BMessage *message) const; + status_t FindMessage(const char *name, int32 index, BMessage *message) const; + status_t FindFlat(const char *name, BFlattenable *object) const; + status_t FindFlat(const char *name, int32 index, BFlattenable *object) const; + status_t FindData(const char *name, type_code type, const void **data, ssize_t *numBytes) const; - status_t FindData(const char *name, type_code type, int32 index, + status_t FindData(const char *name, type_code type, int32 index, const void **data, ssize_t *numBytes) const; -// Replacing data - status_t ReplaceRect(const char *name, BRect a_rect); - status_t ReplaceRect(const char *name, int32 index, BRect a_rect); - status_t ReplacePoint(const char *name, BPoint a_point); - status_t ReplacePoint(const char *name, int32 index, BPoint a_point); - status_t ReplaceString(const char *name, const char *string); - status_t ReplaceString(const char *name, int32 index, const char *string); - status_t ReplaceString(const char *name, const BString& string); - status_t ReplaceString(const char *name, int32 index, const BString& string); - status_t ReplaceInt8(const char *name, int8 val); - status_t ReplaceInt8(const char *name, int32 index, int8 val); - status_t ReplaceInt16(const char *name, int16 val); - status_t ReplaceInt16(const char *name, int32 index, int16 val); - status_t ReplaceInt32(const char *name, int32 val); - status_t ReplaceInt32(const char *name, int32 index, int32 val); - status_t ReplaceInt64(const char *name, int64 val); - status_t ReplaceInt64(const char *name, int32 index, int64 val); - status_t ReplaceBool(const char *name, bool a_bool); - status_t ReplaceBool(const char *name, int32 index, bool a_bool); - status_t ReplaceFloat(const char *name, float a_float); - status_t ReplaceFloat(const char *name, int32 index, float a_float); - status_t ReplaceDouble(const char *name, double a_double); - status_t ReplaceDouble(const char *name, int32 index, double a_double); - status_t ReplacePointer(const char *name, const void *ptr); - status_t ReplacePointer(const char *name,int32 index,const void *ptr); - status_t ReplaceMessenger(const char *name, BMessenger messenger); - status_t ReplaceMessenger(const char *name, int32 index, BMessenger msngr); - status_t ReplaceRef( const char *name,const entry_ref *ref); - status_t ReplaceRef( const char *name, int32 index, const entry_ref *ref); - status_t ReplaceMessage(const char *name, const BMessage *msg); - status_t ReplaceMessage(const char *name, int32 index, const BMessage *msg); - status_t ReplaceFlat(const char *name, BFlattenable *obj); - status_t ReplaceFlat(const char *name, int32 index, BFlattenable *obj); - status_t ReplaceData(const char *name, type_code type, - const void *data, ssize_t data_size); - status_t ReplaceData(const char *name, type_code type, int32 index, - const void *data, ssize_t data_size); + // Replacing data + status_t ReplaceRect(const char *name, BRect aRect); + status_t ReplaceRect(const char *name, int32 index, BRect aRect); + status_t ReplacePoint(const char *name, BPoint aPoint); + status_t ReplacePoint(const char *name, int32 index, BPoint aPoint); + status_t ReplaceString(const char *name, const char *aString); + status_t ReplaceString(const char *name, int32 index, const char *aString); + status_t ReplaceString(const char *name, const BString &aString); + status_t ReplaceString(const char *name, int32 index, const BString &aString); + status_t ReplaceInt8(const char *name, int8 value); + status_t ReplaceInt8(const char *name, int32 index, int8 value); + status_t ReplaceInt16(const char *name, int16 value); + status_t ReplaceInt16(const char *name, int32 index, int16 value); + status_t ReplaceInt32(const char *name, int32 value); + status_t ReplaceInt32(const char *name, int32 index, int32 value); + status_t ReplaceInt64(const char *name, int64 value); + status_t ReplaceInt64(const char *name, int32 index, int64 value); + status_t ReplaceBool(const char *name, bool aBoolean); + status_t ReplaceBool(const char *name, int32 index, bool aBoolean); + status_t ReplaceFloat(const char *name, float aFloat); + status_t ReplaceFloat(const char *name, int32 index, float aFloat); + status_t ReplaceDouble(const char *name, double aDouble); + status_t ReplaceDouble(const char *name, int32 index, double aDouble); + status_t ReplacePointer(const char *name, const void *pointer); + status_t ReplacePointer(const char *name,int32 index,const void *pointer); + status_t ReplaceMessenger(const char *name, BMessenger messenger); + status_t ReplaceMessenger(const char *name, int32 index, BMessenger messenger); + status_t ReplaceRef( const char *name,const entry_ref *ref); + status_t ReplaceRef( const char *name, int32 index, const entry_ref *ref); + status_t ReplaceMessage(const char *name, const BMessage *message); + status_t ReplaceMessage(const char *name, int32 index, const BMessage *message); + status_t ReplaceFlat(const char *name, BFlattenable *object); + status_t ReplaceFlat(const char *name, int32 index, BFlattenable *object); + status_t ReplaceData(const char *name, type_code type, + const void *data, ssize_t numBytes); + status_t ReplaceData(const char *name, type_code type, int32 index, + const void *data, ssize_t numBytes); - void *operator new(size_t size); - void *operator new(size_t, void* p); - void operator delete(void *ptr, size_t size); + void *operator new(size_t size); + void *operator new(size_t, void *pointer); + void operator delete(void *pointer, size_t size); -// Private, reserved, or obsolete ---------------------------------------------- - bool HasRect(const char *, int32 n = 0) const; - bool HasPoint(const char *, int32 n = 0) const; - bool HasString(const char *, int32 n = 0) const; - bool HasInt8(const char *, int32 n = 0) const; - bool HasInt16(const char *, int32 n = 0) const; - bool HasInt32(const char *, int32 n = 0) const; - bool HasInt64(const char *, int32 n = 0) const; - bool HasBool(const char *, int32 n = 0) const; - bool HasFloat(const char *, int32 n = 0) const; - bool HasDouble(const char *, int32 n = 0) const; - bool HasPointer(const char *, int32 n = 0) const; - bool HasMessenger(const char *, int32 n = 0) const; - bool HasRef(const char *, int32 n = 0) const; - bool HasMessage(const char *, int32 n = 0) const; - bool HasFlat(const char *, const BFlattenable *) const; - bool HasFlat(const char *,int32 ,const BFlattenable *) const; - bool HasData(const char *, type_code , int32 n = 0) const; - BRect FindRect(const char *, int32 n = 0) const; - BPoint FindPoint(const char *, int32 n = 0) const; - const char *FindString(const char *, int32 n = 0) const; - int8 FindInt8(const char *, int32 n = 0) const; - int16 FindInt16(const char *, int32 n = 0) const; - int32 FindInt32(const char *, int32 n = 0) const; - int64 FindInt64(const char *, int32 n = 0) const; - bool FindBool(const char *, int32 n = 0) const; - float FindFloat(const char *, int32 n = 0) const; - double FindDouble(const char *, int32 n = 0) const; + // Private, reserved, or obsolete + bool HasRect(const char *, int32 n = 0) const; + bool HasPoint(const char *, int32 n = 0) const; + bool HasString(const char *, int32 n = 0) const; + bool HasInt8(const char *, int32 n = 0) const; + bool HasInt16(const char *, int32 n = 0) const; + bool HasInt32(const char *, int32 n = 0) const; + bool HasInt64(const char *, int32 n = 0) const; + bool HasBool(const char *, int32 n = 0) const; + bool HasFloat(const char *, int32 n = 0) const; + bool HasDouble(const char *, int32 n = 0) const; + bool HasPointer(const char *, int32 n = 0) const; + bool HasMessenger(const char *, int32 n = 0) const; + bool HasRef(const char *, int32 n = 0) const; + bool HasMessage(const char *, int32 n = 0) const; + bool HasFlat(const char *, const BFlattenable *) const; + bool HasFlat(const char *, int32 n, const BFlattenable *) const; + bool HasData(const char *, type_code , int32 n = 0) const; + BRect FindRect(const char *, int32 n = 0) const; + BPoint FindPoint(const char *, int32 n = 0) const; + const char *FindString(const char *, int32 n = 0) const; + int8 FindInt8(const char *, int32 n = 0) const; + int16 FindInt16(const char *, int32 n = 0) const; + int32 FindInt32(const char *, int32 n = 0) const; + int64 FindInt64(const char *, int32 n = 0) const; + bool FindBool(const char *, int32 n = 0) const; + float FindFloat(const char *, int32 n = 0) const; + double FindDouble(const char *, int32 n = 0) const; class Private; + struct message_header; + struct field_header; -private: - class Header; + private: + friend class Private; + friend class BMessageQueue; -friend class BMessageQueue; -friend class BMessenger; -friend class BApplication; -friend class Header; -friend class Private; + status_t _InitCommon(); + status_t _InitHeader(); + status_t _Clear(); -friend inline void _set_message_target_(BMessage *, int32, bool); -friend inline void _set_message_reply_(BMessage *, BMessenger); -friend inline int32 _get_message_target_(BMessage *); -friend inline bool _use_preferred_target_(BMessage *); + status_t _ResizeData(int32 offset, int32 change); - // deprecated - BMessage(BMessage *a_message); - -virtual void _ReservedMessage1(); -virtual void _ReservedMessage2(); -virtual void _ReservedMessage3(); + uint32 _HashName(const char* name) const; + status_t _FindField(const char* name, type_code type, + field_header** _result) const; + status_t _AddField(const char* name, type_code type, + bool isFixedSize, field_header** _result); + status_t _RemoveField(field_header* field); - void init_data(); - status_t flatten_target_info(BDataIO *stream, - ssize_t size, - uchar flags) const; - status_t real_flatten(char *result, - ssize_t size) const; - status_t real_flatten(BDataIO *stream) const; - char *stack_flatten(char *stack_ptr, - ssize_t stack_size, - bool incl_reply, - ssize_t *size = NULL) const; + ssize_t _NativeFlattenedSize() const; + status_t _NativeFlatten(char *buffer, ssize_t size) const; + status_t _NativeFlatten(BDataIO *stream, ssize_t *size = NULL) const; + void _PrintToStream(const char* indent) const; - ssize_t calc_size(uchar flags) const; - ssize_t calc_hdr_size(uchar flags) const; - status_t nfind_data( const char *name, - type_code type, - int32 index, - const void **data, - ssize_t *data_size) const; - status_t copy_data( const char *name, - type_code type, - int32 index, - void *data, - ssize_t data_size) const; + private: + message_header* fHeader; + field_header* fFields; + uint8* fData; + area_id fClonedArea; -static void _StaticInit(); -static void _StaticCleanup(); -static void _StaticCacheCleanup(); + mutable BMessage* fOriginal; -static BBlockCache *sMsgCache; + BMessage* fQueueLink; + // fQueueLink is used by BMessageQueue to build a linked list - struct dyn_array { - int32 fLogicalBytes; - int32 fPhysicalBytes; - int32 fChunkSize; - int32 fCount; - int32 fEntryHdrSize; - }; + // deprecated + BMessage(BMessage *message); - struct entry_hdr : public dyn_array { - entry_hdr *fNext; - uint32 fType; - uchar fNameLength; - char fName[1]; - }; + static void _StaticCacheCleanup(); - struct var_chunk { - int32 fDataSize; - char fData[1]; - }; - - entry_hdr *entry_find(const char *name, uint32 type,status_t *result=NULL) const; - void entry_remove(entry_hdr *entry); - - void *da_create(int32 header_size, int32 chunk_size, - bool fixed, int32 nchunks); - status_t da_add_data(dyn_array **da, const void *data, int32 size); - void *da_find_data(dyn_array *da, int32 index, - int32 *size = NULL) const; - status_t da_delete_data(dyn_array **pda, int32 index); - status_t da_replace_data(dyn_array **pda, int32 index, - const void *data, int32 dsize); - int32 da_calc_size(int32 hdr_size, int32 chunksize, - bool is_fixed, int32 nchunks) const; - void *da_grow(dyn_array **pda, int32 increase); - void da_dump(dyn_array *da); - - int32 da_chunk_hdr_size() const - { return sizeof(int32); } - int32 da_chunk_size(var_chunk *v) const - { return (v->fDataSize + da_chunk_hdr_size() + 7) & ~7; } - var_chunk *da_first_chunk(dyn_array *da) const - { return (var_chunk *) da_start_of_data(da); } - var_chunk *da_next_chunk(var_chunk *v) const - { return (var_chunk *) (((char*) v) + da_chunk_size(v)); } - var_chunk *da_chunk_ptr(void *data) const - { return (var_chunk*) (((char *) data) - da_chunk_hdr_size()); } - - int32 da_pad_8(int32 val) const - { return (val + 7) & ~7; } - int32 da_total_size(dyn_array *da) const - { return (int32)sizeof(dyn_array) + da->fEntryHdrSize + - da->fPhysicalBytes; } - int32 da_total_logical_size(dyn_array *da) const - { return (int32)sizeof(dyn_array) + da->fEntryHdrSize + - da->fLogicalBytes; } - char *da_start_of_data(dyn_array *da) const - { return ((char *) da) + (sizeof(dyn_array) + - da->fEntryHdrSize); } - bool da_is_mini_data(dyn_array *da) const - { return ((da->fLogicalBytes <= (int32) UCHAR_MAX) && - (da->fCount <= (int32) UCHAR_MAX));} - void da_swap_var_sized(dyn_array *da); - void da_swap_fixed_sized(dyn_array *da); - - BMessage *link; - int32 fTarget; - BMessage *fOriginal; - uint32 fChangeCount; - int32 fCurSpecifier; - uint32 fPtrOffset; - - // ejaesler: Stealing one for my whacky BMessageBody l33tness - uint32 _reserved[2]; - BPrivate::BMessageBody* fBody; - - BMessage::entry_hdr *fEntries; - - struct reply_to_info { - port_id port; - int32 target; - team_id team; - bool preferred; - } fReplyTo; - - bool fPreferred; - bool fReplyRequired; - bool fReplyDone; - bool fIsReply; - bool fWasDelivered; - bool fReadOnly; - bool fHasSpecifiers; + static BBlockCache* sMsgCache; }; -//------------------------------------------------------------------------------ - #endif // _MESSAGE_H - -/* - * $Log $ - * - * $Id $ - * - */ - diff --git a/headers/build/private/app/Message2.h b/headers/build/private/app/Message2.h deleted file mode 100644 index 9a09b23c2c..0000000000 --- a/headers/build/private/app/Message2.h +++ /dev/null @@ -1,454 +0,0 @@ -//------------------------------------------------------------------------------ -// Copyright (c) 2001-2005, Haiku -// -// Permission is hereby granted, free of charge, to any person obtaining a -// copy of this software and associated documentation files (the "Software"), -// to deal in the Software without restriction, including without limitation -// the rights to use, copy, modify, merge, publish, distribute, sublicense, -// and/or sell copies of the Software, and to permit persons to whom the -// Software is furnished to do so, subject to the following conditions: -// -// The above copyright notice and this permission notice shall be included in -// all copies or substantial portions of the Software. -// -// THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR -// IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY, -// FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE -// AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER -// LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING -// FROM, OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER -// DEALINGS IN THE SOFTWARE. -// -// File Name: Message.h -// Author(s): Erik Jaesler (erik@cgsoftware.com) -// DarkWyrm -// Description: BMessage class creates objects that store data and that -// can be processed in a message loop. BMessage objects -// are also used as data containers by the archiving and -// the scripting mechanisms. -//------------------------------------------------------------------------------ - -#ifndef _MESSAGE_H -#define _MESSAGE_H - -#include -#include -#include -#include -#include - -#include /* For convenience */ -#include /* For convenience */ - -class BBlockCache; -class BMessenger; -class BHandler; -class BString; - -// Private or reserved --------------------------------------------------------- -extern "C" void _msg_cache_cleanup_(); -extern "C" int _init_message_(); -extern "C" int _delete_message_(); -//------------------------------------------------------------------------------ - - -// Name lengths and Scripting specifiers --------------------------------------- -#define B_FIELD_NAME_LENGTH 255 -#define B_PROPERTY_NAME_LENGTH 255 - -enum -{ - B_NO_SPECIFIER = 0, - B_DIRECT_SPECIFIER = 1, - B_INDEX_SPECIFIER, - B_REVERSE_INDEX_SPECIFIER, - B_RANGE_SPECIFIER, - B_REVERSE_RANGE_SPECIFIER, - B_NAME_SPECIFIER, - B_ID_SPECIFIER, - - B_SPECIFIERS_END = 128 - // app-defined specifiers start at B_SPECIFIERS_END+1 -}; - -namespace BPrivate { - class BMessageBody; -} - -// BMessage class -------------------------------------------------------------- -class BMessage -{ -public: - uint32 what; - - BMessage(); - BMessage(uint32 what); - BMessage(const BMessage &a_message); -virtual ~BMessage(); - - BMessage &operator=(const BMessage &msg); - -// Statistics and misc info - status_t GetInfo(type_code typeRequested, int32 which, char **name, - type_code *typeReturned, int32 *count = NULL) const; - - status_t GetInfo(const char *name, type_code *type, int32 *c = 0) const; - status_t GetInfo(const char *name, type_code *type, bool *fixed_size) const; - - int32 CountNames(type_code type) const; - bool IsEmpty() const; - bool IsSystem() const; - bool IsReply() const; - void PrintToStream() const; - - status_t Rename(const char *old_entry, const char *new_entry); - -// Delivery info - bool WasDelivered() const; - bool IsSourceWaiting() const; - bool IsSourceRemote() const; - BMessenger ReturnAddress() const; - const BMessage *Previous() const; - bool WasDropped() const; - BPoint DropPoint(BPoint *offset = NULL) const; - -// Replying - status_t SendReply(uint32 command, BHandler *reply_to = NULL); - status_t SendReply(BMessage *the_reply, BHandler *reply_to = NULL, - bigtime_t timeout = B_INFINITE_TIMEOUT); - status_t SendReply(BMessage *the_reply, BMessenger reply_to, - bigtime_t timeout = B_INFINITE_TIMEOUT); - - status_t SendReply(uint32 command, BMessage *reply_to_reply); - status_t SendReply(BMessage *the_reply, BMessage *reply_to_reply, - bigtime_t send_timeout = B_INFINITE_TIMEOUT, - bigtime_t reply_timeout = B_INFINITE_TIMEOUT); - -// Flattening data - ssize_t FlattenedSize() const; - status_t Flatten(char *buffer, ssize_t size) const; - status_t Flatten(BDataIO *stream, ssize_t *size = NULL) const; - status_t Unflatten(const char *flat_buffer); - status_t Unflatten(BDataIO *stream); - - -// Specifiers (scripting) - status_t AddSpecifier(const char *property); - status_t AddSpecifier(const char *property, int32 index); - status_t AddSpecifier(const char *property, int32 index, int32 range); - status_t AddSpecifier(const char *property, const char *name); - status_t AddSpecifier(const BMessage *specifier); - - status_t SetCurrentSpecifier(int32 index); - status_t GetCurrentSpecifier(int32 *index, BMessage *specifier = NULL, - int32 *form = NULL, const char **property = NULL) const; - bool HasSpecifiers() const; - status_t PopSpecifier(); - -// Adding data - status_t AddRect(const char *name, BRect a_rect); - status_t AddPoint(const char *name, BPoint a_point); - status_t AddString(const char *name, const char *a_string); - status_t AddString(const char *name, const BString& a_string); - status_t AddInt8(const char *name, int8 val); - status_t AddInt16(const char *name, int16 val); - status_t AddInt32(const char *name, int32 val); - status_t AddInt64(const char *name, int64 val); - status_t AddBool(const char *name, bool a_boolean); - status_t AddFloat(const char *name, float a_float); - status_t AddDouble(const char *name, double a_double); - status_t AddPointer(const char *name, const void *ptr); - status_t AddMessenger(const char *name, BMessenger messenger); - status_t AddRef(const char *name, const entry_ref *ref); - status_t AddMessage(const char *name, const BMessage *msg); - status_t AddFlat(const char *name, BFlattenable *obj, int32 count = 1); - status_t AddData(const char *name, type_code type, const void *data, - ssize_t numBytes, bool is_fixed_size = true, int32 count = 1); - -// Removing data - status_t RemoveData(const char *name, int32 index = 0); - status_t RemoveName(const char *name); - status_t MakeEmpty(); - -// Finding data - status_t FindRect(const char *name, BRect *rect) const; - status_t FindRect(const char *name, int32 index, BRect *rect) const; - status_t FindPoint(const char *name, BPoint *pt) const; - status_t FindPoint(const char *name, int32 index, BPoint *pt) const; - status_t FindString(const char *name, const char **str) const; - status_t FindString(const char *name, int32 index, const char **str) const; - status_t FindString(const char *name, BString *str) const; - status_t FindString(const char *name, int32 index, BString *str) const; - status_t FindInt8(const char *name, int8 *value) const; - status_t FindInt8(const char *name, int32 index, int8 *val) const; - status_t FindInt16(const char *name, int16 *value) const; - status_t FindInt16(const char *name, int32 index, int16 *val) const; - status_t FindInt32(const char *name, int32 *value) const; - status_t FindInt32(const char *name, int32 index, int32 *val) const; - status_t FindInt64(const char *name, int64 *value) const; - status_t FindInt64(const char *name, int32 index, int64 *val) const; - status_t FindBool(const char *name, bool *value) const; - status_t FindBool(const char *name, int32 index, bool *value) const; - status_t FindFloat(const char *name, float *f) const; - status_t FindFloat(const char *name, int32 index, float *f) const; - status_t FindDouble(const char *name, double *d) const; - status_t FindDouble(const char *name, int32 index, double *d) const; - status_t FindPointer(const char *name, void **ptr) const; - status_t FindPointer(const char *name, int32 index, void **ptr) const; - status_t FindMessenger(const char *name, BMessenger *m) const; - status_t FindMessenger(const char *name, int32 index, BMessenger *m) const; - status_t FindRef(const char *name, entry_ref *ref) const; - status_t FindRef(const char *name, int32 index, entry_ref *ref) const; - status_t FindMessage(const char *name, BMessage *msg) const; - status_t FindMessage(const char *name, int32 index, BMessage *msg) const; - status_t FindFlat(const char *name, BFlattenable *obj) const; - status_t FindFlat(const char *name, int32 index, BFlattenable *obj) const; - status_t FindData(const char *name, type_code type, - const void **data, ssize_t *numBytes) const; - status_t FindData(const char *name, type_code type, int32 index, - const void **data, ssize_t *numBytes) const; - -// Replacing data - status_t ReplaceRect(const char *name, BRect a_rect); - status_t ReplaceRect(const char *name, int32 index, BRect a_rect); - status_t ReplacePoint(const char *name, BPoint a_point); - status_t ReplacePoint(const char *name, int32 index, BPoint a_point); - status_t ReplaceString(const char *name, const char *string); - status_t ReplaceString(const char *name, int32 index, const char *string); - status_t ReplaceString(const char *name, const BString& string); - status_t ReplaceString(const char *name, int32 index, const BString& string); - status_t ReplaceInt8(const char *name, int8 val); - status_t ReplaceInt8(const char *name, int32 index, int8 val); - status_t ReplaceInt16(const char *name, int16 val); - status_t ReplaceInt16(const char *name, int32 index, int16 val); - status_t ReplaceInt32(const char *name, int32 val); - status_t ReplaceInt32(const char *name, int32 index, int32 val); - status_t ReplaceInt64(const char *name, int64 val); - status_t ReplaceInt64(const char *name, int32 index, int64 val); - status_t ReplaceBool(const char *name, bool a_bool); - status_t ReplaceBool(const char *name, int32 index, bool a_bool); - status_t ReplaceFloat(const char *name, float a_float); - status_t ReplaceFloat(const char *name, int32 index, float a_float); - status_t ReplaceDouble(const char *name, double a_double); - status_t ReplaceDouble(const char *name, int32 index, double a_double); - status_t ReplacePointer(const char *name, const void *ptr); - status_t ReplacePointer(const char *name,int32 index,const void *ptr); - status_t ReplaceMessenger(const char *name, BMessenger messenger); - status_t ReplaceMessenger(const char *name, int32 index, BMessenger msngr); - status_t ReplaceRef( const char *name,const entry_ref *ref); - status_t ReplaceRef( const char *name, int32 index, const entry_ref *ref); - status_t ReplaceMessage(const char *name, const BMessage *msg); - status_t ReplaceMessage(const char *name, int32 index, const BMessage *msg); - status_t ReplaceFlat(const char *name, BFlattenable *obj); - status_t ReplaceFlat(const char *name, int32 index, BFlattenable *obj); - status_t ReplaceData(const char *name, type_code type, - const void *data, ssize_t data_size); - status_t ReplaceData(const char *name, type_code type, int32 index, - const void *data, ssize_t data_size); - - void *operator new(size_t size); - void *operator new(size_t, void* p); - void operator delete(void *ptr, size_t size); - -// Private, reserved, or obsolete ---------------------------------------------- - bool HasRect(const char *, int32 n = 0) const; - bool HasPoint(const char *, int32 n = 0) const; - bool HasString(const char *, int32 n = 0) const; - bool HasInt8(const char *, int32 n = 0) const; - bool HasInt16(const char *, int32 n = 0) const; - bool HasInt32(const char *, int32 n = 0) const; - bool HasInt64(const char *, int32 n = 0) const; - bool HasBool(const char *, int32 n = 0) const; - bool HasFloat(const char *, int32 n = 0) const; - bool HasDouble(const char *, int32 n = 0) const; - bool HasPointer(const char *, int32 n = 0) const; - bool HasMessenger(const char *, int32 n = 0) const; - bool HasRef(const char *, int32 n = 0) const; - bool HasMessage(const char *, int32 n = 0) const; - bool HasFlat(const char *, const BFlattenable *) const; - bool HasFlat(const char *,int32 ,const BFlattenable *) const; - bool HasData(const char *, type_code , int32 n = 0) const; - BRect FindRect(const char *, int32 n = 0) const; - BPoint FindPoint(const char *, int32 n = 0) const; - const char *FindString(const char *, int32 n = 0) const; - int8 FindInt8(const char *, int32 n = 0) const; - int16 FindInt16(const char *, int32 n = 0) const; - int32 FindInt32(const char *, int32 n = 0) const; - int64 FindInt64(const char *, int32 n = 0) const; - bool FindBool(const char *, int32 n = 0) const; - float FindFloat(const char *, int32 n = 0) const; - double FindDouble(const char *, int32 n = 0) const; - - class Private; - -private: - class Header; - -friend class BMessageQueue; -friend class BMessenger; -friend class BApplication; -friend class Header; -friend class Private; - -friend inline void _set_message_target_(BMessage *, int32, bool); -friend inline void _set_message_reply_(BMessage *, BMessenger); -friend inline int32 _get_message_target_(BMessage *); -friend inline bool _use_preferred_target_(BMessage *); - - // deprecated - BMessage(BMessage *a_message); - -virtual void _ReservedMessage1(); -virtual void _ReservedMessage2(); -virtual void _ReservedMessage3(); - - void init_data(); - status_t flatten_target_info(BDataIO *stream, - ssize_t size, - uchar flags) const; - status_t real_flatten(char *result, ssize_t size) const; - status_t real_flatten(BDataIO *stream, ssize_t *size) const; - char *stack_flatten(char *stack_ptr, - ssize_t stack_size, - bool incl_reply, - ssize_t *size = NULL) const; - - status_t _UnflattenKMessage(const char *buffer); - - ssize_t calc_size(uchar flags) const; - ssize_t calc_hdr_size(uchar flags) const; - status_t nfind_data( const char *name, - type_code type, - int32 index, - const void **data, - ssize_t *data_size) const; - status_t copy_data( const char *name, - type_code type, - int32 index, - void *data, - ssize_t data_size) const; - - status_t _send_(port_id port, - int32 token, - bool preferred, - bigtime_t timeout, - bool reply_required, - BMessenger &reply_to) const; - status_t send_message(port_id port, - team_id port_owner, - int32 token, - bool preferred, - BMessage *reply, - bigtime_t send_timeout, - bigtime_t reply_timeout) const; -static status_t _SendFlattenedMessage(void *data, int32 size, - port_id port, int32 token, bool preferred, - bigtime_t timeout); - -static void _StaticInit(); -static void _StaticCleanup(); -static void _StaticCacheCleanup(); - - enum { sNumReplyPorts = 3 }; -static port_id sReplyPorts[sNumReplyPorts]; -static long sReplyPortInUse[sNumReplyPorts]; -static int32 sGetCachedReplyPort(); - -static BBlockCache *sMsgCache; - - struct dyn_array { - int32 fLogicalBytes; - int32 fPhysicalBytes; - int32 fChunkSize; - int32 fCount; - int32 fEntryHdrSize; - }; - - struct entry_hdr : public dyn_array { - entry_hdr *fNext; - uint32 fType; - uchar fNameLength; - char fName[1]; - }; - - struct var_chunk { - int32 fDataSize; - char fData[1]; - }; - - entry_hdr *entry_find(const char *name, uint32 type,status_t *result=NULL) const; - void entry_remove(entry_hdr *entry); - - void *da_create(int32 header_size, int32 chunk_size, - bool fixed, int32 nchunks); - status_t da_add_data(dyn_array **da, const void *data, int32 size); - void *da_find_data(dyn_array *da, int32 index, - int32 *size = NULL) const; - status_t da_delete_data(dyn_array **pda, int32 index); - status_t da_replace_data(dyn_array **pda, int32 index, - const void *data, int32 dsize); - int32 da_calc_size(int32 hdr_size, int32 chunksize, - bool is_fixed, int32 nchunks) const; - void *da_grow(dyn_array **pda, int32 increase); - void da_dump(dyn_array *da); - - int32 da_chunk_hdr_size() const - { return sizeof(int32); } - int32 da_chunk_size(var_chunk *v) const - { return (v->fDataSize + da_chunk_hdr_size() + 7) & ~7; } - var_chunk *da_first_chunk(dyn_array *da) const - { return (var_chunk *) da_start_of_data(da); } - var_chunk *da_next_chunk(var_chunk *v) const - { return (var_chunk *) (((char*) v) + da_chunk_size(v)); } - var_chunk *da_chunk_ptr(void *data) const - { return (var_chunk*) (((char *) data) - da_chunk_hdr_size()); } - - int32 da_pad_8(int32 val) const - { return (val + 7) & ~7; } - int32 da_total_size(dyn_array *da) const - { return (int32)sizeof(dyn_array) + da->fEntryHdrSize + - da->fPhysicalBytes; } - int32 da_total_logical_size(dyn_array *da) const - { return (int32)sizeof(dyn_array) + da->fEntryHdrSize + - da->fLogicalBytes; } - char *da_start_of_data(dyn_array *da) const - { return ((char *) da) + (sizeof(dyn_array) + - da->fEntryHdrSize); } - bool da_is_mini_data(dyn_array *da) const - { return ((da->fLogicalBytes <= (int32) UCHAR_MAX) && - (da->fCount <= (int32) UCHAR_MAX));} - void da_swap_var_sized(dyn_array *da); - void da_swap_fixed_sized(dyn_array *da); - - BMessage *link; - int32 fTarget; - BMessage *fOriginal; - uint32 fChangeCount; - int32 fCurSpecifier; - uint32 fPtrOffset; - - // ejaesler: Stealing one for my whacky BMessageBody l33tness - uint32 _reserved[2]; - BPrivate::BMessageBody* fBody; - - BMessage::entry_hdr *fEntries; - - struct reply_to_info { - port_id port; - int32 target; - team_id team; - bool preferred; - } fReplyTo; - - bool fPreferred; - bool fReplyRequired; - bool fReplyDone; - bool fIsReply; - bool fWasDelivered; - bool fReadOnly; - bool fHasSpecifiers; -}; - -//------------------------------------------------------------------------------ - -#endif // _MESSAGE_H diff --git a/headers/build/private/app/Message3.h b/headers/build/private/app/Message3.h deleted file mode 100644 index 1a6eb476f0..0000000000 --- a/headers/build/private/app/Message3.h +++ /dev/null @@ -1,368 +0,0 @@ -//------------------------------------------------------------------------------ -// Copyright (c) 2001-2005, Haiku -// -// Permission is hereby granted, free of charge, to any person obtaining a -// copy of this software and associated documentation files (the "Software"), -// to deal in the Software without restriction, including without limitation -// the rights to use, copy, modify, merge, publish, distribute, sublicense, -// and/or sell copies of the Software, and to permit persons to whom the -// Software is furnished to do so, subject to the following conditions: -// -// The above copyright notice and this permission notice shall be included in -// all copies or substantial portions of the Software. -// -// THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR -// IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY, -// FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE -// AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER -// LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING -// FROM, OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER -// DEALINGS IN THE SOFTWARE. -// -// File Name: Message.h -// Author(s): Erik Jaesler (erik@cgsoftware.com) -// DarkWyrm -// Description: BMessage class creates objects that store data and that -// can be processed in a message loop. BMessage objects -// are also used as data containers by the archiving and -// the scripting mechanisms. -//------------------------------------------------------------------------------ - -#ifndef _MESSAGE_H -#define _MESSAGE_H - -#include -#include -#include -#include -#include - -#include /* For convenience */ -#include /* For convenience */ - -class BBlockCache; -class BMessenger; -class BHandler; -class BString; - -// Private or reserved --------------------------------------------------------- -extern "C" void _msg_cache_cleanup_(); -extern "C" int _init_message_(); -extern "C" int _delete_message_(); -//------------------------------------------------------------------------------ - - -// Name lengths and Scripting specifiers --------------------------------------- -#define B_FIELD_NAME_LENGTH 255 -#define B_PROPERTY_NAME_LENGTH 255 - -enum -{ - B_NO_SPECIFIER = 0, - B_DIRECT_SPECIFIER = 1, - B_INDEX_SPECIFIER, - B_REVERSE_INDEX_SPECIFIER, - B_RANGE_SPECIFIER, - B_REVERSE_RANGE_SPECIFIER, - B_NAME_SPECIFIER, - B_ID_SPECIFIER, - - B_SPECIFIERS_END = 128 - // app-defined specifiers start at B_SPECIFIERS_END + 1 -}; - -namespace BPrivate { - class BMessageBody; -} - -// BMessage class -------------------------------------------------------------- -class BMessage -{ -public: - uint32 what; - - BMessage(); - BMessage(uint32 what); - BMessage(const BMessage &a_message); -virtual ~BMessage(); - - BMessage &operator=(const BMessage &msg); - -// Statistics and misc info - status_t GetInfo(type_code typeRequested, int32 which, char **name, - type_code *typeReturned, int32 *count = NULL) const; - - status_t GetInfo(const char *name, type_code *type, int32 *c = 0) const; - status_t GetInfo(const char *name, type_code *type, bool *fixed_size) const; - - int32 CountNames(type_code type) const; - bool IsEmpty() const; - bool IsSystem() const; - bool IsReply() const; - void PrintToStream() const; - - status_t Rename(const char *old_entry, const char *new_entry); - -// Delivery info - bool WasDelivered() const; - bool IsSourceWaiting() const; - bool IsSourceRemote() const; - BMessenger ReturnAddress() const; - const BMessage *Previous() const; - bool WasDropped() const; - BPoint DropPoint(BPoint *offset = NULL) const; - -// Replying - status_t SendReply(uint32 command, BHandler *reply_to = NULL); - status_t SendReply(BMessage *the_reply, BHandler *reply_to = NULL, - bigtime_t timeout = B_INFINITE_TIMEOUT); - status_t SendReply(BMessage *the_reply, BMessenger reply_to, - bigtime_t timeout = B_INFINITE_TIMEOUT); - - status_t SendReply(uint32 command, BMessage *reply_to_reply); - status_t SendReply(BMessage *the_reply, BMessage *reply_to_reply, - bigtime_t send_timeout = B_INFINITE_TIMEOUT, - bigtime_t reply_timeout = B_INFINITE_TIMEOUT); - -// Flattening data - ssize_t FlattenedSize() const; - status_t Flatten(char *buffer, ssize_t size) const; - status_t Flatten(BDataIO *stream, ssize_t *size = NULL) const; - status_t Unflatten(const char *flat_buffer); - status_t Unflatten(BDataIO *stream); - - -// Specifiers (scripting) - status_t AddSpecifier(const char *property); - status_t AddSpecifier(const char *property, int32 index); - status_t AddSpecifier(const char *property, int32 index, int32 range); - status_t AddSpecifier(const char *property, const char *name); - status_t AddSpecifier(const BMessage *specifier); - - status_t SetCurrentSpecifier(int32 index); - status_t GetCurrentSpecifier(int32 *index, BMessage *specifier = NULL, - int32 *form = NULL, const char **property = NULL) const; - bool HasSpecifiers() const; - status_t PopSpecifier(); - -// Adding data - status_t AddRect(const char *name, BRect a_rect); - status_t AddPoint(const char *name, BPoint a_point); - status_t AddString(const char *name, const char *a_string); - status_t AddString(const char *name, const BString& a_string); - status_t AddInt8(const char *name, int8 val); - status_t AddInt16(const char *name, int16 val); - status_t AddInt32(const char *name, int32 val); - status_t AddInt64(const char *name, int64 val); - status_t AddBool(const char *name, bool a_boolean); - status_t AddFloat(const char *name, float a_float); - status_t AddDouble(const char *name, double a_double); - status_t AddPointer(const char *name, const void *ptr); - status_t AddMessenger(const char *name, BMessenger messenger); - status_t AddRef(const char *name, const entry_ref *ref); - status_t AddMessage(const char *name, const BMessage *msg); - status_t AddFlat(const char *name, BFlattenable *obj, int32 count = 1); - status_t AddData(const char *name, type_code type, const void *data, - ssize_t numBytes, bool is_fixed_size = true, int32 count = 1); - -// Removing data - status_t RemoveData(const char *name, int32 index = 0); - status_t RemoveName(const char *name); - status_t MakeEmpty(); - -// Finding data - status_t FindRect(const char *name, BRect *rect) const; - status_t FindRect(const char *name, int32 index, BRect *rect) const; - status_t FindPoint(const char *name, BPoint *pt) const; - status_t FindPoint(const char *name, int32 index, BPoint *pt) const; - status_t FindString(const char *name, const char **str) const; - status_t FindString(const char *name, int32 index, const char **str) const; - status_t FindString(const char *name, BString *str) const; - status_t FindString(const char *name, int32 index, BString *str) const; - status_t FindInt8(const char *name, int8 *value) const; - status_t FindInt8(const char *name, int32 index, int8 *val) const; - status_t FindInt16(const char *name, int16 *value) const; - status_t FindInt16(const char *name, int32 index, int16 *val) const; - status_t FindInt32(const char *name, int32 *value) const; - status_t FindInt32(const char *name, int32 index, int32 *val) const; - status_t FindInt64(const char *name, int64 *value) const; - status_t FindInt64(const char *name, int32 index, int64 *val) const; - status_t FindBool(const char *name, bool *value) const; - status_t FindBool(const char *name, int32 index, bool *value) const; - status_t FindFloat(const char *name, float *f) const; - status_t FindFloat(const char *name, int32 index, float *f) const; - status_t FindDouble(const char *name, double *d) const; - status_t FindDouble(const char *name, int32 index, double *d) const; - status_t FindPointer(const char *name, void **ptr) const; - status_t FindPointer(const char *name, int32 index, void **ptr) const; - status_t FindMessenger(const char *name, BMessenger *m) const; - status_t FindMessenger(const char *name, int32 index, BMessenger *m) const; - status_t FindRef(const char *name, entry_ref *ref) const; - status_t FindRef(const char *name, int32 index, entry_ref *ref) const; - status_t FindMessage(const char *name, BMessage *msg) const; - status_t FindMessage(const char *name, int32 index, BMessage *msg) const; - status_t FindFlat(const char *name, BFlattenable *obj) const; - status_t FindFlat(const char *name, int32 index, BFlattenable *obj) const; - status_t FindData(const char *name, type_code type, - const void **data, ssize_t *numBytes) const; - status_t FindData(const char *name, type_code type, int32 index, - const void **data, ssize_t *numBytes) const; - -// Replacing data - status_t ReplaceRect(const char *name, BRect a_rect); - status_t ReplaceRect(const char *name, int32 index, BRect a_rect); - status_t ReplacePoint(const char *name, BPoint a_point); - status_t ReplacePoint(const char *name, int32 index, BPoint a_point); - status_t ReplaceString(const char *name, const char *string); - status_t ReplaceString(const char *name, int32 index, const char *string); - status_t ReplaceString(const char *name, const BString& string); - status_t ReplaceString(const char *name, int32 index, const BString& string); - status_t ReplaceInt8(const char *name, int8 val); - status_t ReplaceInt8(const char *name, int32 index, int8 val); - status_t ReplaceInt16(const char *name, int16 val); - status_t ReplaceInt16(const char *name, int32 index, int16 val); - status_t ReplaceInt32(const char *name, int32 val); - status_t ReplaceInt32(const char *name, int32 index, int32 val); - status_t ReplaceInt64(const char *name, int64 val); - status_t ReplaceInt64(const char *name, int32 index, int64 val); - status_t ReplaceBool(const char *name, bool a_bool); - status_t ReplaceBool(const char *name, int32 index, bool a_bool); - status_t ReplaceFloat(const char *name, float a_float); - status_t ReplaceFloat(const char *name, int32 index, float a_float); - status_t ReplaceDouble(const char *name, double a_double); - status_t ReplaceDouble(const char *name, int32 index, double a_double); - status_t ReplacePointer(const char *name, const void *ptr); - status_t ReplacePointer(const char *name,int32 index,const void *ptr); - status_t ReplaceMessenger(const char *name, BMessenger messenger); - status_t ReplaceMessenger(const char *name, int32 index, BMessenger msngr); - status_t ReplaceRef( const char *name,const entry_ref *ref); - status_t ReplaceRef( const char *name, int32 index, const entry_ref *ref); - status_t ReplaceMessage(const char *name, const BMessage *msg); - status_t ReplaceMessage(const char *name, int32 index, const BMessage *msg); - status_t ReplaceFlat(const char *name, BFlattenable *obj); - status_t ReplaceFlat(const char *name, int32 index, BFlattenable *obj); - status_t ReplaceData(const char *name, type_code type, - const void *data, ssize_t data_size); - status_t ReplaceData(const char *name, type_code type, int32 index, - const void *data, ssize_t data_size); - - void *operator new(size_t size); - void *operator new(size_t, void* p); - void operator delete(void *ptr, size_t size); - -// Private, reserved, or obsolete ---------------------------------------------- - bool HasRect(const char *, int32 n = 0) const; - bool HasPoint(const char *, int32 n = 0) const; - bool HasString(const char *, int32 n = 0) const; - bool HasInt8(const char *, int32 n = 0) const; - bool HasInt16(const char *, int32 n = 0) const; - bool HasInt32(const char *, int32 n = 0) const; - bool HasInt64(const char *, int32 n = 0) const; - bool HasBool(const char *, int32 n = 0) const; - bool HasFloat(const char *, int32 n = 0) const; - bool HasDouble(const char *, int32 n = 0) const; - bool HasPointer(const char *, int32 n = 0) const; - bool HasMessenger(const char *, int32 n = 0) const; - bool HasRef(const char *, int32 n = 0) const; - bool HasMessage(const char *, int32 n = 0) const; - bool HasFlat(const char *, const BFlattenable *) const; - bool HasFlat(const char *,int32 ,const BFlattenable *) const; - bool HasData(const char *, type_code , int32 n = 0) const; - BRect FindRect(const char *, int32 n = 0) const; - BPoint FindPoint(const char *, int32 n = 0) const; - const char *FindString(const char *, int32 n = 0) const; - int8 FindInt8(const char *, int32 n = 0) const; - int16 FindInt16(const char *, int32 n = 0) const; - int32 FindInt32(const char *, int32 n = 0) const; - int64 FindInt64(const char *, int32 n = 0) const; - bool FindBool(const char *, int32 n = 0) const; - float FindFloat(const char *, int32 n = 0) const; - double FindDouble(const char *, int32 n = 0) const; - - class Private; - -private: - class Header; - -friend class BMessageQueue; -friend class BMessenger; -friend class BApplication; -friend class Header; -friend class Private; - -friend inline void _set_message_target_(BMessage *, int32, bool); -friend inline void _set_message_reply_(BMessage *, BMessenger); -friend inline int32 _get_message_target_(BMessage *); -friend inline bool _use_preferred_target_(BMessage *); - - // deprecated - BMessage(BMessage *a_message); - -virtual void _ReservedMessage1(); -virtual void _ReservedMessage2(); -virtual void _ReservedMessage3(); - - void init_data(); - status_t real_flatten(char *result, ssize_t size) const; - status_t real_flatten(BDataIO *stream, ssize_t *size) const; - char *stack_flatten(char *stack_ptr, - ssize_t stack_size, bool incl_reply, - ssize_t *size = NULL) const; - - status_t _UnflattenKMessage(const char *buffer); - - ssize_t calc_hdr_size() const; - - status_t _send_(port_id port, int32 token, - bool preferred, bigtime_t timeout, - bool reply_required, - BMessenger &reply_to) const; - status_t send_message(port_id port, team_id port_owner, - int32 token, bool preferred, - BMessage *reply, - bigtime_t send_timeout, - bigtime_t reply_timeout) const; - -static status_t _SendFlattenedMessage(void *data, int32 size, - port_id port, int32 token, bool preferred, - bigtime_t timeout); - -static void _StaticInit(); -static void _StaticCleanup(); -static void _StaticCacheCleanup(); - - enum { sNumReplyPorts = 3 }; -static port_id sReplyPorts[sNumReplyPorts]; -static long sReplyPortInUse[sNumReplyPorts]; -static int32 sGetCachedReplyPort(); - -static BBlockCache *sMsgCache; - - BMessage *fUnused1; - int32 fTarget; - BMessage *fOriginal; - uint32 fUnused2; - int32 fCurSpecifier; - uint32 fReserved[4]; - - BPrivate::BMessageBody *fBody; - - struct reply_to_info { - port_id port; - int32 target; - team_id team; - bool preferred; - } fReplyTo; - - bool fPreferred; - bool fReplyRequired; - bool fReplyDone; - bool fIsReply; - bool fWasDelivered; - bool fReadOnly; - bool fHasSpecifiers; -}; - -//------------------------------------------------------------------------------ - -#endif // _MESSAGE_H diff --git a/headers/build/private/app/MessageAdapter.h b/headers/build/private/app/MessageAdapter.h new file mode 100644 index 0000000000..3ce06446ea --- /dev/null +++ b/headers/build/private/app/MessageAdapter.h @@ -0,0 +1,51 @@ +/* + * Copyright 2007, Haiku Inc. All rights reserved. + * Distributed under the terms of the MIT License. + * + * Authors: + * Michael Lotz + */ +#ifndef _MESSAGE_ADAPTER_H_ +#define _MESSAGE_ADAPTER_H_ + +#include + +// message formats +#define MESSAGE_FORMAT_R5 'FOB1' +#define MESSAGE_FORMAT_R5_SWAPPED '1BOF' +#define MESSAGE_FORMAT_DANO 'FOB2' +#define MESSAGE_FORMAT_DANO_SWAPPED '2BOF' +#define MESSAGE_FORMAT_HAIKU '1FMH' +#define MESSAGE_FORMAT_HAIKU_SWAPPED 'HMF1' + +namespace BPrivate { + +class MessageAdapter { +public: +static ssize_t FlattenedSize(uint32 format, const BMessage *from); + +static status_t Flatten(uint32 format, const BMessage *from, + char *buffer, ssize_t *size); +static status_t Flatten(uint32 format, const BMessage *from, + BDataIO *stream, ssize_t *size); + +static status_t Unflatten(uint32 format, BMessage *into, + const char *buffer); +static status_t Unflatten(uint32 format, BMessage *into, + BDataIO *stream); + +private: +static ssize_t _R5FlattenedSize(const BMessage *from); + +static status_t _FlattenR5Message(uint32 format, const BMessage *from, + char *buffer, ssize_t *size); + +static status_t _UnflattenR5Message(uint32 format, BMessage *into, + BDataIO *stream); +static status_t _UnflattenDanoMessage(uint32 format, BMessage *into, + BDataIO *stream); +}; + +} // namespace BPrivate + +#endif // _MESSAGE_ADAPTER_H_ diff --git a/headers/build/private/app/MessageBody.h b/headers/build/private/app/MessageBody.h deleted file mode 100644 index e5a88b68c3..0000000000 --- a/headers/build/private/app/MessageBody.h +++ /dev/null @@ -1,255 +0,0 @@ -//------------------------------------------------------------------------------ -// Copyright (c) 2001-2002, OpenBeOS -// -// Permission is hereby granted, free of charge, to any person obtaining a -// copy of this software and associated documentation files (the "Software"), -// to deal in the Software without restriction, including without limitation -// the rights to use, copy, modify, merge, publish, distribute, sublicense, -// and/or sell copies of the Software, and to permit persons to whom the -// Software is furnished to do so, subject to the following conditions: -// -// The above copyright notice and this permission notice shall be included in -// all copies or substantial portions of the Software. -// -// THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR -// IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY, -// FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE -// AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER -// LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING -// FROM, OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER -// DEALINGS IN THE SOFTWARE. -// -// File Name: MessageBody.h -// Author(s): Erik Jaesler (erik@cgsoftware.com) -// Description: BMessageBody handles data storage and retrieval for -// BMessage. -//------------------------------------------------------------------------------ - -#ifndef MESSAGEBODY_H -#define MESSAGEBODY_H -#include -// Standard Includes ----------------------------------------------------------- -#include -#include -#include - -// System Includes ------------------------------------------------------------- -#include -#include -#include -#include -//#include -#include -#include - -// Project Includes ------------------------------------------------------------ - -// Local Includes -------------------------------------------------------------- - -// Local Defines --------------------------------------------------------------- - -// Globals --------------------------------------------------------------------- - -using namespace std; - -enum { B_FLATTENABLE_TYPE = 'FLAT' }; - -namespace BPrivate { - -class BMessageBody -{ -public: - BMessageBody(); - BMessageBody(const BMessageBody& rhs); - ~BMessageBody(); - - BMessageBody& operator=(const BMessageBody& rhs); - -// Statistics and misc info - status_t GetInfo(type_code typeRequested, int32 which, char **name, - type_code *typeReturned, int32 *count = NULL) const; - - status_t GetInfo(const char *name, type_code *type, int32 *c = 0) const; - status_t GetInfo(const char *name, type_code *type, bool *fixed_size) const; - - int32 CountNames(type_code type) const; - bool IsEmpty() const; - bool IsSystem() const; - bool IsReply() const; - void PrintToStream() const; - - status_t Rename(const char *old_entry, const char *new_entry); - -// Flattening data - ssize_t FlattenedSize() const; - status_t Flatten(BDataIO *stream) const; - -// Removing data - status_t RemoveData(const char *name, int32 index = 0); - status_t RemoveName(const char *name); - status_t MakeEmpty(); - - bool HasData(const char* name, type_code t, int32 n) const; - - template - status_t AddData(const char* name, const T1& data, type_code type); - status_t AddData(const char* name, type_code type, const void* data, ssize_t numBytes, bool is_fixed_size, int32); - status_t FindData(const char* name, type_code type, int32 index, - const void** data, ssize_t* numBytes) const; - template - status_t FindData(const char* name, int32 index, T1* data, type_code type); - template - status_t ReplaceData(const char* name, int32 index, const T1& data, type_code type); - -#if 0 - void *operator new(size_t size); - void operator delete(void *ptr, size_t size); -#endif - -private: - BMessageField* FindData(const char *name, type_code type, - status_t& err) const; - - typedef std::map TMsgDataMap; - TMsgDataMap fData; - ssize_t fFlattenedSize; -}; -//------------------------------------------------------------------------------ -template -status_t BMessageBody::AddData(const char *name, const T1 &data, type_code type) -{ - // The flattened message format in R5 only allows 1 byte - // for the length of field names - if (!name || (strlen(name) > 255)) return B_BAD_VALUE; - - status_t err = B_OK; - BMessageField* BMF = FindData(name, type, err); - - if (err) - { - if (err == B_NAME_NOT_FOUND) - { - // Reset err; we'll create the field - err = B_OK; - } - else - { - // Looking for B_BAD_TYPE here in particular, which would indicate - // that we tried to add data of type X when we already had data of - // type Y with the same name - return err; - } - } - - if (!BMF) - { - BMF = new(nothrow) BMessageFieldImpl(name, type); - if (BMF) - { - fData[name] = BMF; - } - else - { - err = B_NO_MEMORY; - } - } - - if (!err) - { - BMessageFieldImpl* RItem = - dynamic_cast*>(BMF); - if (!RItem) - { - debugger("\n\n\tyou \033[44;1;37mB\033[41;1;37me\033[m screwed\n\n"); - } - RItem->AddItem(data); - } - - return err; -} -//------------------------------------------------------------------------------ -template -status_t BMessageBody::FindData(const char *name, int32 index, T1 *data, - type_code type) -{ - if (!name) - { - return B_BAD_VALUE; - } - if (index < 0) - { - return B_BAD_INDEX; - } - - status_t err = B_OK; - BMessageField* Item = FindData(name, type, err); - if (Item) - { - BMessageFieldImpl* RItem = - dynamic_cast*>(Item); - if (!RItem) - { - debugger("\n\n\tyou \033[44;1;37mB\033[41;1;37me" - "\033[m screwed\n\n"); - } - if (index < RItem->CountItems()) - { - *data = RItem->Data()[index]; - } - else - { - err = B_BAD_INDEX; - } - } - - return err; -} -//------------------------------------------------------------------------------ -template -status_t BMessageBody::ReplaceData(const char *name, int32 index, - const T1 &data, type_code type) -{ - if (!name) - { - return B_BAD_VALUE; - } - if (index < 0) - { - return B_BAD_INDEX; - } - - status_t err = B_OK; - BMessageField* Item = FindData(name, type, err); - if (Item) - { - BMessageFieldImpl* RItem = - dynamic_cast*>(Item); - if (!RItem) - { - debugger("\n\n\tyou \033[44;1;37mB\033[41;1;37me\033[m screwed\n\n"); - } - if (index < (int32)RItem->Data().Size()) - { - RItem->Data()[index] = data; - } - else - { - err = B_BAD_INDEX; - } - } - - return err; -} -//------------------------------------------------------------------------------ - -} // namespace BPrivate - -#endif //MESSAGEBODY_H - -/* - * $Log $ - * - * $Id $ - * - */ - diff --git a/headers/build/private/app/MessageBody2.h b/headers/build/private/app/MessageBody2.h deleted file mode 100644 index 354c1cf9a1..0000000000 --- a/headers/build/private/app/MessageBody2.h +++ /dev/null @@ -1,87 +0,0 @@ -/* - * Copyright 2005, Haiku. - * Distributed under the terms of the MIT License. - * - * Authors: - * Michael Lotz - */ - -/* BMessageBody handles data storage and retrieval for BMessage. */ - -#ifndef _MESSAGE_BODY_H_ -#define _MESSAGE_BODY_H_ - -#include -#include "MessageField2.h" - -enum { - B_FLATTENABLE_TYPE = 'FLAT' -}; - -namespace BPrivate { - -class BMessageBody { -public: - BMessageBody(); - BMessageBody(const BMessageBody &other); - ~BMessageBody(); - - BMessageBody &operator=(const BMessageBody &other); - - status_t GetInfo(type_code typeRequested, int32 which, - char **name, type_code *typeFound, - int32 *countFound = NULL) const; - status_t GetInfo(const char *name, type_code *typeFound, - int32 *countFound = NULL) const; - status_t GetInfo(const char *name, type_code *typeFound, - bool *fixedSize) const; - - int32 CountNames(type_code type) const; - bool IsEmpty() const; - - ssize_t FlattenedSize() const; - status_t Flatten(BDataIO *stream) const; - status_t Unflatten(BDataIO *stream); - - status_t AddData(const char *name, type_code type, - size_t length, void **buffer, - bool fixedSize = false, int32 count = 1); - status_t RemoveData(const char *name, int32 index = 0); - - bool HasData(const char *name, type_code t, int32 n) const; - status_t FindData(const char *name, type_code type, - int32 index, const void **data, - ssize_t *numBytes) const; - status_t ReplaceData(const char *name, type_code type, - int32 index, size_t length, void **buffer); - - status_t Rename(const char *oldName, const char *newName); - status_t RemoveName(const char *name); - status_t MakeEmpty(); - - void PrintToStream() const; - - // hash table support - void HashInsert(BMessageField *field); - BMessageField *HashLookup(const char *name) const; - BMessageField *HashRemove(const char *name); - uint32 HashString(const char *string) const; - void HashClear(); - -private: - status_t InitCommon(); - BMessageField *AddField(const char *name, type_code type, - status_t &error); - BMessageField *FindData(const char *name, type_code type, - status_t &error) const; - - BList fFieldList; - BMessageField **fFieldTable; - int32 fFieldTableSize; - -mutable ssize_t fFlattenedSize; -}; - -} // namespace BPrivate - -#endif // _MESSAGE_BODY_H_ diff --git a/headers/build/private/app/MessageBody3.h b/headers/build/private/app/MessageBody3.h deleted file mode 100644 index c5e61d08d3..0000000000 --- a/headers/build/private/app/MessageBody3.h +++ /dev/null @@ -1,103 +0,0 @@ -/* - * Copyright 2005, Haiku. - * Distributed under the terms of the MIT License. - * - * Authors: - * Michael Lotz - */ - -/* BMessageBody handles data storage and retrieval for BMessage. */ - -#ifndef _MESSAGE_BODY_H_ -#define _MESSAGE_BODY_H_ - -#include - -enum { - B_FLATTENABLE_TYPE = 'FLAT' -}; - -namespace BPrivate { - -class BMessageField; - -class BMessageBody { -public: - BMessageBody(); - BMessageBody(const BMessageBody &other); - ~BMessageBody(); - - BMessageBody &operator=(const BMessageBody &other); - - status_t GetInfo(type_code typeRequested, int32 which, - char **name, type_code *typeFound, - int32 *countFound = NULL) const; - status_t GetInfo(const char *name, type_code *typeFound, - int32 *countFound = NULL) const; - status_t GetInfo(const char *name, type_code *typeFound, - bool *fixedSize) const; - - int32 CountNames(type_code type) const; - bool IsEmpty() const; - - ssize_t FlattenedSize() const; - status_t Flatten(BDataIO *stream) const; - status_t Unflatten(BDataIO *stream, int32 length); - - status_t AddData(const char *name, type_code type, - const void *item, ssize_t length, - bool fixedSize); - status_t AddData(const char *name, type_code type, - void **buffer, ssize_t length); - status_t ReplaceData(const char *name, type_code type, - int32 index, const void *item, ssize_t length); - status_t ReplaceData(const char *name, type_code type, - int32 index, void **buffer, ssize_t length); - - status_t RemoveData(const char *name, int32 index = 0); - - bool HasData(const char *name, type_code t, - int32 index) const; - status_t FindData(const char *name, type_code type, - int32 index, const void **data, - ssize_t *numBytes) const; - - status_t Rename(const char *oldName, const char *newName); - status_t RemoveName(const char *name); - status_t MakeEmpty(); - - void PrintToStream() const; - - // flat buffer management -inline uint8 *FlatBuffer() const { return fFlatBuffer; }; - uint8 *FlatInsert(int32 offset, ssize_t oldLength, - ssize_t newLength); - void FlatResize(int32 newSize); - - // hash table support - void HashInsert(BMessageField *field); - BMessageField *HashLookup(const char *name) const; - BMessageField *HashRemove(const char *name); - uint32 HashString(const char *string) const; - void HashClear(); - -private: - status_t InitCommon(); - BMessageField *AddData(const char *name, type_code type, - status_t &error); - BMessageField *FindData(const char *name, type_code type, - status_t &error) const; - - BList fFieldList; - BMessageField **fFieldTable; - int32 fFieldTableSize; - - uint8 *fFlatBuffer; - int32 fFlatLength; - int32 fFlatAllocated; - int32 fBlockSize; -}; - -} // namespace BPrivate - -#endif // _MESSAGE_BODY_H_ diff --git a/headers/build/private/app/MessageField.h b/headers/build/private/app/MessageField.h deleted file mode 100644 index 6e958f457f..0000000000 --- a/headers/build/private/app/MessageField.h +++ /dev/null @@ -1,791 +0,0 @@ -//------------------------------------------------------------------------------ -// Copyright (c) 2001-2002, OpenBeOS -// -// Permission is hereby granted, free of charge, to any person obtaining a -// copy of this software and associated documentation files (the "Software"), -// to deal in the Software without restriction, including without limitation -// the rights to use, copy, modify, merge, publish, distribute, sublicense, -// and/or sell copies of the Software, and to permit persons to whom the -// Software is furnished to do so, subject to the following conditions: -// -// The above copyright notice and this permission notice shall be included in -// all copies or substantial portions of the Software. -// -// THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR -// IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY, -// FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE -// AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER -// LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING -// FROM, OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER -// DEALINGS IN THE SOFTWARE. -// -// File Name: MessageField.h -// Author(s): Erik Jaesler (erik@cgsoftware.com) -// Description: BMessageField contains and manages the data for indiviual -// named field in BMessageBody -//------------------------------------------------------------------------------ - -#ifndef MESSAGEFIELD_H -#define MESSAGEFIELD_H - -// Standard Includes ----------------------------------------------------------- -#include -#include -#include -#include -#include - -// System Includes ------------------------------------------------------------- -#include -#include -#include -#include -#include -#include - -// Project Includes ------------------------------------------------------------ -#include -#include - -// Local Includes -------------------------------------------------------------- - -// Local Defines --------------------------------------------------------------- -// flags for each entry (the bitfield is 1 byte) -#define MSG_FLAG_VALID 0x01 -#define MSG_FLAG_MINI_DATA 0x02 -#define MSG_FLAG_FIXED_SIZE 0x04 -#define MSG_FLAG_SINGLE_ITEM 0x08 -#define MSG_FLAG_ALL 0x0F - -#define MSG_LAST_ENTRY 0x0 - -using namespace std; - -// Globals --------------------------------------------------------------------- -namespace BPrivate { - -class BMessageField -{ - public: - static const char* sNullData; - - BMessageField(const std::string& name, type_code t) - : fType(t), fName(name) - {;} - virtual ~BMessageField() {} - virtual const std::string& Name() const { return fName; } - virtual type_code Type() const { return fType; } - virtual bool FixedSize() const { return true; } - virtual ssize_t FlattenedSize() const { return 0; } - virtual status_t Flatten(BDataIO& stream) const = 0; - virtual ssize_t CountItems() const { return 0; } - virtual void RemoveItem(ssize_t index) = 0; - virtual void PrintToStream(const char* name) const; - virtual const void* DataAt(int32 index, ssize_t* size) const = 0; - - virtual BMessageField* Clone() const = 0; - - protected: - virtual void PrintDataItem(int32 index) const = 0; - - private: - type_code fType; - std::string fName; -}; - -//------------------------------------------------------------------------------ -template -struct BMessageFieldStoragePolicy -{ - class Store - { - public: - // Compiler-generated versions should be just fine - #if 0 - Store(); - Store(const Store& rhs); - ~Store(); - Store& operator=(const Store& rhs); - #endif - inline size_t Size() const { return fData.size(); } - inline T& operator[](uint index) { return fData[index]; } - inline const T& operator[](uint index) const { return fData[index]; } - inline void Add(const T& data) { fData.push_back(data); } - inline void Remove(uint index) { fData.erase(fData.begin() + index); } - inline void Copy(const Store& rhs) { fData = rhs.fData; } - - private: - std::vector fData; - }; -}; -//------------------------------------------------------------------------------ -template -struct BMessageFieldSizePolicy -{ - typedef typename BMessageFieldStoragePolicy::Store Store; - - inline static size_t Size(const T&) { return sizeof (T); } - inline static size_t Size(const Store& data) - { - return sizeof (T) * data.Size(); - } - inline static bool Fixed() { return true; } - inline static size_t Padding(const T&) { return 0; } - inline static size_t Padding(const Store& data) { return 0; } -}; -//------------------------------------------------------------------------------ -template -struct BMessageFieldPrintPolicy -{ - static void PrintData(const T& data) {;} -}; -//------------------------------------------------------------------------------ -template -struct BMessageFieldFlattenPolicy -{ - typedef BMessageFieldSizePolicy SizePolicy; - - inline static status_t Flatten(BDataIO& stream, const T& data) - { - return stream.Write((const void*)&data, SizePolicy::Size(data)); - } -}; -//------------------------------------------------------------------------------ -template -struct BMessageFieldGetDataPolicy -{ - inline static const void* GetData(const T* data) - { return (const void*)data; } -}; -//------------------------------------------------------------------------------ - -//------------------------------------------------------------------------------ -template -< - class T1, - class StoragePolicy = BMessageFieldStoragePolicy, - class SizePolicy = BMessageFieldSizePolicy, - class PrintPolicy = BMessageFieldPrintPolicy, - class FlattenPolicy = BMessageFieldFlattenPolicy, - class GetDataPolicy = BMessageFieldGetDataPolicy -> -class BMessageFieldImpl : public BMessageField -{ - public: - typedef typename StoragePolicy::Store StorageType; - - BMessageFieldImpl(const std::string& name, type_code type) - : BMessageField(name, type), - fMaxSize(0), - fFlags(MSG_FLAG_ALL) - {;} - virtual ~BMessageFieldImpl() {} - - virtual bool FixedSize() const - { return fFlags & MSG_FLAG_FIXED_SIZE; } - virtual ssize_t FlattenedSize() const; - virtual status_t Flatten(BDataIO& stream) const; - virtual ssize_t CountItems() const { return fData.Size(); } - virtual void AddItem(const T1& data); - virtual void RemoveItem(ssize_t index) - { fData.Remove(index); }; - - virtual const void* DataAt(int32 index, ssize_t* size) const; - - virtual BMessageField* Clone() const; - - StorageType& Data() { return fData; } - - protected: - virtual void PrintDataItem(int32 index) const; - - private: - StorageType fData; - size_t fMaxSize; - uchar fFlags; -}; -//------------------------------------------------------------------------------ - - -//------------------------------------------------------------------------------ -template -< - class T1, - class StoragePolicy, - class SizePolicy, - class PrintPolicy, - class FlattenPolicy, - class GetDataPolicy -> -ssize_t -BMessageFieldImpl:: -FlattenedSize() const -{ - // Mandatory stuff - ssize_t size = 1; // field flags byte - size += sizeof (type_code); // field type bytes - if (!(fFlags & MSG_FLAG_SINGLE_ITEM)) // item count byte - { - if (fFlags & MSG_FLAG_MINI_DATA) - ++size; // item count byte for mini data - else - size += 4; // item count bytes for maxi data - } - - if (fFlags & MSG_FLAG_MINI_DATA) - ++size; // data length byte for mini data - else - size += 4; // data length bytes for maxi data - - ++size; // name length byte - size += Name().length(); // name length - - // item data length - size += SizePolicy::Size(fData); - - // Calculate any necessary padding - if (!SizePolicy::Fixed()) - { - size += 4 * fData.Size(); - size += SizePolicy::Padding(fData); -#if 0 - for (uint32 i = 0; i < fData.Size(); ++i) - { - // pad to 8-byte boundary, including size bytes in calculation - size += calc_padding(SizePolicy::Size(fData[i]) + 4, 8); - // item size bytes - size += 4; - } -#endif - } - - return size; -} -//------------------------------------------------------------------------------ -template -< - class T1, - class StoragePolicy, - class SizePolicy, - class PrintPolicy, - class FlattenPolicy, - class GetDataPolicy -> -status_t -BMessageFieldImpl:: -Flatten(BDataIO& stream) const -{ - status_t err = B_OK; - type_code type = Type(); - uint32 count = fData.Size(); - uint8 nameLen = Name().length(); - size_t size = SizePolicy::Size(fData); - - err = stream.Write(&fFlags, sizeof (fFlags)); - - // Field type_code - if (err >= 0) - err = stream.Write(&type, sizeof (type_code)); - - // Item count, if more than one - if (err >= 0 && !(fFlags & MSG_FLAG_SINGLE_ITEM)) - { - if (fFlags & MSG_FLAG_MINI_DATA) - { - uint8 miniCount = count; - err = stream.Write(&miniCount, sizeof (miniCount)); - } - else - { - err = stream.Write(&count, sizeof (count)); - } - } - - // Data length - if (err >= 0) - { - if (!(fFlags & MSG_FLAG_FIXED_SIZE)) - { - // Add the bytes for holding the item size for each item - size += 4 * fData.Size(); - size += SizePolicy::Padding(fData); - } - if (fFlags & MSG_FLAG_MINI_DATA) - { - uint8 miniSize = size; - err = stream.Write(&miniSize, sizeof (miniSize)); - } - else - { - err = stream.Write(&size, sizeof (size)); - } - } - - // Name length - if (err >= 0) - err = stream.Write(&nameLen, sizeof (nameLen)); - - // Name - if (err >= 0) - err = stream.Write(Name().c_str(), Name().length()); - - // Actual data items - for (uint32 i = 0; i < fData.Size() && err >= 0; ++i) - { - if (!SizePolicy::Fixed()) - { - size = (int32)SizePolicy::Size(fData[i]); - err = stream.Write(&size, sizeof (size)); - } - if (err >= 0) - { - err = FlattenPolicy::Flatten(stream, fData[i]); - } - if (err >= 0 && !SizePolicy::Fixed()) - { - // Add any necessary padding - err = stream.Write(BMessageField::sNullData, - SizePolicy::Padding(fData[i])); - } - } - - if (err >= 0) - err = B_OK; - return err; -} -//------------------------------------------------------------------------------ -template -< - class T1, - class StoragePolicy, - class SizePolicy, - class PrintPolicy, - class FlattenPolicy, - class GetDataPolicy -> -void -BMessageFieldImpl:: -AddItem(const T1& data) -{ - fData.Add(data); - - if (fMaxSize) - { - if ((fFlags & MSG_FLAG_FIXED_SIZE) && - (!SizePolicy::Fixed() || - fMaxSize != SizePolicy::Size(data))) - { - fMaxSize = max(SizePolicy::Size(data), fMaxSize); - fFlags &= ~MSG_FLAG_FIXED_SIZE; - } - } - else - { - if (!SizePolicy::Fixed()) - { - fFlags &= ~MSG_FLAG_FIXED_SIZE; - } - fMaxSize = SizePolicy::Size(data); - } - - if (fFlags & MSG_FLAG_MINI_DATA) - { - int32 size = SizePolicy::Size(fData); - if (!(fFlags & MSG_FLAG_FIXED_SIZE)) - { - size += 4 * fData.Size(); - size += SizePolicy::Padding(fData); - } - if (size > 255) - fFlags &= ~MSG_FLAG_MINI_DATA; - } - - if (fData.Size() > 1) - fFlags &= ~MSG_FLAG_SINGLE_ITEM; -} -//------------------------------------------------------------------------------ -template -< - class T1, - class StoragePolicy, - class SizePolicy, - class PrintPolicy, - class FlattenPolicy, - class GetDataPolicy -> -const void* -BMessageFieldImpl:: -DataAt(int32 index, ssize_t* size) const -{ - if (index < CountItems()) - { - *size = SizePolicy::Size(fData[index]); - const T1& ref = fData[index]; - const T1* data = &ref; - - return GetDataPolicy::GetData(data);//(const void*)data; - } - - return NULL; -} -//------------------------------------------------------------------------------ -template -< - class T1, - class StoragePolicy, - class SizePolicy, - class PrintPolicy, - class FlattenPolicy, - class GetDataPolicy -> -BMessageField* -BMessageFieldImpl:: -Clone() const -{ - BMessageFieldImpl* BMF = - new(nothrow) BMessageFieldImpl(Name(), Type()); - if (BMF) - { - BMF->fMaxSize = fMaxSize; - BMF->fFlags = fFlags; - BMF->fData.Copy(fData); - } - return BMF; -} -//------------------------------------------------------------------------------ -template -< - class T1, - class StoragePolicy, - class SizePolicy, - class PrintPolicy, - class FlattenPolicy, - class GetDataPolicy -> -void -BMessageFieldImpl:: -PrintDataItem(int32 index) const -{ - if (index && FixedSize()) - { - std::printf(" "); - } - else - { - std::printf("size=%2ld, ", SizePolicy::Size(fData[index])); - } - std::printf("data[%ld]: ", index); - PrintPolicy::PrintData(fData[index]); -} -//------------------------------------------------------------------------------ - - -// Print policy specializations ------------------------------------------------ -template<> struct BMessageFieldPrintPolicy -{ - static void PrintData(const bool& b) { std::printf("%d", int(b)); } -}; -template<> struct BMessageFieldPrintPolicy -{ - static void PrintData(const int8& i) - { std::printf("0x%X (%d, '%c')", int(i), int(i), char(i)); } -}; -template<> struct BMessageFieldPrintPolicy -{ - static void PrintData(const int16& i) - { std::printf("0x%X (%d, '%c')", i, i, char(i)); } -}; -template<> struct BMessageFieldPrintPolicy -{ - static void PrintData(const int32& i) - { std::printf("0x%lX (%ld, '%c')", i, i, char(i)); } -}; -template<> struct BMessageFieldPrintPolicy -{ - static void PrintData(const int64& i) - { std::printf("0x%LX (%Ld, '%c')", i, i, char(i)); } -}; -template<> struct BMessageFieldPrintPolicy -{ - static void PrintData(const float& f) { std::printf("%.4f", f); } -}; -template<> struct BMessageFieldPrintPolicy -{ - static void PrintData(const double& d) { std::printf("%.8f", d); } -}; -template<> struct BMessageFieldPrintPolicy -{ - static void PrintData(const BString& s) { std::printf("\"%s\"", s.String()); } -}; -template<> struct BMessageFieldPrintPolicy -{ - static void PrintData(const BPoint& p) { std::printf("BPoint(x:%.1f, y:%.1f)", p.x, p.y); } -}; -template<> struct BMessageFieldPrintPolicy -{ - static void PrintData(const BRect& r) - { std::printf("BRect(l:%.1f, t:%.1f, r:%.1f, b:%.1f)", r.left, r.top, r.right, r.bottom); } -}; -template<> struct BMessageFieldPrintPolicy -{ - static void PrintData(const entry_ref& ref) - { - std::printf("device=%ld, directory=%Ld, name=\"%s\", path=\"%s\"", - ref.device, ref.directory, ref.name, BPath(&ref).Path()); - } -}; -// Storage policy specializations ---------------------------------------------- -template<> -struct BMessageFieldStoragePolicy -{ - class Store - { - private: - struct Boolean - { - Boolean() : data(bool()) {;} - Boolean(bool b) : data(b) {;} - bool data; - }; - - public: - inline size_t Size() const - { return fData.size(); } - inline bool& operator[](uint index) - { return fData[index].data; } - inline const bool& operator[](uint index) const - { return fData[index].data; } - inline void Add(const bool& data) - { - fData.push_back(data); - } - inline void Remove(uint index) - { - fData.erase(fData.begin() + index); - } - inline void Copy(const Store& rhs) - { - if (&fData != &rhs.fData) - { - fData = rhs.fData; - } - } - - private: - std::vector fData; - }; -}; -//------------------------------------------------------------------------------ -template<> -struct BMessageFieldStoragePolicy -{ - class Store - { - public: - inline size_t Size() const - { return fData.size(); } - inline BDataBuffer& operator[](uint index) - { return fData[index]; } - inline const BDataBuffer& operator[](uint index) const - { return fData[index]; } - inline void Add(const BDataBuffer& data) - { fData.push_back(data); } - inline void Remove(uint index) - { fData.erase(fData.begin() + index); } - void Copy(const Store& rhs) - { - if (&fData == &rhs.fData) - { - return; - } - - fData.clear(); - for (size_t i = 0; i < rhs.Size(); ++i) - { - Add(BDataBuffer(rhs[i], true)); - } - } - - private: - std::vector fData; - }; -}; -// Size policy specializations ------------------------------------------------- -template<> struct BMessageFieldSizePolicy -{ - typedef BMessageFieldStoragePolicy::Store Store; - - inline static size_t Size(const BString& s) { return s.Length() + 1; } - inline static size_t Size(const Store& data) - { - size_t size = 0; - for (uint32 i = 0; i < data.Size(); ++i) - { - size += Size(data[i]); - } - return size; - } - inline static bool Fixed() { return false; } - inline static size_t Padding(const BString& s) - { - // Padding calculations are only done for variable-sized items, - // which by definition have four bytes of size info preceeding the - // actual data; those four bytes are included in the padding - // calculation. Padding is calculated to an 8-byte boundary - return calc_padding(Size(s) + 4, 8); - } - inline static size_t Padding(const Store& data) - { - size_t size = 0; - for (uint32 i = 0; i < data.Size(); ++i) - { - size += Padding(data[i]); - } - return size; - } -}; -//------------------------------------------------------------------------------ -template<> struct BMessageFieldSizePolicy -{ - typedef BMessageFieldStoragePolicy::Store Store; - - inline static size_t Size(const BDataBuffer& db) - { return db.BufferSize(); } - inline static size_t Size(const Store& data) - { - size_t size = 0; - for (uint32 i = 0; i < data.Size(); ++i) - { - size += Size(data[i]); - } - - return size; - } - inline static bool Fixed() { return false; } - inline static size_t Padding(const BDataBuffer& db) - { - // Padding calculations are only done for variable-sized items, - // which by definition have four bytes of size info preceeding the - // actual data; those four bytes are included in the padding - // calculation. Padding is calculated to an 8-byte boundary - return calc_padding(Size(db) + 4, 8); - } - inline static size_t Padding(const Store& data) - { - size_t size = 0; - for (uint32 i = 0; i < data.Size(); ++i) - { - size += Padding(data[i]); - } - return size; - } -}; -//------------------------------------------------------------------------------ -template<> struct BMessageFieldSizePolicy -{ - typedef BMessageFieldStoragePolicy::Store Store; - - inline static size_t Size(const BMessage* msg) - { return msg->FlattenedSize(); } - inline static size_t Size(const Store& data) - { - size_t size = 0; - for (uint32 i = 0; i < data.Size(); ++i) - { - size += Size(data[i]); - } - - return size; - } - inline static bool Fixed() { return false; } - inline static size_t Padding(const BMessage* msg) - { - // Padding calculations are only done for variable-sized items, - // which by definition have four bytes of size info preceeding the - // actual data; those four bytes are included in the padding - // calculation. Padding is calculated to an 8-byte boundary - return calc_padding(Size(msg) + 4, 8); - } - inline static size_t Padding(const Store& data) - { - size_t size = 0; - for (uint32 i = 0; i < data.Size(); ++i) - { - size += Padding(data[i]); - } - return size; - } -}; -// Flatten policy specializations ---------------------------------------------- -template<> -struct BMessageFieldFlattenPolicy -{ - typedef BMessageFieldSizePolicy SizePolicy; - - static status_t Flatten(BDataIO& stream, const BString& data) - { - size_t size = SizePolicy::Size(data); - status_t err = stream.Write((const void*)data.String(), size); - - if (err > 0) - err = B_OK; - return err; - } -}; -//------------------------------------------------------------------------------ -template<> -struct BMessageFieldFlattenPolicy -{ - typedef BMessageFieldSizePolicy SizePolicy; - - static status_t Flatten(BDataIO& stream, const BMessage* data) - { - status_t err = data->Flatten(&stream); - - if (err > 0) - err = B_OK; - return err; - } -}; -//------------------------------------------------------------------------------ -template<> -struct BMessageFieldFlattenPolicy -{ - typedef BMessageFieldSizePolicy SizePolicy; - - static status_t Flatten(BDataIO& stream, const BDataBuffer& db) - { - size_t size = SizePolicy::Size(db); - status_t err = stream.Write(db.Buffer(), size); - if (err > 0) - err = B_OK; - return err; - } -}; -// GetData policy specializations ---------------------------------------------- -template<> -struct BMessageFieldGetDataPolicy -{ - inline static const void* GetData(const BDataBuffer* data) - { return data->Buffer(); } -}; -//------------------------------------------------------------------------------ -template<> -struct BMessageFieldGetDataPolicy -{ - inline static const void* GetData(const BString* data) - { return data->String(); } -}; -//------------------------------------------------------------------------------ - -} // namespace BPrivate - -#endif // MESSAGEFIELD_H - -/* - * $Log $ - * - * $Id $ - * - */ - diff --git a/headers/build/private/app/MessageField2.h b/headers/build/private/app/MessageField2.h deleted file mode 100644 index 550f316902..0000000000 --- a/headers/build/private/app/MessageField2.h +++ /dev/null @@ -1,96 +0,0 @@ -/* - * Copyright 2005, Haiku. - * Distributed under the terms of the MIT License. - * - * Authors: - * Michael Lotz - */ - -/* BMessageField contains the data for indiviual named fields in BMessageBody */ - -#ifndef _MESSAGE_FIELD_H_ -#define _MESSAGE_FIELD_H_ - -#include -#include -#include - -#define MSG_FLAG_VALID 0x01 -#define MSG_FLAG_MINI_DATA 0x02 -#define MSG_FLAG_FIXED_SIZE 0x04 -#define MSG_FLAG_SINGLE_ITEM 0x08 -#define MSG_FLAG_ALL 0x0F - -#define MSG_LAST_ENTRY 0x00 - -namespace BPrivate { - -typedef struct field_header_s { - uint8 flags; - type_code type; - int32 count; - ssize_t dataSize; - uint8 nameLength; - char name[255]; -} __attribute__((__packed__)) FieldHeader; - -class BMessageField { -public: - BMessageField(); - BMessageField(const char *name, type_code type); - BMessageField(uint8 flags, BDataIO *stream); - BMessageField(const BMessageField &other); - ~BMessageField(); - - BMessageField &operator=(const BMessageField &other); - - void Flatten(BDataIO *stream); - void Unflatten(uint8 flags, BDataIO *stream); - - uint8 Flags() { return fHeader.flags; }; - - void SetName(const char *name); - const char *Name() const { return fHeader.name; }; - uint8 NameLength() const { return fHeader.nameLength; }; - type_code Type() const { return fHeader.type; }; - - void *AddItem(size_t length); - void *ReplaceItem(int32 index, size_t newLength); - void RemoveItem(int32 index); - int32 CountItems() const { return fHeader.count; }; - - const void *BufferAt(int32 index, ssize_t *size) const; - - void MakeEmpty(); - - status_t SetFixedSize(int32 itemSize, int32 count); - bool IsFixedSize() const { return fHeader.flags & MSG_FLAG_FIXED_SIZE; }; - size_t TotalSize() const { return fHeader.dataSize; }; - - void PrintToStream() const; - - // hash table support - void SetNext(BMessageField *next) { fNext = next; }; - BMessageField *Next() const { return fNext; }; - -private: - void ResetHeader(const char *name, type_code type); - void FlatResize(int32 offset, size_t oldLength, - size_t newLength); - - FieldHeader fHeader; -mutable BMallocIO fFlatBuffer; - - // fixed size items - int32 fItemSize; - - // variable sized items - BList *fOffsets; - - // hash table support - BMessageField *fNext; -}; - -} // namespace BPrivate - -#endif // _MESSAGE_FIELD_H_ diff --git a/headers/build/private/app/MessageField3.h b/headers/build/private/app/MessageField3.h deleted file mode 100644 index c437db5c2d..0000000000 --- a/headers/build/private/app/MessageField3.h +++ /dev/null @@ -1,120 +0,0 @@ -/* - * Copyright 2005, Haiku. - * Distributed under the terms of the MIT License. - * - * Authors: - * Michael Lotz - */ - -/* BMessageField contains the data for indiviual named fields in BMessageBody */ - -#ifndef _MESSAGE_FIELD_H_ -#define _MESSAGE_FIELD_H_ - -#include -#include -#include -#include "MessageBody3.h" - -// we only support those -#define MSG_FLAG_VALID 0x01 -#define MSG_FLAG_FIXED_SIZE 0x04 -#define MSG_FLAG_ALL 0x05 - -// these are for R5 compatibility -#define MSG_FLAG_MINI_DATA 0x02 -#define MSG_FLAG_SINGLE_ITEM 0x08 - -#define MSG_LAST_ENTRY 0x00 - -namespace BPrivate { - -struct field_header_s { - uint8 flags; - type_code type; - int32 count; - ssize_t dataSize; - uint8 nameLength; -} __attribute__((__packed__)); - -struct item_info_s { - item_info_s(int32 _offset) - : offset(_offset) - { - } - - item_info_s(int32 _offset, int32 _length) - : offset(_offset), - length(_length) - { - } - - int32 offset; - int32 length; - int32 paddedLength; -}; - -typedef field_header_s FieldHeader; -typedef item_info_s ItemInfo; - -class BMessageField { -public: - BMessageField(BMessageBody *parent, - int32 offset, const char *name, - type_code type); - - // only use this constructor to unflatten - BMessageField(BMessageBody *parent); - int32 Unflatten(int32 offset); - - uint8 Flags() const { return Header()->flags; }; - status_t SetFixedSize(int32 itemSize); - bool FixedSize() const { return fFixedSize; }; - - void SetName(const char *newName); - const char *Name() const; - uint8 NameLength() const { return Header()->nameLength; }; - type_code Type() const { return Header()->type; }; - - void AddItem(const void *item, ssize_t length); - uint8 *AddItem(ssize_t length); - - void ReplaceItem(int32 index, const void *newItem, - ssize_t length); - uint8 *ReplaceItem(int32 index, ssize_t length); - - void *ItemAt(int32 index, ssize_t *size); - - void RemoveItem(int32 index); - int32 CountItems() const { return Header()->count; }; - - void PrintToStream() const; - - void SetOffset(int32 offset) { fOffset = offset; }; - int32 Offset() const { return fOffset; }; - - // always do MakeEmpty -> RemoveSelf -> delete - void MakeEmpty(); - void RemoveSelf(); - - // hash table support - void SetNext(BMessageField *next) { fNext = next; }; - BMessageField *Next() const { return fNext; }; - -private: -inline FieldHeader *Header() const { return (FieldHeader *)(fParent->FlatBuffer() + fOffset); }; - - BMessageBody *fParent; - int32 fOffset; - int32 fDataOffset; - - bool fFixedSize; - int32 fItemSize; - BList fItemInfos; - - BMessageField *fNext; -}; - -} // namespace BPrivate - -#endif // _MESSAGE_FIELD_H_ diff --git a/headers/build/private/app/MessagePrivate.h b/headers/build/private/app/MessagePrivate.h index 6e4675df8e..bafba3af2d 100644 --- a/headers/build/private/app/MessagePrivate.h +++ b/headers/build/private/app/MessagePrivate.h @@ -1,80 +1,189 @@ -//------------------------------------------------------------------------------ -// MessagePrivate.h -// -//------------------------------------------------------------------------------ - -#ifndef MESSAGEPRIVATE_H -#define MESSAGEPRIVATE_H +/* + * Copyright 2005-2007, Haiku Inc. All rights reserved. + * Distributed under the terms of the MIT License. + * + * Authors: + * Michael Lotz + */ +#ifndef _MESSAGE_PRIVATE_H_ +#define _MESSAGE_PRIVATE_H_ #include -#include -#include #include -class BMessage::Private -{ + +#define MESSAGE_BODY_HASH_TABLE_SIZE 10 +#define MAX_DATA_PREALLOCATION B_PAGE_SIZE * 10 +#define MAX_FIELD_PREALLOCATION 50 +#define MAX_ITEM_PREALLOCATION B_PAGE_SIZE + + +static const int32 kPortMessageCode = 'pjpp'; + + +enum { + MESSAGE_FLAG_VALID = 0x0001, + MESSAGE_FLAG_REPLY_REQUIRED = 0x0002, + MESSAGE_FLAG_REPLY_DONE = 0x0004, + MESSAGE_FLAG_IS_REPLY = 0x0008, + MESSAGE_FLAG_WAS_DELIVERED = 0x0010, + MESSAGE_FLAG_HAS_SPECIFIERS = 0x0020, + MESSAGE_FLAG_WAS_DROPPED = 0x0080, + MESSAGE_FLAG_PASS_BY_AREA = 0x0100 +}; + + +enum { + FIELD_FLAG_VALID = 0x0001, + FIELD_FLAG_FIXED_SIZE = 0x0002, +}; + + +struct BMessage::field_header { + uint32 flags; + type_code type; + int32 name_length; + int32 count; + ssize_t data_size; + ssize_t allocated; + int32 offset; + int32 next_field; +}; + + +struct BMessage::message_header { + uint32 format; + uint32 what; + uint32 flags; + + ssize_t fields_size; + ssize_t data_size; + ssize_t fields_available; + ssize_t data_available; + + uint32 fields_checksum; + uint32 data_checksum; + + int32 target; + int32 current_specifier; + area_id shared_area; + + // reply info + port_id reply_port; + int32 reply_target; + team_id reply_team; + + // body info + int32 field_count; + int32 hash_table_size; + int32 hash_table[MESSAGE_BODY_HASH_TABLE_SIZE]; + + /* The hash table does contain indexes into the field list and + not direct offsets to the fields. This has the advantage + of not needing to update offsets in two locations. + The hash table must be reevaluated when we remove a field + though. + */ +}; + + +class BMessage::Private { public: - Private(BMessage* msg) : fMessage(msg) {;} - Private(BMessage& msg) : fMessage(&msg) {;} - - inline void SetTarget(int32 token, bool preferred) + Private(BMessage *msg) + : fMessage(msg) { - fMessage->fTarget = token; - fMessage->fPreferred = preferred; } - inline void SetReply(BMessenger messenger) + Private(BMessage &msg) + : fMessage(&msg) { - BMessenger::Private mp(messenger); - fMessage->fReplyTo.port = mp.Port(); - fMessage->fReplyTo.target - = (mp.IsPreferredTarget() ? B_PREFERRED_TOKEN : mp.Token()); - fMessage->fReplyTo.team = mp.Team(); - fMessage->fReplyTo.preferred = mp.IsPreferredTarget(); } - inline int32 GetTarget() + void + SetTarget(int32 token) { - return fMessage->fTarget; + fMessage->fHeader->target = token; } - inline bool UsePreferredTarget() + int32 + GetTarget() { - return fMessage->fPreferred; + return fMessage->fHeader->target; } - static inline status_t SendFlattenedMessage(void *data, int32 size, - port_id port, int32 token, bool preferred, bigtime_t timeout) + bool + UsePreferredTarget() { - return BMessage::_SendFlattenedMessage(data, size, port, token, - preferred, timeout); + return fMessage->fHeader->target == B_PREFERRED_TOKEN; } - static inline void StaticInit() + void + SetWasDropped(bool wasDropped) { - BMessage::_StaticInit(); + if (wasDropped) + fMessage->fHeader->flags |= MESSAGE_FLAG_WAS_DROPPED; + else + fMessage->fHeader->flags &= ~MESSAGE_FLAG_WAS_DROPPED; } - static inline void StaticCleanup() + status_t + Clear() { - BMessage::_StaticCleanup(); + return fMessage->_Clear(); } - static inline void StaticCacheCleanup() + status_t + InitHeader() + { + return fMessage->_InitHeader(); + } + + BMessage::message_header* + GetMessageHeader() + { + return fMessage->fHeader; + } + + BMessage::field_header* + GetMessageFields() + { + return fMessage->fFields; + } + + uint8* + GetMessageData() + { + return fMessage->fData; + } + + ssize_t + NativeFlattenedSize() const + { + return fMessage->_NativeFlattenedSize(); + } + + status_t + NativeFlatten(char *buffer, ssize_t size) const + { + return fMessage->_NativeFlatten(buffer, size); + } + + status_t + NativeFlatten(BDataIO *stream, ssize_t *size) const + { + return fMessage->_NativeFlatten(stream, size); + } + + // static methods + + static void + StaticCacheCleanup() { BMessage::_StaticCacheCleanup(); } private: - BMessage* fMessage; + BMessage* fMessage; }; -#endif // MESSAGEPRIVATE_H - -/* - * $Log $ - * - * $Id $ - * - */ - +#endif // _MESSAGE_PRIVATE_H_ diff --git a/headers/build/private/app/MessageUtils.h b/headers/build/private/app/MessageUtils.h index dc8faf5c72..4625b52dae 100644 --- a/headers/build/private/app/MessageUtils.h +++ b/headers/build/private/app/MessageUtils.h @@ -1,31 +1,12 @@ -//------------------------------------------------------------------------------ -// MessageUtils.h -// -//------------------------------------------------------------------------------ +#ifndef _MESSAGE_UTILS_H_ +#define _MESSAGE_UTILS_H_ -#ifndef MESSAGEUTILS_H -#define MESSAGEUTILS_H - -// Standard Includes ----------------------------------------------------------- - -// System Includes ------------------------------------------------------------- #include #include #include #include -#include -#include #include -// Project Includes ------------------------------------------------------------ - -// Local Includes -------------------------------------------------------------- - -// Local Defines --------------------------------------------------------------- - -// Globals --------------------------------------------------------------------- - -uint32 _checksum_(const uchar *buf, int32 size); namespace BPrivate { // Only putting these here because Be did @@ -33,177 +14,150 @@ status_t entry_ref_flatten(char* buffer, size_t* size, const entry_ref* ref); status_t entry_ref_unflatten(entry_ref* ref, const char* buffer, size_t size); status_t entry_ref_swap(char* buffer, size_t size); -size_t calc_padding(size_t size, size_t boundary); +uint32 CalculateChecksum(const uint8 *buffer, int32 size); } // namespace BPrivate -//------------------------------------------------------------------------------ -// _set_message_target_ -/*! \brief Sets the target of a message. - \param message The message. - \param token The target handler token. - \param preferred Indicates whether to use the looper's preferred handler. -*/ -inline -void -_set_message_target_(BMessage *message, int32 token, bool preferred) -{ - message->fTarget = token; - message->fPreferred = preferred; -} -//------------------------------------------------------------------------------ -// _set_message_reply_ -/*! \brief Sets a message's reply target. - - \param message The message. - \param messenger The reply messenger. -*/ -inline -void -_set_message_reply_(BMessage *message, BMessenger messenger) -{ - BMessenger::Private messengerPrivate(messenger); - message->fReplyTo.port = messengerPrivate.Port(); - message->fReplyTo.target = messengerPrivate.Token(); - message->fReplyTo.team = messengerPrivate.Team(); - message->fReplyTo.preferred = messengerPrivate.IsPreferredTarget(); -} -//------------------------------------------------------------------------------ -inline int32 _get_message_target_(BMessage *msg) -{ - return msg->fTarget; -} -//------------------------------------------------------------------------------ -inline bool _use_preferred_target_(BMessage *msg) -{ - return msg->fPreferred; -} -//------------------------------------------------------------------------------ -inline status_t normalize_err(status_t err) -{ - return err >= 0 ? B_OK : err; -} -//------------------------------------------------------------------------------ template -inline void byte_swap(T& /*data*/) +inline void +byte_swap(T &/*data*/) { // Specialize for data types which actually swap } -//------------------------------------------------------------------------------ -inline void write_helper(BDataIO* stream, const void* data, size_t size, - status_t& err) + + +inline void +write_helper(BDataIO *stream, const void *data, size_t size) { - err = normalize_err(stream->Write(data, size)); + status_t error = stream->Write(data, size); + if (error < B_OK) + throw error; } -//------------------------------------------------------------------------------ -// Will the template madness never cease?? -template -inline status_t write_helper(BDataIO* stream, T& data, status_t& err) -{ - return normalize_err(stream->Write((const void*)data, sizeof (T))); -} -//------------------------------------------------------------------------------ -class TReadHelper -{ - public: - TReadHelper(BDataIO* stream) - : fStream(stream), err(B_OK), fSwap(false) - { - ; - } - TReadHelper(BDataIO* stream, bool swap) - : fStream(stream), err(B_OK), fSwap(swap) - { - ; - } - template inline void operator()(T& data) - { - err = normalize_err(fStream->Read((void*)&data, sizeof (T))); - if (err) - throw err; +class TReadHelper { +public: + TReadHelper(BDataIO *stream) + : fStream(stream), + fError(B_OK), + fSwap(false) + { + } - if (IsSwapping()) - { - byte_swap(data); - } - } + TReadHelper(BDataIO *stream, bool swap) + : fStream(stream), + fError(B_OK), + fSwap(swap) + { + } - template inline void operator()(T data, size_t len) - { - err = normalize_err(fStream->Read((void*)data, len)); - if (err) - throw err; - } + template + inline void operator()(T &data) + { + fError = fStream->Read((void *)&data, sizeof(T)); + if (fError > B_OK) { + if (IsSwapping()) + byte_swap(data); + return; + } - status_t Status() { return err; } - void SetSwap(bool yesNo) { fSwap = yesNo; } - bool IsSwapping() { return fSwap; } + if (fError == 0) + fError = B_ERROR; + throw fError; + } - private: - BDataIO* fStream; - status_t err; - bool fSwap; + template + inline void operator()(T data, size_t len) + { + fError = fStream->Read((void *)data, len); + if (fError >= B_OK) + return; + + throw fError; + } + + status_t Status() { return fError >= B_OK ? B_OK : fError; }; + + void SetSwap(bool yesNo) { fSwap = yesNo; }; + bool IsSwapping() { return fSwap; }; + +private: + BDataIO *fStream; + status_t fError; + bool fSwap; }; -//------------------------------------------------------------------------------ -class TChecksumHelper -{ - public: - TChecksumHelper(uchar* buffer) : fBuffer(buffer), fBufPtr(buffer) {;} - template inline void Cache(const T& data) - { - *((T*)fBufPtr) = data; - fBufPtr += sizeof (T); - } - int32 CheckSum(); +class TChecksumHelper { +public: + TChecksumHelper(uchar* buffer) + : fBuffer(buffer), + fBufPtr(buffer) + { + } - private: - uchar* fBuffer; - uchar* fBufPtr; + template + inline void Cache(const T &data) + { + *((T*)fBufPtr) = data; + fBufPtr += sizeof (T); + } + + int32 CheckSum(); + +private: + uchar *fBuffer; + uchar *fBufPtr; }; -//------------------------------------------------------------------------------ -template inline status_t read_helper(BDataIO* stream, T& data) -{ - return normalize_err(stream->Read((void*)&data, sizeof (T))); -} -//------------------------------------------------------------------------------ -template<> inline void byte_swap(double& data) + + +template<> +inline void +byte_swap(double &data) { data = __swap_double(data); } -template<> inline void byte_swap(float& data) + + +template<> +inline void +byte_swap(float &data) { data = __swap_float(data); } -template<> inline void byte_swap(int64& data) + + +template<> +inline void +byte_swap(int64 &data) { data = __swap_int64(data); } -template<> inline void byte_swap(int32& data) + + +template<> +inline void +byte_swap(int32 &data) { data = __swap_int32(data); } -template<> inline void byte_swap(int16& data) + + +template<> +inline void +byte_swap(int16 &data) { data = __swap_int16(data); } -template<> inline void byte_swap(entry_ref& data) + + +template<> +inline void +byte_swap(entry_ref &data) { byte_swap(data.device); byte_swap(data.directory); } -//------------------------------------------------------------------------------ - -#endif // MESSAGEUTILS_H - -/* - * $Log $ - * - * $Id $ - * - */ +#endif // _MESSAGE_UTILS_H_ diff --git a/headers/build/private/app/MessageUtils2.h b/headers/build/private/app/MessageUtils2.h deleted file mode 100644 index 1087ba2aad..0000000000 --- a/headers/build/private/app/MessageUtils2.h +++ /dev/null @@ -1,222 +0,0 @@ -#ifndef MESSAGEUTILS_H -#define MESSAGEUTILS_H - -#include -#include -#include -#include -#include -#include -#include - - -uint32 _checksum_(const uchar *buf, int32 size); - -namespace BPrivate { // Only putting these here because Be did - -status_t entry_ref_flatten(char* buffer, size_t* size, const entry_ref* ref); -status_t entry_ref_unflatten(entry_ref* ref, const char* buffer, size_t size); -status_t entry_ref_swap(char* buffer, size_t size); - -size_t calc_padding(size_t size, size_t boundary); - -} // namespace BPrivate - -//------------------------------------------------------------------------------ -// _set_message_target_ -/*! \brief Sets the target of a message. - - \param message The message. - \param token The target handler token. - \param preferred Indicates whether to use the looper's preferred handler. -*/ -inline void -_set_message_target_(BMessage *message, int32 token, bool preferred) -{ - message->fTarget = token; - message->fPreferred = preferred; -} - - -// _set_message_reply_ -/*! \brief Sets a message's reply target. - - \param message The message. - \param messenger The reply messenger. -*/ -inline void -_set_message_reply_(BMessage *message, BMessenger messenger) -{ - BMessenger::Private messengerPrivate(messenger); - message->fReplyTo.port = messengerPrivate.Port(); - message->fReplyTo.target = messengerPrivate.Token(); - message->fReplyTo.team = messengerPrivate.Team(); - message->fReplyTo.preferred = messengerPrivate.IsPreferredTarget(); -} - - -inline int32 -_get_message_target_(BMessage *msg) -{ - return msg->fTarget; -} - - -inline bool -_use_preferred_target_(BMessage *msg) -{ - return msg->fPreferred; -} - - -inline status_t -normalize_err(status_t err) -{ - return err >= 0 ? B_OK : err; -} - - -template -inline void -byte_swap(T &/*data*/) -{ - // Specialize for data types which actually swap -} - - -inline void -write_helper(BDataIO *stream, const void *data, size_t size) -{ - status_t error = stream->Write(data, size); - if (error < B_OK) - throw error; -} - - -class TReadHelper { -public: - TReadHelper(BDataIO *stream) - : fStream(stream), - fError(B_OK), - fSwap(false) - { - } - - TReadHelper(BDataIO *stream, bool swap) - : fStream(stream), - fError(B_OK), - fSwap(swap) - { - } - - template - inline void operator()(T &data) - { - fError = fStream->Read((void *)&data, sizeof(T)); - if (fError < B_OK) - throw fError; - - if (IsSwapping()) - byte_swap(data); - } - - template - inline void operator()(T data, size_t len) - { - fError = fStream->Read((void *)data, len); - if (fError < B_OK) - throw fError; - } - - status_t Status() { return fError; }; - - void SetSwap(bool yesNo) { fSwap = yesNo; }; - bool IsSwapping() { return fSwap; }; - -private: - BDataIO *fStream; - status_t fError; - bool fSwap; -}; - - -class TChecksumHelper { -public: - TChecksumHelper(uchar* buffer) - : fBuffer(buffer), - fBufPtr(buffer) - { - } - - template - inline void Cache(const T &data) - { - *((T*)fBufPtr) = data; - fBufPtr += sizeof (T); - } - - int32 CheckSum(); - -private: - uchar *fBuffer; - uchar *fBufPtr; -}; - - -template -inline status_t -read_helper(BDataIO *stream, T &data) -{ - return normalize_err(stream->Read((void *)&data, sizeof(T))); -} - - -template<> -inline void -byte_swap(double &data) -{ - data = __swap_double(data); -} - - -template<> -inline void -byte_swap(float &data) -{ - data = __swap_float(data); -} - - -template<> -inline void -byte_swap(int64 &data) -{ - data = __swap_int64(data); -} - - -template<> -inline void -byte_swap(int32 &data) -{ - data = __swap_int32(data); -} - - -template<> -inline void -byte_swap(int16 &data) -{ - data = __swap_int16(data); -} - - -template<> -inline void -byte_swap(entry_ref &data) -{ - byte_swap(data.device); - byte_swap(data.directory); -} - -#endif // MESSAGEUTILS_H diff --git a/headers/build/private/app/MessageUtils3.h b/headers/build/private/app/MessageUtils3.h deleted file mode 100644 index aac4ca3588..0000000000 --- a/headers/build/private/app/MessageUtils3.h +++ /dev/null @@ -1,230 +0,0 @@ -#ifndef MESSAGEUTILS_H -#define MESSAGEUTILS_H - -#include -#include -#include -#include -#include -#include -#include - - -uint32 _checksum_(const uchar *buf, int32 size); - -namespace BPrivate { // Only putting these here because Be did - -status_t entry_ref_flatten(char* buffer, size_t* size, const entry_ref* ref); -status_t entry_ref_unflatten(entry_ref* ref, const char* buffer, size_t size); -status_t entry_ref_swap(char* buffer, size_t size); - -size_t calc_padding(size_t size, size_t boundary); - -} // namespace BPrivate - -//------------------------------------------------------------------------------ -// _set_message_target_ -/*! \brief Sets the target of a message. - - \param message The message. - \param token The target handler token. - \param preferred Indicates whether to use the looper's preferred handler. -*/ -inline void -_set_message_target_(BMessage *message, int32 token, bool preferred) -{ - message->fTarget = token; - message->fPreferred = preferred; -} - - -// _set_message_reply_ -/*! \brief Sets a message's reply target. - - \param message The message. - \param messenger The reply messenger. -*/ -inline void -_set_message_reply_(BMessage *message, BMessenger messenger) -{ - BMessenger::Private messengerPrivate(messenger); - message->fReplyTo.port = messengerPrivate.Port(); - message->fReplyTo.target = messengerPrivate.Token(); - message->fReplyTo.team = messengerPrivate.Team(); - message->fReplyTo.preferred = messengerPrivate.IsPreferredTarget(); -} - - -inline int32 -_get_message_target_(BMessage *msg) -{ - return msg->fTarget; -} - - -inline bool -_use_preferred_target_(BMessage *msg) -{ - return msg->fPreferred; -} - - -inline status_t -normalize_err(status_t err) -{ - return err >= 0 ? B_OK : err; -} - - -template -inline void -byte_swap(T &/*data*/) -{ - // Specialize for data types which actually swap -} - - -inline void -write_helper(BDataIO *stream, const void *data, size_t size) -{ - status_t error = stream->Write(data, size); - if (error < B_OK) - throw error; -} - - -class TReadHelper { -public: - TReadHelper(BDataIO *stream) - : fStream(stream), - fError(B_OK), - fSwap(false) - { - } - - TReadHelper(BDataIO *stream, bool swap) - : fStream(stream), - fError(B_OK), - fSwap(swap) - { - } - - template - inline void operator()(T &data) - { - fError = fStream->Read((void *)&data, sizeof(T)); - if (fError > B_OK) { - if (IsSwapping()) - byte_swap(data); - return; - } - - if (fError == 0) - throw B_ERROR; - throw fError; - } - - template - inline void operator()(T data, size_t len) - { - fError = fStream->Read((void *)data, len); - if (fError > B_OK) - return; - - if (fError == 0) - throw B_ERROR; - throw fError; - } - - status_t Status() { return fError; }; - - void SetSwap(bool yesNo) { fSwap = yesNo; }; - bool IsSwapping() { return fSwap; }; - -private: - BDataIO *fStream; - status_t fError; - bool fSwap; -}; - - -class TChecksumHelper { -public: - TChecksumHelper(uchar* buffer) - : fBuffer(buffer), - fBufPtr(buffer) - { - } - - template - inline void Cache(const T &data) - { - *((T*)fBufPtr) = data; - fBufPtr += sizeof (T); - } - - int32 CheckSum(); - -private: - uchar *fBuffer; - uchar *fBufPtr; -}; - - -template -inline status_t -read_helper(BDataIO *stream, T &data) -{ - return normalize_err(stream->Read((void *)&data, sizeof(T))); -} - - -template<> -inline void -byte_swap(double &data) -{ - data = __swap_double(data); -} - - -template<> -inline void -byte_swap(float &data) -{ - data = __swap_float(data); -} - - -template<> -inline void -byte_swap(int64 &data) -{ - data = __swap_int64(data); -} - - -template<> -inline void -byte_swap(int32 &data) -{ - data = __swap_int32(data); -} - - -template<> -inline void -byte_swap(int16 &data) -{ - data = __swap_int16(data); -} - - -template<> -inline void -byte_swap(entry_ref &data) -{ - byte_swap(data.device); - byte_swap(data.directory); -} - -#endif // MESSAGEUTILS_H diff --git a/src/build/libbe/app/Jamfile b/src/build/libbe/app/Jamfile index 0e2b22eb2a..c582c2b85e 100644 --- a/src/build/libbe/app/Jamfile +++ b/src/build/libbe/app/Jamfile @@ -9,8 +9,7 @@ BuildPlatformMergeObjectPIC app_kit.o : Application.cpp AppMisc.cpp Message.cpp - MessageBody.cpp - MessageField.cpp + MessageAdapter.cpp Messenger.cpp MessageUtils.cpp TypeConstants.cpp diff --git a/src/build/libbe/app/Message.cpp b/src/build/libbe/app/Message.cpp index 6ca7380582..9da86360cc 100644 --- a/src/build/libbe/app/Message.cpp +++ b/src/build/libbe/app/Message.cpp @@ -1,558 +1,297 @@ /* - * Copyright 2001-2005, Haiku. + * Copyright 2005-2007, Haiku Inc. All rights reserved. * Distributed under the terms of the MIT License. * * Authors: - * Erik Jaesler (erik@cgsoftware.com) - * DarkWyrm - * Ingo Weinhold + * Michael Lotz */ - -/** BMessage class creates objects that store data and that - * can be processed in a message loop. BMessage objects - * are also used as data containers by the archiving and - * the scripting mechanisms. - */ - -// debugging -//#define DBG(x) x -#define DBG(x) ; -#define PRINT(x) DBG({ printf("[%6ld] ", find_thread(NULL)); printf x; }) - -#include - -#include -#include -#include -#include #include -#include -#include -#include - -#include -#include -#include +#include +#include #include + #include +#include +#include +#include +#include +#include +#include +#include +#include +#include +#include -static const uint32 kMessageMagic = 'FOB1'; -static const uint32 kMessageMagicSwapped = '1BOF'; - -static const uint32 kMessageMagicDano = 'FOB2'; -static const uint32 kMessageMagicDanoSwapped = '2BOF'; - -// flags for the overall message (the bitfield is 1 byte) -#define MSG_FLAG_BIG_ENDIAN 0x01 -#define MSG_FLAG_INCL_TARGET 0x02 -#define MSG_FLAG_INCL_REPLY 0x04 -#define MSG_FLAG_SCRIPT_MSG 0x08 -// These are for future improvement -#if 0 -#define MSG_FLAG_USE_PREFERRED 0x10 -#define MSG_FLAG_REPLY_WANTED 0x20 -#define MSG_FLAG_REPLY_DONE 0x40 -#define MSG_FLAG_IS_REPLY 0x80 - -#define MSG_FLAG_HDR_MASK 0xF0 -#endif - -#define MSG_HEADER_MAX_SIZE 38 -#define MSG_NAME_MAX_SIZE 256 - -// Globals --------------------------------------------------------------------- - -using namespace BPrivate; - -const char* B_SPECIFIER_ENTRY = "specifiers"; -const char* B_PROPERTY_ENTRY = "property"; -const char* B_PROPERTY_NAME_ENTRY = "name"; - -BBlockCache* BMessage::sMsgCache = NULL; +#include +#include +#include +#include +#include -static ssize_t min_hdr_size(); +const char *B_SPECIFIER_ENTRY = "specifiers"; +const char *B_PROPERTY_ENTRY = "property"; +const char *B_PROPERTY_NAME_ENTRY = "name"; -// #pragma mark - - -class BMessage::Header { -public: - Header() {} - Header(const BMessage &message) { ReadFrom(message); } - - status_t SetMagic(uint32 magic); - - status_t ReadFrom(BDataIO &stream); - void ReadFrom(const BMessage &message); - status_t WriteTo(BDataIO &stream, bool calculateCheckSum = true) const; - void WriteTo(BMessage &message) const; - - uint32 CalculateCheckSum() const; - uint32 CalculateHeaderSize() const; - - bool IsSwapped() const { return fSwapped; } - - bool HasTarget() const { return (fFlags & MSG_FLAG_INCL_TARGET); } - void SetTarget(int32 token, bool preferred); - - void Dump() const; - -private: - uint32 fMagic; - int32 fBodySize; - uint32 fWhat; - uint8 fFlags; - int32 fTargetToken; - port_id fReplyPort; - int32 fReplyToken; - team_id fReplyTeam; - bool fPreferredTarget; - bool fReplyRequired; - bool fReplyDone; - bool fIsReply; - bool fSwapped; -}; +BBlockCache *BMessage::sMsgCache = NULL; -status_t -BMessage::Header::SetMagic(uint32 magic) -{ - if (magic == kMessageMagicSwapped) { - fSwapped = true; - } else if (magic == kMessageMagic) { - fSwapped = false; - } else { - // This is *not* a message - return B_NOT_A_MESSAGE; - } - - fMagic = magic; - return B_OK; -} - - -// ReadFrom -status_t -BMessage::Header::ReadFrom(BDataIO &stream) -{ - int32 checkSum; - uchar csBuffer[MSG_HEADER_MAX_SIZE]; - - TReadHelper read_helper(&stream); - TChecksumHelper checksum_helper(csBuffer); - int32 flattenedSize; - - try { - read_helper.SetSwap(fSwapped); - - // get the checksum - read_helper(checkSum); - // get the size - read_helper(flattenedSize); - checksum_helper.Cache(flattenedSize); - // Get the what - read_helper(fWhat); - checksum_helper.Cache(fWhat); - // Get the flags - read_helper(fFlags); - checksum_helper.Cache(fFlags); - - if (fFlags & MSG_FLAG_BIG_ENDIAN) { - // TODO: ??? - // Isn't this already indicated by the byte order of the message version? - } - if (fFlags & MSG_FLAG_INCL_TARGET) { - // Get the target data - read_helper(fTargetToken); - checksum_helper.Cache(fTargetToken); - } - if (fFlags & MSG_FLAG_INCL_REPLY) { - // Get the reply port - read_helper(fReplyPort); - read_helper(fReplyToken); - read_helper(fReplyTeam); - checksum_helper.Cache(fReplyPort); - checksum_helper.Cache(fReplyToken); - checksum_helper.Cache(fReplyTeam); - - // Get the "big flags" - uint8 bigFlags; - // Get the preferred flag - read_helper(bigFlags); - checksum_helper.Cache(bigFlags); - fPreferredTarget = bigFlags; - - // Get the reply requirement flag - read_helper(bigFlags); - checksum_helper.Cache(bigFlags); - fReplyRequired = bigFlags; - - // Get the reply done flag - read_helper(bigFlags); - checksum_helper.Cache(bigFlags); - fReplyDone = bigFlags; - - // Get the "is reply" flag - read_helper(bigFlags); - checksum_helper.Cache(bigFlags); - fIsReply = bigFlags; - } - } catch (status_t& e) { - return e; - } - - fBodySize = flattenedSize - CalculateHeaderSize(); - - if (checkSum != checksum_helper.CheckSum()) - return B_NOT_A_MESSAGE; - - return B_OK; -} - -// ReadFrom -void -BMessage::Header::ReadFrom(const BMessage &message) -{ - fMagic = kMessageMagic; - - fBodySize = message.fBody->FlattenedSize(); - fWhat = message.what; - fFlags = 0; -#ifdef B_HOST_IS_BENDIAN - fFlags |= MSG_FLAG_BIG_ENDIAN; -#endif - if (message.HasSpecifiers()) - fFlags |= MSG_FLAG_SCRIPT_MSG; - if (message.fTarget != B_NULL_TOKEN) - fFlags |= MSG_FLAG_INCL_TARGET; - if (message.fReplyTo.port >= 0 && - message.fReplyTo.target != B_NULL_TOKEN && - message.fReplyTo.team >= 0) { - fFlags |= MSG_FLAG_INCL_REPLY; - } - fTargetToken = message.fTarget; - fReplyPort = message.fReplyTo.port; - fReplyToken = message.fReplyTo.target; - fReplyTeam = message.fReplyTo.team; - fPreferredTarget = message.fPreferred; - fReplyRequired = message.fReplyRequired; - fReplyDone = message.fReplyDone; - fIsReply = message.fIsReply; -} - -// WriteTo -status_t -BMessage::Header::WriteTo(BDataIO &stream, bool calculateCheckSum) const -{ - status_t err = B_OK; - int32 data; - - // Write the version of the binary data format - data = fMagic; - write_helper(&stream, (const void*)&data, sizeof (data), err); - if (!err) { - // compute checksum - data = (calculateCheckSum ? CalculateCheckSum() : 0); - write_helper(&stream, (const void*)&data, sizeof (data), err); - } - if (!err) { - // Write the flattened size of the entire message - data = CalculateHeaderSize() + fBodySize; - write_helper(&stream, (const void*)&data, sizeof (data), err); - } - if (!err) { - // Write the 'what' member - write_helper(&stream, (const void*)&fWhat, sizeof (fWhat), err); - } - if (!err) { - // Write the header flags - write_helper(&stream, (const void*)&fFlags, sizeof (fFlags), err); - } - - // Write targeting info if necessary - if (!err && (fFlags & MSG_FLAG_INCL_TARGET)) { - data = fPreferredTarget ? B_PREFERRED_TOKEN : fTargetToken; - write_helper(&stream, (const void*)&data, sizeof (data), err); - } - - // Write reply info if necessary - if (!err && (fFlags & MSG_FLAG_INCL_REPLY)) { - write_helper(&stream, (const void*)&fReplyPort, sizeof(fReplyPort), - err); - if (!err) { - write_helper(&stream, (const void*)&fReplyToken, - sizeof(fReplyToken), err); - } - if (!err) { - write_helper(&stream, (const void*)&fReplyTeam, - sizeof(fReplyTeam), err); - } - - uint8 bigFlags; - if (!err) { - bigFlags = fPreferredTarget ? 1 : 0; - write_helper(&stream, (const void*)&bigFlags, sizeof(bigFlags), - err); - } - if (!err) - { - bigFlags = fReplyRequired ? 1 : 0; - write_helper(&stream, (const void*)&bigFlags, sizeof(bigFlags), - err); - } - if (!err) - { - bigFlags = fReplyDone ? 1 : 0; - write_helper(&stream, (const void*)&bigFlags, sizeof(bigFlags), - err); - } - if (!err) - { - bigFlags = fIsReply ? 1 : 0; - write_helper(&stream, (const void*)&bigFlags, sizeof(bigFlags), - err); - } - } - - return err; -} - -// WriteTo -void -BMessage::Header::WriteTo(BMessage &message) const -{ - // Make way for the new data - message.MakeEmpty(); - - message.what = fWhat; - - message.fHasSpecifiers = fFlags & MSG_FLAG_SCRIPT_MSG; - - if (fFlags & MSG_FLAG_INCL_TARGET) { - // Get the target data - message.fTarget = fTargetToken; - } - if (fFlags & MSG_FLAG_INCL_REPLY) { - // Get the reply port - message.fReplyTo.port = fReplyPort; - message.fReplyTo.target = fReplyToken; - message.fReplyTo.team = fReplyTeam; - - message.fWasDelivered = true; - - message.fPreferred = fPreferredTarget; - if (fPreferredTarget) - message.fTarget = B_PREFERRED_TOKEN; - - message.fReplyRequired = fReplyRequired; - message.fReplyDone = fReplyDone; - message.fIsReply = fIsReply; - } -} - -// CalculateCheckSum -uint32 -BMessage::Header::CalculateCheckSum() const -{ - uchar buffer[MSG_HEADER_MAX_SIZE]; - BMemoryIO stream(buffer, sizeof(buffer)); - WriteTo(stream, false); - int32 size = stream.Position(); - return _checksum_(buffer + 8, size - 8); -} - -// CalculateHeaderSize -uint32 -BMessage::Header::CalculateHeaderSize() const -{ - ssize_t size = min_hdr_size(); - - if (fTargetToken != B_NULL_TOKEN) - size += sizeof (fTargetToken); - - if (fReplyPort >= 0 && fReplyToken != B_NULL_TOKEN && fReplyTeam >= 0) { - size += sizeof (fReplyPort); - size += sizeof (fReplyToken); - size += sizeof (fReplyTeam); - - size += 4; // For the "big" flags - } - - return size; -} - -// SetTarget -void -BMessage::Header::SetTarget(int32 token, bool preferred) -{ - fTargetToken = token; - if (fTargetToken == B_NULL_TOKEN) - fFlags &= ~MSG_FLAG_INCL_TARGET; - else - fFlags |= MSG_FLAG_INCL_TARGET; - - fPreferredTarget = preferred; -} - -// Dump -void -BMessage::Header::Dump() const -{ - printf("BMessage::Header:\n"); - printf(" magic: %lx\n", fMagic); - printf(" body size: %ld\n", fBodySize); - printf(" what: %lx\n", fWhat); - printf(" flags: %x\n", fFlags); - printf(" target token: %ld\n", fTargetToken); - printf(" reply port: %ld\n", fReplyPort); - printf(" reply token: %ld\n", fReplyToken); - printf(" reply team: %ld\n", fReplyTeam); - printf(" preferred target: %d\n", fPreferredTarget); - printf(" reply required: %d\n", fReplyRequired); - printf(" reply done: %d\n", fReplyDone); - printf(" is reply: %d\n", fIsReply); - printf(" swapped: %d\n", fSwapped); -} - -// #pragma mark - - -void BMessage::_ReservedMessage1() {} -void BMessage::_ReservedMessage2() {} -void BMessage::_ReservedMessage3() {} - -//------------------------------------------------------------------------------ BMessage::BMessage() - : what(0), fBody(NULL) { - init_data(); + _InitCommon(); } -//------------------------------------------------------------------------------ -BMessage::BMessage(uint32 w) - : fBody(NULL) + + +BMessage::BMessage(BMessage *other) { - init_data(); - what = w; + _InitCommon(); + *this = *other; } -//------------------------------------------------------------------------------ -BMessage::BMessage(const BMessage& a_message) - : fBody(NULL) + + +BMessage::BMessage(uint32 _what) { - init_data(); - *this = a_message; + _InitCommon(); + fHeader->what = what = _what; } -//------------------------------------------------------------------------------ -BMessage::BMessage(BMessage *a_message) - : fBody(NULL) + + +BMessage::BMessage(const BMessage &other) { - init_data(); - *this = *a_message; + _InitCommon(); + *this = other; } -//------------------------------------------------------------------------------ + + BMessage::~BMessage() { - if (IsSourceWaiting()) - { -// SendReply(B_NO_REPLY); - } - delete fBody; + _Clear(); } -//------------------------------------------------------------------------------ -BMessage& BMessage::operator=(const BMessage& msg) + + +BMessage & +BMessage::operator=(const BMessage &other) { - what = msg.what; + _Clear(); - link = msg.link; - fTarget = msg.fTarget; - fOriginal = msg.fOriginal; - fChangeCount = msg.fChangeCount; - fCurSpecifier = msg.fCurSpecifier; - fPtrOffset = msg.fPtrOffset; + fHeader = (message_header *)malloc(sizeof(message_header)); + memcpy(fHeader, other.fHeader, sizeof(message_header)); - fEntries = msg.fEntries; + // Clear some header flags inherited from the original message that don't + // apply to the clone. + fHeader->flags &= ~(MESSAGE_FLAG_REPLY_REQUIRED | MESSAGE_FLAG_REPLY_DONE + | MESSAGE_FLAG_IS_REPLY | MESSAGE_FLAG_WAS_DELIVERED + | MESSAGE_FLAG_WAS_DROPPED | MESSAGE_FLAG_PASS_BY_AREA); + // Note, that BeOS R5 seems to keep the reply info. - fReplyTo.port = msg.fReplyTo.port; - fReplyTo.target = msg.fReplyTo.target; - fReplyTo.team = msg.fReplyTo.team; - fReplyTo.preferred = msg.fReplyTo.preferred; + if (fHeader->fields_size > 0) { + fFields = (field_header *)malloc(fHeader->fields_size); + memcpy(fFields, other.fFields, fHeader->fields_size); + } - fPreferred = msg.fPreferred; - fReplyRequired = msg.fReplyRequired; - fReplyDone = msg.fReplyDone; - fIsReply = msg.fIsReply; - fWasDelivered = msg.fWasDelivered; - fReadOnly = msg.fReadOnly; - fHasSpecifiers = msg.fHasSpecifiers; + if (fHeader->data_size > 0) { + fData = (uint8 *)malloc(fHeader->data_size); + memcpy(fData, other.fData, fHeader->data_size); + } + + fHeader->shared_area = -1; + fHeader->fields_available = 0; + fHeader->data_available = 0; + fHeader->what = what = other.what; - *fBody = *(msg.fBody); return *this; } -//------------------------------------------------------------------------------ -void BMessage::init_data() + + +void * +BMessage::operator new(size_t size) +{ + if (!sMsgCache) + sMsgCache = new BBlockCache(10, sizeof(BMessage), B_OBJECT_CACHE); + + return sMsgCache->Get(size); +} + + +void * +BMessage::operator new(size_t, void *pointer) +{ + return pointer; +} + + +void +BMessage::operator delete(void *pointer, size_t size) +{ + sMsgCache->Save(pointer, size); +} + + +status_t +BMessage::_InitCommon() { what = 0; - link = NULL; - fTarget = B_NULL_TOKEN; + fHeader = NULL; + fFields = NULL; + fData = NULL; + fOriginal = NULL; - fChangeCount = 0; - fCurSpecifier = -1; - fPtrOffset = 0; + fQueueLink = NULL; - fEntries = NULL; + return _InitHeader(); +} - fReplyTo.port = -1; - fReplyTo.target = B_NULL_TOKEN; - fReplyTo.team = -1; - fReplyTo.preferred = false; - fPreferred = false; - fReplyRequired = false; - fReplyDone = false; - fIsReply = false; - fWasDelivered = false; - fReadOnly = false; - fHasSpecifiers = false; +status_t +BMessage::_InitHeader() +{ + fHeader = (message_header *)malloc(sizeof(message_header)); + memset(fHeader, 0, sizeof(message_header) - sizeof(fHeader->hash_table)); - if (fBody) - { - fBody->MakeEmpty(); + fHeader->format = MESSAGE_FORMAT_HAIKU; + fHeader->flags = MESSAGE_FLAG_VALID; + fHeader->what = what; + fHeader->current_specifier = -1; + fHeader->shared_area = -1; + + fHeader->target = B_NULL_TOKEN; + fHeader->reply_target = B_NULL_TOKEN; + fHeader->reply_port = -1; + fHeader->reply_team = -1; + + // initializing the hash table to -1 because 0 is a valid index + fHeader->hash_table_size = MESSAGE_BODY_HASH_TABLE_SIZE; + memset(&fHeader->hash_table, 255, sizeof(fHeader->hash_table)); + return B_OK; +} + + +status_t +BMessage::_Clear() +{ + free(fHeader); + fHeader = NULL; + free(fFields); + fFields = NULL; + free(fData); + fData = NULL; + + delete fOriginal; + fOriginal = NULL; + + return B_OK; +} + + +status_t +BMessage::GetInfo(type_code typeRequested, int32 index, char **nameFound, + type_code *typeFound, int32 *countFound) const +{ + if (typeRequested == B_ANY_TYPE) { + if (index >= fHeader->field_count) + return B_BAD_INDEX; + + if (nameFound) + *nameFound = (char *)fData + fFields[index].offset; + if (typeFound) + *typeFound = fFields[index].type; + if (countFound) + *countFound = fFields[index].count; + return B_OK; } - else - { - fBody = new BPrivate::BMessageBody; + + int32 counter = -1; + field_header *field = fFields; + for (int32 i = 0; i < fHeader->field_count; i++, field++) { + if (field->type == typeRequested) + counter++; + + if (counter == index) { + if (nameFound) + *nameFound = (char *)fData + field->offset; + if (typeFound) + *typeFound = field->type; + if (countFound) + *countFound = field->count; + return B_OK; + } } + + if (counter == -1) + return B_BAD_TYPE; + + return B_BAD_INDEX; } -//------------------------------------------------------------------------------ -status_t BMessage::GetInfo(type_code typeRequested, int32 which, char** name, - type_code* typeReturned, int32* count) const + + +status_t +BMessage::GetInfo(const char *name, type_code *typeFound, int32 *countFound) + const { - return fBody->GetInfo(typeRequested, which, name, typeReturned, count); + if (countFound) + *countFound = 0; + + field_header *field = NULL; + status_t result = _FindField(name, B_ANY_TYPE, &field); + if (result < B_OK || !field) + return result; + + if (typeFound) + *typeFound = field->type; + if (countFound) + *countFound = field->count; + + return B_OK; } -//------------------------------------------------------------------------------ -status_t BMessage::GetInfo(const char* name, type_code* type, int32* c) const + + +status_t +BMessage::GetInfo(const char *name, type_code *typeFound, bool *fixedSize) + const { - return fBody->GetInfo(name, type, c); + field_header *field = NULL; + status_t result = _FindField(name, B_ANY_TYPE, &field); + if (result < B_OK || !field) + return result; + + if (typeFound) + *typeFound = field->type; + if (fixedSize) + *fixedSize = field->flags & FIELD_FLAG_FIXED_SIZE; + + return B_OK; } -//------------------------------------------------------------------------------ -status_t BMessage::GetInfo(const char* name, type_code* type, - bool* fixed_size) const + + +int32 +BMessage::CountNames(type_code type) const { - return fBody->GetInfo(name, type, fixed_size); + if (type == B_ANY_TYPE) + return fHeader->field_count; + + int32 count = 0; + field_header *field = fFields; + for (int32 i = 0; i < fHeader->field_count; i++, field++) { + if (field->type == type) + count++; + } + + return count; } -//------------------------------------------------------------------------------ -int32 BMessage::CountNames(type_code type) const + + +bool +BMessage::IsEmpty() const { - return fBody->CountNames(type); + return fHeader->field_count == 0; } -//------------------------------------------------------------------------------ -bool BMessage::IsEmpty() const -{ - return fBody->IsEmpty(); -} -//------------------------------------------------------------------------------ -bool BMessage::IsSystem() const + + +bool +BMessage::IsSystem() const { char a = char(what >> 24); char b = char(what >> 16); @@ -566,61 +305,231 @@ bool BMessage::IsSystem() const // characters limited to uppercase letters and the underbar // Between that and what's in AppDefs.h, this algo seems like a safe bet: if (a == '_' && isupper(b) && isupper(c) && isupper(d)) - { return true; - } return false; } -//------------------------------------------------------------------------------ -bool BMessage::IsReply() const + + +bool +BMessage::IsReply() const { - return fIsReply; + return fHeader->flags & MESSAGE_FLAG_IS_REPLY; } -//------------------------------------------------------------------------------ -void BMessage::PrintToStream() const + + +template static uint8 * +print_to_stream_type(uint8* pointer) { - printf("\nBMessage: what = (0x%lX or %ld)\n", what, what); - fBody->PrintToStream(); + Type *item = (Type *)pointer; + item->PrintToStream(); + return (uint8 *)(item+1); } -//------------------------------------------------------------------------------ -status_t BMessage::Rename(const char* old_entry, const char* new_entry) + + +template static uint8 * +print_type(const char* format, uint8* pointer) { - return fBody->Rename(old_entry, new_entry); + Type *item = (Type *)pointer; + printf(format, *item, *item); + return (uint8 *)(item+1); } -//------------------------------------------------------------------------------ -bool BMessage::WasDelivered() const + + +void +BMessage::PrintToStream() const { - return fWasDelivered; + _PrintToStream(""); + printf("}\n"); } -//------------------------------------------------------------------------------ -bool BMessage::IsSourceWaiting() const + + +void +BMessage::_PrintToStream(const char* indent) const { - return fReplyRequired && !fReplyDone; + int32 value = B_BENDIAN_TO_HOST_INT32(what); + printf("BMessage("); + if (isprint(*(char *)&value)) { + printf("'%.4s'", (char *)&value); + } else + printf("0x%lx", what); + printf(") {\n"); + + field_header *field = fFields; + for (int32 i = 0; i < fHeader->field_count; i++, field++) { + value = B_BENDIAN_TO_HOST_INT32(field->type); + ssize_t size = 0; + if (field->flags & FIELD_FLAG_FIXED_SIZE) + size = field->data_size / field->count; + + uint8 *pointer = fData + field->offset + field->name_length; + + for (int32 j=0; jcount; j++) { + if (field->count == 1) { + printf("%s %s = ", indent, + (char *)(fData + field->offset)); + } else { + printf("%s %s[%ld] = ", indent, + (char *)(fData + field->offset), j); + } + + switch (field->type) { + case B_RECT_TYPE: + pointer = print_to_stream_type(pointer); + break; + + case B_POINT_TYPE: + pointer = print_to_stream_type(pointer); + break; + + case B_STRING_TYPE: { + ssize_t size = *(ssize_t *)pointer; + pointer += sizeof(ssize_t); + printf("string(\"%s\", %ld bytes)\n", (char *)pointer, size); + pointer += size; + break; + } + + case B_INT8_TYPE: + pointer = print_type("int8(0x%hx or %d or \'%.1s\')\n", pointer); + break; + + case B_INT16_TYPE: + pointer = print_type("int16 (0x%x or %d)\n", pointer); + break; + + case B_INT32_TYPE: + pointer = print_type("int32(0x%lx or %ld)\n", pointer); + break; + + case B_INT64_TYPE: + pointer = print_type("int64(0x%Lx or %Ld)\n", pointer); + break; + + case B_BOOL_TYPE: + printf("bool(%s)\n", *((bool *)pointer)!= 0 ? "true" : "false"); + pointer += sizeof(bool); + break; + + case B_FLOAT_TYPE: + pointer = print_type("float(%.4f)\n", pointer); + break; + + case B_DOUBLE_TYPE: + pointer = print_type("double(%.8f)\n", pointer); + break; + + case B_REF_TYPE: { + ssize_t size = *(ssize_t *)pointer; + pointer += sizeof(ssize_t); + entry_ref ref; + BPrivate::entry_ref_unflatten(&ref, (char *)pointer, size); + + printf("entry_ref(device=%ld, directory=%lld, name=\"%s\", ", + ref.device, ref.directory, ref.name); + + BPath path(&ref); + printf("path=\"%s\")\n", path.Path()); + pointer += size; + break; + } + + case B_MESSAGE_TYPE: + { + char buffer[1024]; + sprintf(buffer, "%s ", indent); + + BMessage message; + const ssize_t size = *(const ssize_t *)pointer; + pointer += sizeof(ssize_t); + if (message.Unflatten((const char *)pointer)!=B_OK) { + fprintf(stderr, "couldn't unflatten item %ld\n", i); + break; + } + message._PrintToStream(buffer); + printf("%s }\n", indent); + pointer += size; + break; + } + + default: { + printf("(type = '%.4s')(size = %ld)\n", (char *)&value, size); + } + } + } + } } -//------------------------------------------------------------------------------ -BMessenger BMessage::ReturnAddress() const + + +status_t +BMessage::Rename(const char *oldEntry, const char *newEntry) { - if (WasDelivered()) - { - BMessenger messenger; - BMessenger::Private(messenger).SetTo(fReplyTo.team, fReplyTo.port, - fReplyTo.target, fReplyTo.preferred); - return messenger; + if (!oldEntry || !newEntry) + return B_BAD_VALUE; + + uint32 hash = _HashName(oldEntry) % fHeader->hash_table_size; + int32 *nextField = &fHeader->hash_table[hash]; + + while (*nextField >= 0) { + field_header *field = &fFields[*nextField]; + + if (strncmp((const char *)(fData + field->offset), oldEntry, + field->name_length) == 0) { + // nextField points to the field for oldEntry, save it and unlink + int32 index = *nextField; + *nextField = field->next_field; + field->next_field = -1; + + hash = _HashName(newEntry) % fHeader->hash_table_size; + nextField = &fHeader->hash_table[hash]; + while (*nextField >= 0) + nextField = &fFields[*nextField].next_field; + *nextField = index; + + int32 oldLength = field->name_length; + field->name_length = strlen(newEntry) + 1; + _ResizeData(field->offset, field->name_length - oldLength); + memcpy(fData + field->offset, newEntry, field->name_length); + return B_OK; + } + + nextField = &field->next_field; } + return B_NAME_NOT_FOUND; +} + + +bool +BMessage::WasDelivered() const +{ + return fHeader->flags & MESSAGE_FLAG_WAS_DELIVERED; +} + + +bool +BMessage::IsSourceWaiting() const +{ + return (fHeader->flags & MESSAGE_FLAG_REPLY_REQUIRED) + && !(fHeader->flags & MESSAGE_FLAG_REPLY_DONE); +} + + +BMessenger +BMessage::ReturnAddress() const +{ return BMessenger(); } -//------------------------------------------------------------------------------ -const BMessage* BMessage::Previous() const + + +const BMessage * +BMessage::Previous() const { - // TODO: test - // In particular, look to see if the "_previous_" field is used in R5 - if (!fOriginal) - { - BMessage* fOriginal = new BMessage; - if (FindMessage("_previous_", fOriginal) != B_OK) - { + /* ToDo: test if the "_previous_" field is used in R5 */ + if (!fOriginal) { + fOriginal = new BMessage(); + + if (FindMessage("_previous_", fOriginal) != B_OK) { delete fOriginal; fOriginal = NULL; } @@ -628,1116 +537,803 @@ const BMessage* BMessage::Previous() const return fOriginal; } -//------------------------------------------------------------------------------ -bool BMessage::WasDropped() const + + +bool +BMessage::WasDropped() const { - return fReadOnly; + return fHeader->flags & MESSAGE_FLAG_WAS_DROPPED; } -//------------------------------------------------------------------------------ -BPoint BMessage::DropPoint(BPoint* offset) const + + +BPoint +BMessage::DropPoint(BPoint *offset) const { - // TODO: Where do we get this stuff??? if (offset) - { *offset = FindPoint("_drop_offset_"); - } + return FindPoint("_drop_point_"); } -//------------------------------------------------------------------------------ -#if 0 -template -status_t SendReplyHelper(BMessage* the_message, BMessage* the_reply, - Sender& the_sender) + +ssize_t +BMessage::FlattenedSize() const { - BMessenger messenger(the_message->fReplyTo.team, the_message->fReplyTo.port, - the_message->fReplyTo.target, - the_message->fReplyTo.preferred); - if (the_message->fReplyRequired) - { - if (the_message->fReplyDone) - { - return B_DUPLICATE_REPLY; - } - the_message->fReplyDone = true; - the_reply->fIsReply = true; - status_t err = the_sender.Send(messenger, the_reply); - the_reply->fIsReply = false; - if (err) - { - if (set_port_owner(messenger.fPort, messenger.fTeam) == B_BAD_TEAM_ID) - { - delete_port(messenger.fPort); - } - } - return err; - } - // no reply required - if (!the_message->fWasDelivered) - { - return B_BAD_REPLY; - } - -#if 0 - char tmp[0x800]; - ssize_t size; - char* p = stack_flatten(tmp, sizeof(tmp), true /* include reply */, &size); - the_reply->AddData("_previous_", B_RAW_TYPE, p ? p : tmp, &size); - if (p) - { - free(p); - } -#endif - the_reply->AddMessage("_previous_", the_message); - the_reply->fIsReply = true; - status_t err = the_sender.Send(messenger, the_reply); - the_reply->fIsReply = false; - the_reply->RemoveName("_previous_"); - return err; -}; -#endif -//------------------------------------------------------------------------------ -#if 0 -struct Sender1 -{ - BMessenger& reply_to; - bigtime_t timeout; - - Sender1(BMessenger& m, bigtime_t t) : reply_to(m), timeout(t) {;} - - status_t Send(BMessenger& messenger, BMessage* the_reply) - { - return messenger.SendMessage(the_reply, reply_to, timeout); - } -}; -status_t BMessage::SendReply(BMessage* the_reply, BMessenger reply_to, - bigtime_t timeout) -{ - Sender1 mySender(reply_to, timeout); - return SendReplyHelper(this, the_reply, mySender); -} -#endif - -//------------------------------------------------------------------------------ -#if 0 -struct Sender2 -{ - BMessage* reply_to_reply; - bigtime_t send_timeout; - bigtime_t reply_timeout; - - Sender2(BMessage* m, bigtime_t t1, bigtime_t t2) - : reply_to_reply(m), send_timeout(t1), reply_timeout(t2) {;} - - status_t Send(BMessenger& messenger, BMessage* the_reply) - { - return messenger.SendMessage(the_reply, reply_to_reply, - send_timeout, reply_timeout); - } -}; -status_t BMessage::SendReply(BMessage* the_reply, BMessage* reply_to_reply, - bigtime_t send_timeout, bigtime_t reply_timeout) -{ - Sender2 mySender(reply_to_reply, send_timeout, reply_timeout); - return SendReplyHelper(this, the_reply, mySender); -} -#endif - -//------------------------------------------------------------------------------ -ssize_t BMessage::FlattenedSize() const -{ - return calc_hdr_size(0) + fBody->FlattenedSize(); -} -//------------------------------------------------------------------------------ -status_t BMessage::Flatten(char* buffer, ssize_t size) const -{ - return real_flatten(buffer, size); -} -//------------------------------------------------------------------------------ -status_t BMessage::Flatten(BDataIO* stream, ssize_t* size) const -{ - status_t err = B_OK; - ssize_t len = FlattenedSize(); - char* buffer = new(std::nothrow) char[len]; - if (buffer) - { - err = Flatten(buffer, len); - if (!err) - { - // size is an optional parameter, don't crash on NULL - if (size != NULL) - { - *size = len; - } - err = stream->Write(buffer, len); - if (err > B_OK) - err = B_OK; - } - - delete[] buffer; - } - else - { - err = B_NO_MEMORY; - } - - return err; + return BPrivate::MessageAdapter::FlattenedSize(MESSAGE_FORMAT_R5, this); } status_t -BMessage::Unflatten(const char* buffer) +BMessage::Flatten(char *buffer, ssize_t size) const +{ + return BPrivate::MessageAdapter::Flatten(MESSAGE_FORMAT_R5, this, buffer, + &size); +} + + +status_t +BMessage::Flatten(BDataIO *stream, ssize_t *size) const +{ + return BPrivate::MessageAdapter::Flatten(MESSAGE_FORMAT_R5, this, stream, + size); +} + + +ssize_t +BMessage::_NativeFlattenedSize() const +{ + return sizeof(message_header) + fHeader->fields_size + fHeader->data_size; +} + + +status_t +BMessage::_NativeFlatten(char *buffer, ssize_t size) const { if (!buffer) return B_BAD_VALUE; - uint32 magic = *(uint32*)buffer; + if (!fHeader) + return B_NO_INIT; - // we support several message formats - this list is ordered - // by importance and frequency + /* we have to sync the what code as it is a public member */ + fHeader->what = what; - if (magic == kMessageMagic) { - // it appears to be a normal flattened BMessage - BMemoryIO memoryStream(buffer, ((uint32*)buffer)[2]); - return Unflatten(&memoryStream); - } + memcpy(buffer, fHeader, min_c(sizeof(message_header), (size_t)size)); + buffer += sizeof(message_header); + size -= sizeof(message_header); - // check whether this is a KMessage -// if (((KMessage::Header*)buffer)->magic -// == KMessage::kMessageHeaderMagic) -// return _UnflattenKMessage(buffer); + memcpy(buffer, fFields, min_c(fHeader->fields_size, size)); + buffer += fHeader->fields_size; + size -= fHeader->fields_size; - if (magic == kMessageMagicSwapped) { - // it appears to be a swapped flattened BMessage - uint32 size = ((uint32*)buffer)[2]; + memcpy(buffer, fData, min_c(fHeader->data_size, size)); + if (size >= fHeader->data_size) + return B_OK; - BMemoryIO memoryStream(buffer, __swap_int32(size)); - return Unflatten(&memoryStream); - } - -// if (magic == kMessageMagicDano || magic == kMessageMagicDanoSwapped) { -// // dano style message -// BMemoryIO memoryStream(buffer, BPrivate::dano_message_size(buffer)); -// return Unflatten(&memoryStream); -// } - - return B_NOT_A_MESSAGE; + return B_NO_MEMORY; } status_t -BMessage::Unflatten(BDataIO* stream) +BMessage::_NativeFlatten(BDataIO *stream, ssize_t *size) const { - TReadHelper reader(stream); - Header header; - status_t status = B_OK; + if (!stream) + return B_BAD_VALUE; - // ToDo: while reading from a stream is certainly more convenient than - // from a buffer, it causes a lot of unnecessary copies, and therefore - // probably shouldn't be the preferred (or only) route. + if (!fHeader) + return B_NO_INIT; - try { - uint32 magic; - reader(magic); + /* we have to sync the what code as it is a public member */ + fHeader->what = what; - status = header.SetMagic(magic); - if (status < B_OK) { - // we support reading Dano messages from disk as well -// if (magic == kMessageMagicDano) -// return BPrivate::unflatten_dano_message(magic, *stream, *this); + ssize_t result1 = stream->Write(fHeader, sizeof(message_header)); + if (result1 != sizeof(message_header)) + return (result1 >= 0 ? B_ERROR : result1); - return status; - } - - status = header.ReadFrom(*stream); - if (status < B_OK) { - printf("BMessage::Unflatten(): Reading the header failed: %lx\n", status); - return status; - } - - header.WriteTo(*this); - bool swap = header.IsSwapped(); - - uint32 count; - uint32 dataLen; - uint8 nameLen; - char name[MSG_NAME_MAX_SIZE]; - unsigned char* databuffer = NULL; - - int8 flags; - reader(flags); - - while (flags != MSG_LAST_ENTRY) { - type_code type; - reader(type); - - // Is there more than one data item? - if (flags & MSG_FLAG_SINGLE_ITEM) { - count = 1; - if (flags & MSG_FLAG_MINI_DATA) { - uint8 littleLen; - reader(littleLen); - dataLen = littleLen; - } else - reader(dataLen); - } else { - // Is there a little data? - if (flags & MSG_FLAG_MINI_DATA) { - // Get item count (1 byte) - uint8 littleCount; - reader(littleCount); - count = littleCount; - - // Get data length (1 byte) - uint8 littleLen; - reader(littleLen); - dataLen = littleLen; - } else { - // Is there a lot of data? - // Get item count (4 bytes) - reader(count); - // Get data length (4 bytes) - reader(dataLen); - } - } - - // Get the name length (1 byte) - reader(nameLen); - // Get the name (name length bytes) - reader(name, nameLen); - name[nameLen] = '\0'; - - // Copy the data into a new buffer to byte align it - databuffer = (unsigned char*)realloc(databuffer, dataLen); - if (!databuffer) - throw B_NO_MEMORY; - // Get the data - reader(databuffer, dataLen); - - if (swap) { - // Is the data fixed size? - if ((flags & MSG_FLAG_FIXED_SIZE) != 0) { - // Make sure to swap the data - status = swap_data(type, (void*)databuffer, dataLen, - B_SWAP_ALWAYS); - if (status < B_OK) - throw status; - } else if (type == B_REF_TYPE) { - // Is the data variable size? - // Apparently, entry_refs are the only variable-length data - // explicitely swapped -- the dev_t and ino_t - // specifically - byte_swap(*(entry_ref*)databuffer); - } - } - - // Add each data field to the message - uint32 itemSize = 0; - if (flags & MSG_FLAG_FIXED_SIZE) - itemSize = dataLen / count; - - unsigned char* dataPtr = databuffer; - - for (uint32 i = 0; i < count; ++i) { - // Line up for the next item - if (i) { - if (flags & MSG_FLAG_FIXED_SIZE) { - dataPtr += itemSize; - } else { - // Have to account for 8-byte boundary padding - // We add 4 because padding as calculated during - // flattening includes the four-byte size header - dataPtr += itemSize + calc_padding(itemSize + 4, 8); - } - } - - if ((flags & MSG_FLAG_FIXED_SIZE) == 0) { - itemSize = *(uint32*)dataPtr; - dataPtr += sizeof (uint32); - } - - status = AddData(name, type, dataPtr, itemSize, - flags & MSG_FLAG_FIXED_SIZE); - if (status < B_OK) - throw status; - } - - reader(flags); - } - } catch (status_t& e) { - status = e; + ssize_t result2 = 0; + if (fHeader->fields_size > 0) { + result2 = stream->Write(fFields, fHeader->fields_size); + if (result2 != fHeader->fields_size) + return (result2 >= 0 ? B_ERROR : result2); } - return status; + ssize_t result3 = 0; + if (fHeader->data_size > 0) { + result3 = stream->Write(fData, fHeader->data_size); + if (result3 != fHeader->data_size) + return (result3 >= 0 ? B_ERROR : result3); + } + + if (size) + *size = result1 + result2 + result3; + + return B_OK; } -//------------------------------------------------------------------------------ -status_t BMessage::AddSpecifier(const char* property) + + +status_t +BMessage::Unflatten(const char *flatBuffer) +{ + if (!flatBuffer) + return B_BAD_VALUE; + + uint32 format = *(uint32 *)flatBuffer; + if (format != MESSAGE_FORMAT_HAIKU) + return BPrivate::MessageAdapter::Unflatten(format, this, flatBuffer); + + // native message unflattening + + _Clear(); + + fHeader = (message_header *)malloc(sizeof(message_header)); + if (!fHeader) + return B_NO_MEMORY; + + memcpy(fHeader, flatBuffer, sizeof(message_header)); + flatBuffer += sizeof(message_header); + + if (fHeader->format != MESSAGE_FORMAT_HAIKU + || !(fHeader->flags & MESSAGE_FLAG_VALID)) { + free(fHeader); + fHeader = NULL; + _InitHeader(); + return B_BAD_VALUE; + } + + fHeader->fields_available = 0; + fHeader->data_available = 0; + what = fHeader->what; + + fHeader->shared_area = -1; + + if (fHeader->fields_size > 0) { + fFields = (field_header *)malloc(fHeader->fields_size); + if (!fFields) + return B_NO_MEMORY; + + memcpy(fFields, flatBuffer, fHeader->fields_size); + flatBuffer += fHeader->fields_size; + } + + if (fHeader->data_size > 0) { + fData = (uint8 *)malloc(fHeader->data_size); + if (!fData) + return B_NO_MEMORY; + + memcpy(fData, flatBuffer, fHeader->data_size); + } + + return B_OK; +} + + +status_t +BMessage::Unflatten(BDataIO *stream) +{ + if (!stream) + return B_BAD_VALUE; + + uint32 format = 0; + stream->Read(&format, sizeof(uint32)); + if (format != MESSAGE_FORMAT_HAIKU) + return BPrivate::MessageAdapter::Unflatten(format, this, stream); + + // native message unflattening + + _Clear(); + + fHeader = (message_header *)malloc(sizeof(message_header)); + if (!fHeader) + return B_NO_MEMORY; + + fHeader->format = format; + uint8 *header = (uint8 *)fHeader; + ssize_t result = stream->Read(header + sizeof(uint32), + sizeof(message_header) - sizeof(uint32)); + result -= sizeof(message_header) - sizeof(uint32); + + if (result != B_OK || fHeader->format != MESSAGE_FORMAT_HAIKU + || !(fHeader->flags & MESSAGE_FLAG_VALID)) { + free(fHeader); + fHeader = NULL; + _InitHeader(); + return B_BAD_VALUE; + } + + fHeader->fields_available = 0; + fHeader->data_available = 0; + what = fHeader->what; + + fHeader->shared_area = -1; + + if (result == B_OK && fHeader->fields_size > 0) { + fFields = (field_header *)malloc(fHeader->fields_size); + if (!fFields) + return B_NO_MEMORY; + + result = stream->Read(fFields, fHeader->fields_size); + result -= fHeader->fields_size; + } + + if (result == B_OK && fHeader->data_size > 0) { + fData = (uint8 *)malloc(fHeader->data_size); + if (!fData) + return B_NO_MEMORY; + + result = stream->Read(fData, fHeader->data_size); + result -= fHeader->data_size; + } + + if (result < B_OK) + return B_BAD_VALUE; + + return B_OK; +} + + +status_t +BMessage::AddSpecifier(const char *property) { BMessage message(B_DIRECT_SPECIFIER); - status_t err = message.AddString(B_PROPERTY_ENTRY, property); - if (err) - return err; + status_t result = message.AddString(B_PROPERTY_ENTRY, property); + if (result < B_OK) + return result; return AddSpecifier(&message); } -//------------------------------------------------------------------------------ -status_t BMessage::AddSpecifier(const char* property, int32 index) + + +status_t +BMessage::AddSpecifier(const char *property, int32 index) { BMessage message(B_INDEX_SPECIFIER); - status_t err = message.AddString(B_PROPERTY_ENTRY, property); - if (err) - return err; + status_t result = message.AddString(B_PROPERTY_ENTRY, property); + if (result < B_OK) + return result; - err = message.AddInt32("index", index); - if (err) - return err; + result = message.AddInt32("index", index); + if (result < B_OK) + return result; return AddSpecifier(&message); } -//------------------------------------------------------------------------------ -status_t BMessage::AddSpecifier(const char* property, int32 index, int32 range) + + +status_t +BMessage::AddSpecifier(const char *property, int32 index, int32 range) { if (range < 0) return B_BAD_VALUE; BMessage message(B_RANGE_SPECIFIER); - status_t err = message.AddString(B_PROPERTY_ENTRY, property); - if (err) - return err; + status_t result = message.AddString(B_PROPERTY_ENTRY, property); + if (result < B_OK) + return result; - err = message.AddInt32("index", index); - if (err) - return err; + result = message.AddInt32("index", index); + if (result < B_OK) + return result; - err = message.AddInt32("range", range); - if (err) - return err; + result = message.AddInt32("range", range); + if (result < B_OK) + return result; return AddSpecifier(&message); } -//------------------------------------------------------------------------------ -status_t BMessage::AddSpecifier(const char* property, const char* name) + + +status_t +BMessage::AddSpecifier(const char *property, const char *name) { BMessage message(B_NAME_SPECIFIER); - status_t err = message.AddString(B_PROPERTY_ENTRY, property); - if (err) - return err; + status_t result = message.AddString(B_PROPERTY_ENTRY, property); + if (result < B_OK) + return result; - err = message.AddString(B_PROPERTY_NAME_ENTRY, name); - if (err) - return err; + result = message.AddString(B_PROPERTY_NAME_ENTRY, name); + if (result < B_OK) + return result; return AddSpecifier(&message); } -//------------------------------------------------------------------------------ -status_t BMessage::AddSpecifier(const BMessage* specifier) + + +status_t +BMessage::AddSpecifier(const BMessage *specifier) { - status_t err = AddMessage(B_SPECIFIER_ENTRY, specifier); - if (!err) - { - ++fCurSpecifier; - fHasSpecifiers = true; - } - return err; -} -//------------------------------------------------------------------------------ -status_t BMessage::SetCurrentSpecifier(int32 index) -{ - type_code type; - int32 count; - status_t err = GetInfo(B_SPECIFIER_ENTRY, &type, &count); - if (err) - return err; - - if (index < 0 || index >= count) - return B_BAD_INDEX; - - fCurSpecifier = index; + status_t result = AddMessage(B_SPECIFIER_ENTRY, specifier); + if (result < B_OK) + return result; + fHeader->current_specifier++; + fHeader->flags |= MESSAGE_FLAG_HAS_SPECIFIERS; return B_OK; } -//------------------------------------------------------------------------------ -status_t BMessage::GetCurrentSpecifier(int32* index, BMessage* specifier, - int32* what, const char** property) const + + +status_t +BMessage::SetCurrentSpecifier(int32 index) { - if (fCurSpecifier == -1 || !WasDelivered()) + if (index < 0) + return B_BAD_INDEX; + + type_code type; + int32 count; + status_t result = GetInfo(B_SPECIFIER_ENTRY, &type, &count); + if (result < B_OK) + return result; + + if (index > count) + return B_BAD_INDEX; + + fHeader->current_specifier = index; + return B_OK; +} + + +status_t +BMessage::GetCurrentSpecifier(int32 *index, BMessage *specifier, int32 *what, + const char **property) const +{ + if (index) + *index = fHeader->current_specifier; + + if (fHeader->current_specifier < 0 + || !(fHeader->flags & MESSAGE_FLAG_WAS_DELIVERED)) return B_BAD_SCRIPT_SYNTAX; - if (index) - *index = fCurSpecifier; - - if (specifier) - { - if (FindMessage(B_SPECIFIER_ENTRY, fCurSpecifier, specifier)) + if (specifier) { + if (FindMessage(B_SPECIFIER_ENTRY, fHeader->current_specifier, + specifier) < B_OK) return B_BAD_SCRIPT_SYNTAX; if (what) *what = specifier->what; - if (property) - { - if (specifier->FindString(B_PROPERTY_ENTRY, property)) + if (property) { + if (specifier->FindString(B_PROPERTY_ENTRY, property) < B_OK) return B_BAD_SCRIPT_SYNTAX; } } return B_OK; } -//------------------------------------------------------------------------------ -bool BMessage::HasSpecifiers() const + + +bool +BMessage::HasSpecifiers() const { - return fHasSpecifiers; -} -//------------------------------------------------------------------------------ -status_t BMessage::PopSpecifier() -{ - if (fCurSpecifier < 0 || !WasDelivered()) - { - return B_BAD_VALUE; - } - - --fCurSpecifier; - return B_OK; -} -//------------------------------------------------------------------------------ -// return fBody->AddData(name, val, TYPESPEC); -// return fBody->FindData(name, index, val, TYPESPEC); -// return fBody->ReplaceData(name, index, val, TYPESPEC); -// return fBody->HasData(name, TYPESPEC, n); - -#define DEFINE_FUNCTIONS(TYPE, fnName, TYPESPEC) \ - status_t BMessage::Add ## fnName(const char* name, TYPE val) \ - { return AddData(name, TYPESPEC, &val, sizeof(TYPE)); } \ - status_t BMessage::Find ## fnName(const char* name, TYPE* p) const \ - { return Find ## fnName(name, 0, p); } \ - status_t BMessage::Find ## fnName(const char* name, int32 index, TYPE* p) const \ - { \ - void* ptr = NULL; ssize_t bytes = 0; status_t err = B_OK;\ - *p = TYPE(); \ - err = FindData(name, TYPESPEC, index, (const void**)&ptr, &bytes); \ - if (err == B_OK) \ - memcpy(p, ptr, sizeof(TYPE)); \ - return err; \ - } \ - status_t BMessage::Replace ## fnName(const char* name, TYPE val) \ - { return Replace ## fnName(name, 0, val); } \ - status_t BMessage::Replace ## fnName(const char *name, int32 index, TYPE val) \ - { return ReplaceData(name, TYPESPEC, index, &val, sizeof(TYPE)); } \ - bool BMessage::Has ## fnName(const char* name, int32 n) const \ - { return fBody->HasData(name, TYPESPEC, n); } - -DEFINE_FUNCTIONS(int8 , Int8 , B_INT8_TYPE) -DEFINE_FUNCTIONS(int16 , Int16 , B_INT16_TYPE) -DEFINE_FUNCTIONS(int32 , Int32 , B_INT32_TYPE) -DEFINE_FUNCTIONS(int64 , Int64 , B_INT64_TYPE) -DEFINE_FUNCTIONS(BPoint, Point , B_POINT_TYPE) -DEFINE_FUNCTIONS(BRect , Rect , B_RECT_TYPE) -DEFINE_FUNCTIONS(float , Float , B_FLOAT_TYPE) -DEFINE_FUNCTIONS(double, Double, B_DOUBLE_TYPE) -DEFINE_FUNCTIONS(bool , Bool , B_BOOL_TYPE) - -#undef DEFINE_FUNCTIONS - - -#define DEFINE_HAS_FUNCTION(fnName, TYPESPEC) \ - bool BMessage::Has ## fnName(const char* name, int32 n) const \ - { return HasData(name, TYPESPEC, n); } - -DEFINE_HAS_FUNCTION(Message , B_MESSAGE_TYPE) -DEFINE_HAS_FUNCTION(String , B_STRING_TYPE) -DEFINE_HAS_FUNCTION(Pointer , B_POINTER_TYPE) -DEFINE_HAS_FUNCTION(Messenger, B_MESSENGER_TYPE) -DEFINE_HAS_FUNCTION(Ref , B_REF_TYPE) - -#undef DEFINE_HAS_FUNCTION - -#define DEFINE_LAZY_FIND_FUNCTION(TYPE, fnName) \ - TYPE BMessage::Find ## fnName(const char* name, int32 n) const \ - { \ - TYPE i = 0; \ - Find ## fnName(name, n, &i); \ - return i; \ - } - -DEFINE_LAZY_FIND_FUNCTION(int8 , Int8) -DEFINE_LAZY_FIND_FUNCTION(int16 , Int16) -DEFINE_LAZY_FIND_FUNCTION(int32 , Int32) -DEFINE_LAZY_FIND_FUNCTION(int64 , Int64) -DEFINE_LAZY_FIND_FUNCTION(float , Float) -DEFINE_LAZY_FIND_FUNCTION(double , Double) -DEFINE_LAZY_FIND_FUNCTION(bool , Bool) -DEFINE_LAZY_FIND_FUNCTION(const char* , String) - -#undef DEFINE_LAZY_FIND_FUNCTION - -//------------------------------------------------------------------------------ - - -status_t -BMessage::AddString(const char* name, const char* string) -{ - return AddData(name, B_STRING_TYPE, string, strlen(string) + 1); -} - - -status_t -BMessage::AddString(const char* name, const BString& string) -{ - return AddData(name, B_STRING_TYPE, string.String(), string.Length() + 1); -} - - -status_t -BMessage::AddPointer(const char* name, const void* pointer) -{ - return AddData(name, B_POINTER_TYPE, &pointer, sizeof(pointer)); -} - - -status_t -BMessage::AddMessenger(const char* name, BMessenger messenger) -{ - return AddData(name, B_MESSENGER_TYPE, &messenger, sizeof(messenger)); + return fHeader->flags & MESSAGE_FLAG_HAS_SPECIFIERS; } status_t -BMessage::AddRef(const char* name, const entry_ref* ref) +BMessage::PopSpecifier() { - char* buffer = new(std::nothrow) char[sizeof(entry_ref) + B_PATH_NAME_LENGTH]; - if (buffer == NULL) - return B_NO_MEMORY; + if (fHeader->current_specifier < 0 || + !(fHeader->flags & MESSAGE_FLAG_WAS_DELIVERED)) + return B_BAD_VALUE; - size_t size; - status_t err = entry_ref_flatten(buffer, &size, ref); - if (err >= B_OK) { - BDataBuffer databuffer((void*)buffer, size); - err = fBody->AddData(name, databuffer, B_REF_TYPE); - // ToDo: even if the code looks like it, test this for real - // if AddData() fails here, the buffer is freed automatically - // as part of the BDataBuffer destruction - } else - delete[] buffer; + if (fHeader->current_specifier >= 0) + fHeader->current_specifier--; - return err; + return B_OK; } -status_t -BMessage::AddMessage(const char* name, const BMessage* msg) +status_t +BMessage::_ResizeData(int32 offset, int32 change) { - ssize_t size = msg->FlattenedSize(); - char* buffer = new(std::nothrow) char[size]; - if (buffer == NULL) - return B_NO_MEMORY; + if (change == 0) + return B_OK; - status_t err = msg->Flatten(buffer, size); - if (err >= B_OK) { - BDataBuffer dataBuffer((void*)buffer, size); - err = fBody->AddData(name, dataBuffer, B_MESSAGE_TYPE); - // if AddData() fails here, the buffer is freed automatically - // as part of the BDataBuffer destruction - } else - delete[] buffer; + /* optimize for the most usual case: appending data */ + if (offset < fHeader->data_size) { + field_header *field = fFields; + for (int32 i = 0; i < fHeader->field_count; i++, field++) { + if (field->offset >= offset) + field->offset += change; + } + } - return err; + if (change > 0) { + if (fHeader->data_available >= change) { + if (offset < fHeader->data_size) { + memmove(fData + offset + change, fData + offset, + fHeader->data_size - offset); + } + + fHeader->data_available -= change; + fHeader->data_size += change; + return B_OK; + } + + ssize_t size = fHeader->data_size * 2; + size = min_c(size, fHeader->data_size + MAX_DATA_PREALLOCATION); + size = max_c(size, fHeader->data_size + change); + + fData = (uint8 *)realloc(fData, size); + if (!fData) + return B_NO_MEMORY; + + if (offset < fHeader->data_size) { + memmove(fData + offset + change, fData + offset, + fHeader->data_size - offset); + } + + fHeader->data_size += change; + fHeader->data_available = size - fHeader->data_size; + } else { + ssize_t length = fHeader->data_size - offset + change; + if (length > 0) + memmove(fData + offset, fData + offset - change, length); + + fHeader->data_size += change; + fHeader->data_available -= change; + + if (fHeader->data_available > MAX_DATA_PREALLOCATION) { + ssize_t available = MAX_DATA_PREALLOCATION / 2; + fData = (uint8 *)realloc(fData, fHeader->data_size + available); + if (!fData) + return B_NO_MEMORY; + + fHeader->data_available = available; + } + } + + return B_OK; } -status_t -BMessage::AddFlat(const char* name, BFlattenable* object, int32 count) +uint32 +BMessage::_HashName(const char *name) const { - ssize_t size = object->FlattenedSize(); - char* buffer = new(std::nothrow) char[size]; - if (buffer == NULL) - return B_NO_MEMORY; + char ch; + uint32 result = 0; - status_t err = object->Flatten((void*)buffer, size); - if (err >= B_OK) { - BDataBuffer dataBuffer((void*)buffer, size); - err = fBody->AddData(name, dataBuffer, object->TypeCode()); - // if AddData() fails here, the buffer is freed automatically - // as part of the BDataBuffer destruction - } else - delete[] buffer; + while ((ch = *name++) != 0) { + result = (result << 7) ^ (result >> 24); + result ^= ch; + } - return err; + result ^= result << 12; + return result; } -status_t -BMessage::AddData(const char* name, type_code type, const void* data, - ssize_t numBytes, bool is_fixed_size, int32 /*count*/) +status_t +BMessage::_FindField(const char *name, type_code type, field_header **result) const { - /** @note - Because we're using vectors for our item storage, the count param - is no longer useful to us: dynamically adding more items is not - really a performance issue, so pre-allocating space for objects - gives us no real advantage. - */ + if (!name) + return B_BAD_VALUE; - // TODO: test - // In particular, we want to see what happens if is_fixed_size == true and - // the user attempts to add something bigger or smaller. We may need to - // enforce the size thing. + if (!fHeader || !fFields || !fData) + return B_NAME_NOT_FOUND; - BDataBuffer buffer((void*)data, numBytes, true); - return fBody->AddData(name, buffer, type); + uint32 hash = _HashName(name) % fHeader->hash_table_size; + int32 nextField = fHeader->hash_table[hash]; + + while (nextField >= 0) { + field_header *field = &fFields[nextField]; + + if (strncmp((const char *)(fData + field->offset), name, + field->name_length) == 0) { + if (type != B_ANY_TYPE && field->type != type) + return B_BAD_TYPE; + + *result = field; + return B_OK; + } + + nextField = field->next_field; + } + + return B_NAME_NOT_FOUND; } -status_t -BMessage::RemoveData(const char* name, int32 index) +status_t +BMessage::_AddField(const char *name, type_code type, bool isFixedSize, + field_header **result) { - return fReadOnly ? B_ERROR : fBody->RemoveData(name, index); + if (!fHeader) + return B_ERROR; + + if (fHeader->fields_available <= 0) { + int32 count = fHeader->field_count * 2 + 1; + count = min_c(count, fHeader->field_count + MAX_FIELD_PREALLOCATION); + + fFields = (field_header *)realloc(fFields, count * sizeof(field_header)); + if (!fFields) + return B_NO_MEMORY; + + fHeader->fields_available = count - fHeader->field_count; + } + + uint32 hash = _HashName(name) % fHeader->hash_table_size; + + int32 *nextField = &fHeader->hash_table[hash]; + while (*nextField >= 0) + nextField = &fFields[*nextField].next_field; + *nextField = fHeader->field_count; + + field_header *field = &fFields[fHeader->field_count]; + field->type = type; + field->flags = FIELD_FLAG_VALID; + if (isFixedSize) + field->flags |= FIELD_FLAG_FIXED_SIZE; + + field->count = 0; + field->data_size = 0; + field->allocated = 0; + field->next_field = -1; + field->offset = fHeader->data_size; + field->name_length = strlen(name) + 1; + _ResizeData(field->offset, field->name_length); + memcpy(fData + field->offset, name, field->name_length); + + fHeader->fields_available--; + fHeader->fields_size += sizeof(field_header); + fHeader->field_count++; + *result = field; + return B_OK; } -status_t -BMessage::RemoveName(const char* name) +status_t +BMessage::_RemoveField(field_header *field) { - return fReadOnly ? B_ERROR : fBody->RemoveName(name); + int32 index = ((uint8 *)field - (uint8 *)fFields) / sizeof(field_header); + int32 nextField = field->next_field; + if (nextField > index) + nextField--; + + int32 *value = fHeader->hash_table; + for (int32 i = 0; i < fHeader->hash_table_size; i++, value++) { + if (*value > index) + *value -= 1; + else if (*value == index) + *value = nextField; + } + + field_header *other = fFields; + for (int32 i = 0; i < fHeader->field_count; i++, other++) { + if (other->next_field > index) + other->next_field--; + else if (other->next_field == index) + other->next_field = nextField; + } + + _ResizeData(field->offset, -(field->data_size + field->name_length)); + + ssize_t size = fHeader->fields_size - (index + 1) * sizeof(field_header); + memmove(fFields + index, fFields + index + 1, size); + fHeader->fields_size -= sizeof(field_header); + fHeader->field_count--; + fHeader->fields_available++; + + if (fHeader->fields_available > MAX_FIELD_PREALLOCATION) { + ssize_t available = MAX_FIELD_PREALLOCATION / 2; + fFields = (field_header *)realloc(fFields, fHeader->fields_size + + available * sizeof(field_header)); + if (!fFields) + return B_NO_MEMORY; + + fHeader->fields_available = available; + } + + return B_OK; } -status_t +status_t +BMessage::AddData(const char *name, type_code type, const void *data, + ssize_t numBytes, bool isFixedSize, int32 count) +{ + if (numBytes <= 0 || !data) + return B_BAD_VALUE; + + field_header *field = NULL; + status_t result = _FindField(name, type, &field); + if (result == B_NAME_NOT_FOUND) + result = _AddField(name, type, isFixedSize, &field); + + if (result < B_OK || !field) + return result; + + uint32 offset = field->offset + field->name_length + field->data_size; + if (field->flags & FIELD_FLAG_FIXED_SIZE) { + if (field->count) { + ssize_t size = field->data_size / field->count; + if (size != numBytes) + return B_BAD_VALUE; + } + + _ResizeData(offset, numBytes); + memcpy(fData + offset, data, numBytes); + field->data_size += numBytes; + } else { + int32 change = numBytes + sizeof(numBytes); + _ResizeData(offset, change); + memcpy(fData + offset, &numBytes, sizeof(numBytes)); + memcpy(fData + offset + sizeof(numBytes), data, numBytes); + field->data_size += change; + } + + field->count++; + return B_OK; +} + + +status_t +BMessage::RemoveData(const char *name, int32 index) +{ + if (index < 0) + return B_BAD_VALUE; + + field_header *field = NULL; + status_t result = _FindField(name, B_ANY_TYPE, &field); + + if (result < B_OK) + return result; + + if (!field) + return B_ERROR; + + if (index >= field->count) + return B_BAD_INDEX; + + if (field->count == 1) + return _RemoveField(field); + + uint32 offset = field->offset + field->name_length; + if (field->flags & FIELD_FLAG_FIXED_SIZE) { + ssize_t size = field->data_size / field->count; + _ResizeData(offset + index * size, -size); + field->data_size -= size; + } else { + uint8 *pointer = fData + offset; + + for (int32 i = 0; i < index; i++) { + offset += *(ssize_t *)pointer + sizeof(ssize_t); + pointer = fData + offset; + } + + ssize_t currentSize = *(ssize_t *)pointer + sizeof(ssize_t); + _ResizeData(offset, -currentSize); + field->data_size -= currentSize; + } + + field->count--; + return B_OK; +} + + +status_t +BMessage::RemoveName(const char *name) +{ + field_header *field = NULL; + status_t result = _FindField(name, B_ANY_TYPE, &field); + + if (result < B_OK) + return result; + + if (!field) + return B_ERROR; + + return _RemoveField(field); +} + + +status_t BMessage::MakeEmpty() { - return fReadOnly ? B_ERROR : fBody->MakeEmpty(); -} - - -status_t -BMessage::FindString(const char* name, const char** string) const -{ - return FindString(name, 0, string); -} - - -status_t -BMessage::FindString(const char* name, int32 index, - const char** string) const -{ - ssize_t bytes; - return FindData(name, B_STRING_TYPE, index, - (const void**)string, &bytes); -} - - -status_t -BMessage::FindString(const char* name, BString* string) const -{ - return FindString(name, 0, string); -} - - -status_t -BMessage::FindString(const char* name, int32 index, BString* string) const -{ - const char* cstr; - status_t err = FindString(name, index, &cstr); - if (err < B_OK) - return err; - - *string = cstr; + _Clear(); + _InitHeader(); return B_OK; } -status_t -BMessage::FindPointer(const char* name, void** ptr) const -{ - return FindPointer(name, 0, ptr); -} - - -status_t -BMessage::FindPointer(const char* name, int32 index, void** ptr) const -{ - void** data = NULL; - ssize_t size = 0; - status_t err = FindData(name, B_POINTER_TYPE, index, (const void**)&data, &size); - if (err == B_OK) - *ptr = *data; - else - *ptr = NULL; - return err; -} - - -status_t -BMessage::FindMessenger(const char* name, BMessenger* m) const -{ - return FindMessenger(name, 0, m); -} - - -status_t -BMessage::FindMessenger(const char* name, int32 index, BMessenger* m) const -{ - void* data = NULL; - ssize_t size = 0; - status_t err = FindData(name, B_MESSENGER_TYPE, index, (const void **)&data, &size); - if (err == B_OK) - memcpy(m, data, sizeof(BMessenger)); - else - *m = BMessenger(); - return err; -} - - -status_t -BMessage::FindRef(const char* name, entry_ref* ref) const -{ - return FindRef(name, 0, ref); -} - - -status_t -BMessage::FindRef(const char* name, int32 index, entry_ref* ref) const -{ - void* data = NULL; - ssize_t size = 0; - status_t err = FindData(name, B_REF_TYPE, index, (const void**)&data, &size); - if (err == B_OK) - err = entry_ref_unflatten(ref, (char*)data, size); - else - *ref = entry_ref(); - return err; -} - - -status_t -BMessage::FindMessage(const char* name, BMessage* msg) const -{ - return FindMessage(name, 0, msg); -} - - -status_t -BMessage::FindMessage(const char* name, int32 index, BMessage* msg) const -{ - void* data = NULL; - ssize_t size = 0; - status_t err = FindData(name, B_MESSAGE_TYPE, index, (const void**)&data, &size); - if (!err) - err = msg->Unflatten((const char*)data); - else - *msg = BMessage(); - return err; -} - - -status_t -BMessage::FindFlat(const char* name, BFlattenable* obj) const -{ - return FindFlat(name, 0, obj); -} - - -status_t -BMessage::FindFlat(const char* name, int32 index, BFlattenable* obj) const -{ - void* data = NULL; - ssize_t numBytes = 0; - status_t err = FindData(name, obj->TypeCode(), index, (const void**)&data, &numBytes); - if (!err) - err = obj->Unflatten(obj->TypeCode(), data, numBytes); - return err; -} - - -status_t -BMessage::FindData(const char* name, type_code type, const void** data, - ssize_t* numBytes) const -{ - return FindData(name, type, 0, data, numBytes); -} - - -status_t -BMessage::FindData(const char* name, type_code type, int32 index, - const void** data, ssize_t* numBytes) const -{ - return fBody->FindData(name, type, index, data, numBytes); -} - - -status_t -BMessage::ReplaceString(const char* name, const char* string) -{ - return ReplaceString(name, 0, string); -} - - -status_t -BMessage::ReplaceString(const char* name, int32 index, const char* string) -{ - return ReplaceData(name, B_STRING_TYPE, index, string, strlen(string)+1); -} - - -status_t -BMessage::ReplaceString(const char* name, const BString& string) -{ - return ReplaceString(name, 0, string); -} - - -status_t -BMessage::ReplaceString(const char* name, int32 index, const BString& string) -{ - return ReplaceData(name, B_STRING_TYPE, index, string.String(), string.Length()+1); -} - - -status_t -BMessage::ReplacePointer(const char* name, const void* ptr) -{ - return ReplacePointer(name, 0, ptr); -} - - -status_t -BMessage::ReplacePointer(const char* name, int32 index, const void* ptr) -{ - return ReplaceData(name, B_POINTER_TYPE, index, &ptr, sizeof(ptr)); -} - - -status_t -BMessage::ReplaceMessenger(const char* name, BMessenger messenger) -{ - return ReplaceData(name, B_MESSENGER_TYPE, 0, &messenger, sizeof(BMessenger)); -} - - -status_t -BMessage::ReplaceMessenger(const char* name, int32 index, BMessenger messenger) -{ - return ReplaceData(name, B_MESSENGER_TYPE, index, &messenger, sizeof(BMessenger)); -} - - -status_t -BMessage::ReplaceRef(const char* name, const entry_ref* ref) -{ - return ReplaceRef(name, 0, ref); -} - - -status_t -BMessage::ReplaceRef(const char* name, int32 index, const entry_ref* ref) -{ - char* buffer = new(std::nothrow) char[sizeof (entry_ref) + B_PATH_NAME_LENGTH]; - if (buffer == NULL) - return B_NO_MEMORY; - - size_t size; - status_t err = entry_ref_flatten(buffer, &size, ref); - if (err >= B_OK) { - BDataBuffer dataBuffer((void*)buffer, size); - err = fBody->ReplaceData(name, index, dataBuffer, B_REF_TYPE); - } else - delete[] buffer; - - return err; -} - - -status_t -BMessage::ReplaceMessage(const char* name, const BMessage* msg) -{ - return ReplaceMessage(name, 0, msg); -} - - -status_t -BMessage::ReplaceMessage(const char* name, int32 index, const BMessage* msg) -{ - ssize_t size = msg->FlattenedSize(); - char* buffer = new(std::nothrow) char[size]; - if (buffer == NULL) - return B_NO_MEMORY; - - status_t err = msg->Flatten(buffer, size); - if (err >= B_OK) { - BDataBuffer dataBuffer((void*)buffer, size); - err = fBody->ReplaceData(name, index, dataBuffer, B_MESSAGE_TYPE); - } else - delete[] buffer; - - return err; -} - - -status_t -BMessage::ReplaceFlat(const char* name, BFlattenable* object) -{ - return ReplaceFlat(name, 0, object); -} - - -status_t -BMessage::ReplaceFlat(const char* name, int32 index, BFlattenable* object) -{ - ssize_t size = object->FlattenedSize(); - char* buffer = new(std::nothrow) char[size]; - if (buffer == NULL) - return B_NO_MEMORY; - - status_t err = object->Flatten(buffer, size); - if (err >= B_OK) { - BDataBuffer dataBuffer((void*)buffer, size); - err = fBody->ReplaceData(name, index, dataBuffer, object->TypeCode()); - } else - delete[] buffer; - - return err; -} - - -status_t -BMessage::ReplaceData(const char* name, type_code type, - const void* data, ssize_t data_size) -{ - return ReplaceData(name, type, 0, data, data_size); -} - - status_t -BMessage::ReplaceData(const char* name, type_code type, int32 index, - const void* data, ssize_t data_size) +BMessage::FindData(const char *name, type_code type, int32 index, + const void **data, ssize_t *numBytes) const { - BDataBuffer databuffer((void*)data, data_size, true); - return fBody->ReplaceData(name, index, databuffer, type); -} + if (!data || !numBytes) + return B_BAD_VALUE; + *data = NULL; + field_header *field = NULL; + status_t result = _FindField(name, type, &field); -void* -BMessage::operator new(size_t size) -{ - if (!sMsgCache) - sMsgCache = new BBlockCache(10, size, B_OBJECT_CACHE); + if (result < B_OK) + return result; - return sMsgCache->Get(size); -} + if (!field) + return B_ERROR; + if (index >= field->count) + return B_BAD_INDEX; -void* -BMessage::operator new(size_t, void* p) -{ - return p; -} + if (field->flags & FIELD_FLAG_FIXED_SIZE) { + *numBytes = field->data_size / field->count; + *data = fData + field->offset + field->name_length + index * *numBytes; + } else { + uint8 *pointer = fData + field->offset + field->name_length; + for (int32 i = 0; i < index; i++) + pointer += *(ssize_t *)pointer + sizeof(ssize_t); -void -BMessage::operator delete(void* ptr, size_t size) -{ - sMsgCache->Save(ptr, size); -} - - -bool -BMessage::HasFlat(const char* name, const BFlattenable* flat) const -{ - return HasFlat(name, 0, flat); -} - - -bool -BMessage::HasFlat(const char* name, int32 n, const BFlattenable* flat) const -{ - return fBody->HasData(name, flat->TypeCode(), n); -} - - -bool -BMessage::HasData(const char* name, type_code t, int32 n) const -{ - return fBody->HasData(name, t, n); -} - - -BRect -BMessage::FindRect(const char* name, int32 n) const -{ - BRect r(0, 0, -1, -1); - FindRect(name, n, &r); - return r; -} - - -BPoint -BMessage::FindPoint(const char* name, int32 n) const -{ - BPoint p(0, 0); - FindPoint(name, n, &p); - return p; -} - - -status_t -BMessage::real_flatten(char* result, ssize_t size) const -{ - BMemoryIO stream((void*)result, size); - return real_flatten(&stream); - -} - - -status_t -BMessage::real_flatten(BDataIO* stream) const -{ - Header header(*this); - - status_t err = header.WriteTo(*stream); - - if (!err) - err = fBody->Flatten(stream); - - return err; -} - - -char* -BMessage::stack_flatten(char* stack_ptr, ssize_t stack_size, - bool /*incl_reply*/, ssize_t* size) const -{ - const ssize_t calcd_size = calc_hdr_size(0) + fBody->FlattenedSize(); - char* new_ptr = NULL; - if (calcd_size > stack_size) { - stack_ptr = new char[calcd_size]; - new_ptr = stack_ptr; + *numBytes = *(ssize_t *)pointer; + *data = pointer + sizeof(ssize_t); } - real_flatten(stack_ptr, calcd_size); - if (size) - *size = calcd_size; - - return new_ptr; + return B_OK; } -ssize_t -BMessage::calc_hdr_size(uchar flags) const +status_t +BMessage::ReplaceData(const char *name, type_code type, int32 index, + const void *data, ssize_t numBytes) { - ssize_t size = min_hdr_size(); + if (numBytes <= 0 || !data) + return B_BAD_VALUE; - if (fTarget != B_NULL_TOKEN) - size += sizeof (fTarget); + field_header *field = NULL; + status_t result = _FindField(name, type, &field); - if (fReplyTo.port >= 0 - && fReplyTo.target != B_NULL_TOKEN - && fReplyTo.team >= 0) { - size += sizeof (fReplyTo.port); - size += sizeof (fReplyTo.target); - size += sizeof (fReplyTo.team); + if (result < B_OK) + return result; - size += 4; // For the "big" flags + if (!field) + return B_ERROR; + + if (index >= field->count) + return B_BAD_INDEX; + + if (field->flags & FIELD_FLAG_FIXED_SIZE) { + ssize_t size = field->data_size / field->count; + if (size != numBytes) + return B_BAD_VALUE; + + memcpy(fData + field->offset + field->name_length + index * size, data, + size); + } else { + uint32 offset = field->offset + field->name_length; + uint8 *pointer = fData + offset; + + for (int32 i = 0; i < index; i++) { + offset += *(ssize_t *)pointer + sizeof(ssize_t); + pointer = fData + offset; + } + + ssize_t currentSize = *(ssize_t *)pointer; + int32 change = numBytes - currentSize; + _ResizeData(offset, change); + memcpy(fData + offset, &numBytes, sizeof(numBytes)); + memcpy(fData + offset + sizeof(numBytes), data, numBytes); + field->data_size += change; } - return size; + return B_OK; +} + + +bool +BMessage::HasData(const char *name, type_code type, int32 index) const +{ + field_header *field = NULL; + status_t result = _FindField(name, type, &field); + + if (result < B_OK) + return false; + + if (!field) + return false; + + if (index >= field->count) + return false; + + return true; } @@ -1749,28 +1345,497 @@ BMessage::_StaticCacheCleanup() } -void -BMessage::_StaticInit() +/* Relay functions from here on (Add... -> AddData, Find... -> FindData) */ + +#define DEFINE_FUNCTIONS(type, typeName, typeCode) \ +status_t \ +BMessage::Add##typeName(const char *name, type val) \ +{ \ + return AddData(name, typeCode, &val, sizeof(type), true); \ +} \ + \ +status_t \ +BMessage::Find##typeName(const char *name, type *p) const \ +{ \ + void *ptr = NULL; \ + ssize_t bytes = 0; \ + status_t error = B_OK; \ + \ + *p = type(); \ + error = FindData(name, typeCode, 0, (const void **)&ptr, &bytes); \ + \ + if (error == B_OK) \ + memcpy(p, ptr, sizeof(type)); \ + \ + return error; \ +} \ + \ +status_t \ +BMessage::Find##typeName(const char *name, int32 index, type *p) const \ +{ \ + void *ptr = NULL; \ + ssize_t bytes = 0; \ + status_t error = B_OK; \ + \ + *p = type(); \ + error = FindData(name, typeCode, index, (const void **)&ptr, &bytes); \ + \ + if (error == B_OK) \ + memcpy(p, ptr, sizeof(type)); \ + \ + return error; \ +} \ + \ +status_t \ +BMessage::Replace##typeName(const char *name, type val) \ +{ \ + return ReplaceData(name, typeCode, 0, &val, sizeof(type)); \ +} \ + \ +status_t \ +BMessage::Replace##typeName(const char *name, int32 index, type val) \ +{ \ + return ReplaceData(name, typeCode, index, &val, sizeof(type)); \ +} \ + \ +bool \ +BMessage::Has##typeName(const char *name, int32 index) const \ +{ \ + return HasData(name, typeCode, index); \ +} + +DEFINE_FUNCTIONS(BPoint, Point, B_POINT_TYPE); +DEFINE_FUNCTIONS(BRect, Rect, B_RECT_TYPE); +DEFINE_FUNCTIONS(int8, Int8, B_INT8_TYPE); +DEFINE_FUNCTIONS(int16, Int16, B_INT16_TYPE); +DEFINE_FUNCTIONS(int32, Int32, B_INT32_TYPE); +DEFINE_FUNCTIONS(int64, Int64, B_INT64_TYPE); +DEFINE_FUNCTIONS(bool, Bool, B_BOOL_TYPE); +DEFINE_FUNCTIONS(float, Float, B_FLOAT_TYPE); +DEFINE_FUNCTIONS(double, Double, B_DOUBLE_TYPE); + +#undef DEFINE_FUNCTIONS + +#define DEFINE_HAS_FUNCTION(typeName, typeCode) \ +bool \ +BMessage::Has##typeName(const char *name, int32 index) const \ +{ \ + return HasData(name, typeCode, index); \ +} + +DEFINE_HAS_FUNCTION(String, B_STRING_TYPE); +DEFINE_HAS_FUNCTION(Pointer, B_POINTER_TYPE); +DEFINE_HAS_FUNCTION(Messenger, B_MESSENGER_TYPE); +DEFINE_HAS_FUNCTION(Ref, B_REF_TYPE); +DEFINE_HAS_FUNCTION(Message, B_MESSAGE_TYPE); + +#undef DEFINE_HAS_FUNCTION + +#define DEFINE_LAZY_FIND_FUNCTION(type, typeName, initialize) \ +type \ +BMessage::Find##typeName(const char *name, int32 index) const \ +{ \ + type val = initialize; \ + Find##typeName(name, index, &val); \ + return val; \ +} + +DEFINE_LAZY_FIND_FUNCTION(BRect, Rect, BRect()); +DEFINE_LAZY_FIND_FUNCTION(BPoint, Point, BPoint()); +DEFINE_LAZY_FIND_FUNCTION(const char *, String, NULL); +DEFINE_LAZY_FIND_FUNCTION(int8, Int8, 0); +DEFINE_LAZY_FIND_FUNCTION(int16, Int16, 0); +DEFINE_LAZY_FIND_FUNCTION(int32, Int32, 0); +DEFINE_LAZY_FIND_FUNCTION(int64, Int64, 0); +DEFINE_LAZY_FIND_FUNCTION(bool, Bool, false); +DEFINE_LAZY_FIND_FUNCTION(float, Float, 0); +DEFINE_LAZY_FIND_FUNCTION(double, Double, 0); + +#undef DEFINE_LAZY_FIND_FUNCTION + +status_t +BMessage::AddString(const char *name, const char *string) { + return AddData(name, B_STRING_TYPE, string, string ? strlen(string) + 1 : 0, false); } -void -BMessage::_StaticCleanup() +status_t +BMessage::AddString(const char *name, const BString &string) { + return AddData(name, B_STRING_TYPE, string.String(), string.Length() + 1, false); } -static ssize_t -min_hdr_size() +status_t +BMessage::AddPointer(const char *name, const void *pointer) { + return AddData(name, B_POINTER_TYPE, &pointer, sizeof(pointer), true); +} + + +status_t +BMessage::AddMessenger(const char *name, BMessenger messenger) +{ + return AddData(name, B_MESSENGER_TYPE, &messenger, sizeof(messenger), true); +} + + +status_t +BMessage::AddRef(const char *name, const entry_ref *ref) +{ + size_t size = sizeof(entry_ref) + B_PATH_NAME_LENGTH; + char buffer[size]; + + status_t error = BPrivate::entry_ref_flatten(buffer, &size, ref); + + if (error >= B_OK) + error = AddData(name, B_REF_TYPE, buffer, size, false); + + return error; +} + + +status_t +BMessage::AddMessage(const char *name, const BMessage *message) +{ + /* ToDo: This and the following functions waste time by allocating and + copying an extra buffer. Functions can be added that return a direct + pointer into the message. */ + + ssize_t size = message->FlattenedSize(); + char buffer[size]; + + status_t error = message->Flatten(buffer, size); + + if (error >= B_OK) + error = AddData(name, B_MESSAGE_TYPE, &buffer, size, false); + + return error; +} + + +status_t +BMessage::AddFlat(const char *name, BFlattenable *object, int32 count) +{ + ssize_t size = object->FlattenedSize(); + char buffer[size]; + + status_t error = object->Flatten(buffer, size); + + if (error >= B_OK) + error = AddData(name, object->TypeCode(), &buffer, size, false); + + return error; +} + + +status_t +BMessage::FindString(const char *name, const char **string) const +{ + return FindString(name, 0, string); +} + + +status_t +BMessage::FindString(const char *name, int32 index, const char **string) const +{ + ssize_t bytes; + return FindData(name, B_STRING_TYPE, index, (const void **)string, &bytes); +} + + +status_t +BMessage::FindString(const char *name, BString *string) const +{ + return FindString(name, 0, string); +} + + +status_t +BMessage::FindString(const char *name, int32 index, BString *string) const +{ + const char *cstr; + status_t error = FindString(name, index, &cstr); + if (error < B_OK) + return error; + + *string = cstr; + return B_OK; +} + + +status_t +BMessage::FindPointer(const char *name, void **pointer) const +{ + return FindPointer(name, 0, pointer); +} + + +status_t +BMessage::FindPointer(const char *name, int32 index, void **pointer) const +{ + void **data = NULL; ssize_t size = 0; + status_t error = FindData(name, B_POINTER_TYPE, index, + (const void **)&data, &size); - size += 4; // version - size += 4; // checksum - size += 4; // flattened size - size += 4; // 'what' - size += 1; // flags + if (error == B_OK) + *pointer = *data; + else + *pointer = NULL; - return size; + return error; +} + + +status_t +BMessage::FindMessenger(const char *name, BMessenger *messenger) const +{ + return FindMessenger(name, 0, messenger); +} + + +status_t +BMessage::FindMessenger(const char *name, int32 index, BMessenger *messenger) + const +{ + void *data = NULL; + ssize_t size = 0; + status_t error = FindData(name, B_MESSENGER_TYPE, index, + (const void **)&data, &size); + + if (error == B_OK) + memcpy(messenger, data, sizeof(BMessenger)); + else + *messenger = BMessenger(); + + return error; +} + + +status_t +BMessage::FindRef(const char *name, entry_ref *ref) const +{ + return FindRef(name, 0, ref); +} + + +status_t +BMessage::FindRef(const char *name, int32 index, entry_ref *ref) const +{ + void *data = NULL; + ssize_t size = 0; + status_t error = FindData(name, B_REF_TYPE, index, + (const void **)&data, &size); + + if (error == B_OK) + error = BPrivate::entry_ref_unflatten(ref, (char *)data, size); + else + *ref = entry_ref(); + + return error; +} + + +status_t +BMessage::FindMessage(const char *name, BMessage *message) const +{ + return FindMessage(name, 0, message); +} + + +status_t +BMessage::FindMessage(const char *name, int32 index, BMessage *message) const +{ + void *data = NULL; + ssize_t size = 0; + status_t error = FindData(name, B_MESSAGE_TYPE, index, + (const void **)&data, &size); + + if (error == B_OK) + error = message->Unflatten((const char *)data); + else + *message = BMessage(); + + return error; +} + + +status_t +BMessage::FindFlat(const char *name, BFlattenable *object) const +{ + return FindFlat(name, 0, object); +} + + +status_t +BMessage::FindFlat(const char *name, int32 index, BFlattenable *object) const +{ + void *data = NULL; + ssize_t numBytes = 0; + status_t error = FindData(name, object->TypeCode(), index, + (const void **)&data, &numBytes); + + if (error == B_OK) + error = object->Unflatten(object->TypeCode(), data, numBytes); + + return error; +} + + +status_t +BMessage::FindData(const char *name, type_code type, const void **data, + ssize_t *numBytes) const +{ + return FindData(name, type, 0, data, numBytes); +} + + +status_t +BMessage::ReplaceString(const char *name, const char *string) +{ + return ReplaceData(name, B_STRING_TYPE, 0, string, strlen(string) + 1); +} + + +status_t +BMessage::ReplaceString(const char *name, int32 index, const char *string) +{ + return ReplaceData(name, B_STRING_TYPE, index, string, strlen(string) + 1); +} + + +status_t +BMessage::ReplaceString(const char *name, const BString &string) +{ + return ReplaceData(name, B_STRING_TYPE, 0, string.String(), + string.Length() + 1); +} + + +status_t +BMessage::ReplaceString(const char *name, int32 index, const BString &string) +{ + return ReplaceData(name, B_STRING_TYPE, index, string.String(), + string.Length() + 1); +} + + +status_t +BMessage::ReplacePointer(const char *name, const void *pointer) +{ + return ReplaceData(name, B_POINTER_TYPE, 0, &pointer, sizeof(pointer)); +} + + +status_t +BMessage::ReplacePointer(const char *name, int32 index, const void *pointer) +{ + return ReplaceData(name, B_POINTER_TYPE, index, &pointer, sizeof(pointer)); +} + + +status_t +BMessage::ReplaceMessenger(const char *name, BMessenger messenger) +{ + return ReplaceData(name, B_MESSENGER_TYPE, 0, &messenger, + sizeof(BMessenger)); +} + + +status_t +BMessage::ReplaceMessenger(const char *name, int32 index, BMessenger messenger) +{ + return ReplaceData(name, B_MESSENGER_TYPE, index, &messenger, + sizeof(BMessenger)); +} + + +status_t +BMessage::ReplaceRef(const char *name, const entry_ref *ref) +{ + return ReplaceRef(name, 0, ref); +} + + +status_t +BMessage::ReplaceRef(const char *name, int32 index, const entry_ref *ref) +{ + size_t size = sizeof(entry_ref) + B_PATH_NAME_LENGTH; + char buffer[size]; + + status_t error = BPrivate::entry_ref_flatten(buffer, &size, ref); + + if (error >= B_OK) + error = ReplaceData(name, B_REF_TYPE, index, &buffer, size); + + return error; +} + + +status_t +BMessage::ReplaceMessage(const char *name, const BMessage *message) +{ + return ReplaceMessage(name, 0, message); +} + + +status_t +BMessage::ReplaceMessage(const char *name, int32 index, const BMessage *message) +{ + ssize_t size = message->FlattenedSize(); + char buffer[size]; + + status_t error = message->Flatten(buffer, size); + + if (error >= B_OK) + error = ReplaceData(name, B_MESSAGE_TYPE, index, &buffer, size); + + return error; +} + + +status_t +BMessage::ReplaceFlat(const char *name, BFlattenable *object) +{ + return ReplaceFlat(name, 0, object); +} + + +status_t +BMessage::ReplaceFlat(const char *name, int32 index, BFlattenable *object) +{ + ssize_t size = object->FlattenedSize(); + char buffer[size]; + + status_t error = object->Flatten(buffer, size); + + if (error >= B_OK) + error = ReplaceData(name, object->TypeCode(), index, &buffer, size); + + return error; +} + + +status_t +BMessage::ReplaceData(const char *name, type_code type, const void *data, + ssize_t numBytes) +{ + return ReplaceData(name, type, 0, data, numBytes); +} + + +bool +BMessage::HasFlat(const char *name, const BFlattenable *object) const +{ + return HasFlat(name, 0, object); +} + + +bool +BMessage::HasFlat(const char *name, int32 index, const BFlattenable *object) + const +{ + return HasData(name, object->TypeCode(), index); } diff --git a/src/build/libbe/app/MessageAdapter.cpp b/src/build/libbe/app/MessageAdapter.cpp new file mode 100644 index 0000000000..9dfb1af73d --- /dev/null +++ b/src/build/libbe/app/MessageAdapter.cpp @@ -0,0 +1,705 @@ +/* + * Copyright 2005-2007, Haiku Inc. All rights reserved. + * Distributed under the terms of the MIT License. + * + * Authors: + * Axel Dörfler, axeld@pinc-software.de + * Michael Lotz + */ +#include +#include +#include + +namespace BPrivate { + +#define R5_MESSAGE_FLAG_VALID 0x01 +#define R5_MESSAGE_FLAG_INCLUDE_TARGET 0x02 +#define R5_MESSAGE_FLAG_INCLUDE_REPLY 0x04 +#define R5_MESSAGE_FLAG_SCRIPT_MESSAGE 0x08 + +#define R5_FIELD_FLAG_VALID 0x01 +#define R5_FIELD_FLAG_MINI_DATA 0x02 +#define R5_FIELD_FLAG_FIXED_SIZE 0x04 +#define R5_FIELD_FLAG_SINGLE_ITEM 0x08 + + +enum { + SECTION_MESSAGE_HEADER = 'FOB2', + SECTION_OFFSET_TABLE = 'STof', + SECTION_TARGET_INFORMATION = 'ENwh', + SECTION_SINGLE_ITEM_DATA = 'SGDa', + SECTION_FIXED_SIZE_ARRAY_DATA = 'FADa', + SECTION_VARIABLE_SIZE_ARRAY_DATA = 'VADa', + SECTION_SORTED_INDEX_TABLE = 'DXIn', + SECTION_END_OF_DATA = 'DDEn' +}; + + +struct r5_message_header { + uint32 magic; + uint32 checksum; + ssize_t flattened_size; + int32 what; + uint8 flags; +} _PACKED; + +struct dano_section_header { + uint32 code; + ssize_t size; + uint8 data[0]; +} _PACKED; + +struct dano_message_header { + int32 what; + int32 padding; +} _PACKED; + +typedef struct offset_table_s { + int32 indexTable; + int32 endOfData; + int64 padding; +} OffsetTable; + +struct dano_single_item { + type_code type; + ssize_t item_size; + uint8 name_length; + char name[0]; +} _PACKED; + +struct dano_fixed_size_array { + type_code type; + ssize_t size_per_item; + uint8 name_length; + char name[0]; +} _PACKED; + + +struct dano_variable_size_array { + type_code type; + int32 padding; + uint8 name_length; + char name[0]; +} _PACKED; + + +inline int32 +pad_to_8(int32 value) +{ + return (value + 7) & ~7; +} + + +ssize_t +MessageAdapter::FlattenedSize(uint32 format, const BMessage *from) +{ + switch (format) { + case MESSAGE_FORMAT_R5: + case MESSAGE_FORMAT_R5_SWAPPED: + return _R5FlattenedSize(from); + } + + return -1; +} + + +status_t +MessageAdapter::Flatten(uint32 format, const BMessage *from, char *buffer, + ssize_t *size) +{ + switch (format) { + case MESSAGE_FORMAT_R5: + case MESSAGE_FORMAT_R5_SWAPPED: + return _FlattenR5Message(format, from, buffer, size); + } + + return B_ERROR; +} + + +status_t +MessageAdapter::Flatten(uint32 format, const BMessage *from, BDataIO *stream, + ssize_t *size) +{ + switch (format) { + case MESSAGE_FORMAT_R5: + case MESSAGE_FORMAT_R5_SWAPPED: + { + ssize_t flattenedSize = _R5FlattenedSize(from); + char *buffer = (char *)malloc(flattenedSize); + if (!buffer) + return B_NO_MEMORY; + + status_t result = _FlattenR5Message(format, from, buffer, + &flattenedSize); + if (result < B_OK) { + free(buffer); + return result; + } + + ssize_t written = stream->Write(buffer, flattenedSize); + if (written != flattenedSize) { + free(buffer); + return (written >= 0 ? B_ERROR : written); + } + + if (size) + *size = flattenedSize; + + free(buffer); + return B_OK; + } + } + + return B_ERROR; +} + + +status_t +MessageAdapter::Unflatten(uint32 format, BMessage *into, const char *buffer) +{ + try { + switch (format) { + case MESSAGE_FORMAT_R5: + case MESSAGE_FORMAT_R5_SWAPPED: + { + r5_message_header *header = (r5_message_header *)buffer; + BMemoryIO stream(buffer + sizeof(uint32), + header->flattened_size - sizeof(uint32)); + return _UnflattenR5Message(format, into, &stream); + } + + case MESSAGE_FORMAT_DANO: + case MESSAGE_FORMAT_DANO_SWAPPED: + { + dano_section_header *header = (dano_section_header *)buffer; + ssize_t size = header->size; + if (header->code == MESSAGE_FORMAT_DANO_SWAPPED) + size = __swap_int32(size); + + BMemoryIO stream(buffer + sizeof(uint32), size - sizeof(uint32)); + return _UnflattenDanoMessage(format, into, &stream); + } + } + } catch (status_t error) { + into->MakeEmpty(); + return error; + } + + return B_NOT_A_MESSAGE; +} + + +status_t +MessageAdapter::Unflatten(uint32 format, BMessage *into, BDataIO *stream) +{ + try { + switch (format) { + case MESSAGE_FORMAT_R5: + case MESSAGE_FORMAT_R5_SWAPPED: + return _UnflattenR5Message(format, into, stream); + + case MESSAGE_FORMAT_DANO: + case MESSAGE_FORMAT_DANO_SWAPPED: + return _UnflattenDanoMessage(format, into, stream); + } + } catch (status_t error) { + into->MakeEmpty(); + return error; + } + + return B_NOT_A_MESSAGE; +} + + +ssize_t +MessageAdapter::_R5FlattenedSize(const BMessage *from) +{ + BMessage::Private messagePrivate((BMessage *)from); + BMessage::message_header* header = messagePrivate.GetMessageHeader(); + + // header size (variable, depending on the flags) + + ssize_t flattenedSize = sizeof(r5_message_header); + + if (header->target != B_NULL_TOKEN) + flattenedSize += sizeof(int32); + + if (header->reply_port >= 0 && header->reply_target != B_NULL_TOKEN + && header->reply_team >= 0) { + // reply info + big flags + flattenedSize += sizeof(port_id) + sizeof(int32) + sizeof(team_id) + 4; + } + + // field size + + uint8 *data = messagePrivate.GetMessageData(); + BMessage::field_header *field = messagePrivate.GetMessageFields(); + for (int32 i = 0; i < header->field_count; i++, field++) { + // flags and type + flattenedSize += 1 + sizeof(type_code); + +#if 0 + bool miniData = field->dataSize <= 255 && field->count <= 255; +#else + // ToDo: we don't know the R5 dataSize yet (padding) + bool miniData = false; +#endif + + // item count + if (field->count > 1) + flattenedSize += (miniData ? sizeof(uint8) : sizeof(uint32)); + + // data size + flattenedSize += (miniData ? sizeof(uint8) : sizeof(size_t)); + + // name length and name + flattenedSize += 1 + min_c(field->name_length - 1, 255); + + // data + if (field->flags & FIELD_FLAG_FIXED_SIZE) + flattenedSize += field->data_size; + else { + uint8 *source = data + field->offset + field->name_length; + + for (int32 i = 0; i < field->count; i++) { + ssize_t itemSize = *(ssize_t *)source + sizeof(ssize_t); + flattenedSize += pad_to_8(itemSize); + source += itemSize; + } + } + } + + // pseudo field with flags 0 + return flattenedSize + 1; +} + + +status_t +MessageAdapter::_FlattenR5Message(uint32 format, const BMessage *from, + char *buffer, ssize_t *size) +{ + BMessage::Private messagePrivate((BMessage *)from); + BMessage::message_header *header = messagePrivate.GetMessageHeader(); + uint8 *data = messagePrivate.GetMessageData(); + + r5_message_header *r5header = (r5_message_header *)buffer; + uint8 *pointer = (uint8 *)buffer + sizeof(r5_message_header); + + r5header->magic = MESSAGE_FORMAT_R5; + r5header->what = from->what; + r5header->checksum = 0; + + uint8 flags = R5_MESSAGE_FLAG_VALID; + if (header->target != B_NULL_TOKEN) { + *(int32 *)pointer = header->target; + pointer += sizeof(int32); + flags |= R5_MESSAGE_FLAG_INCLUDE_TARGET; + } + + if (header->reply_port >= 0 && header->reply_target != B_NULL_TOKEN + && header->reply_team >= 0) { + // reply info + *(port_id *)pointer = header->reply_port; + pointer += sizeof(port_id); + *(int32 *)pointer = header->reply_target; + pointer += sizeof(int32); + *(team_id *)pointer = header->reply_team; + pointer += sizeof(team_id); + + // big flags + *pointer = (header->reply_target == B_PREFERRED_TOKEN ? 1 : 0); + pointer++; + + *pointer = (header->flags & MESSAGE_FLAG_REPLY_REQUIRED ? 1 : 0); + pointer++; + + *pointer = (header->flags & MESSAGE_FLAG_REPLY_DONE ? 1 : 0); + pointer++; + + *pointer = (header->flags & MESSAGE_FLAG_IS_REPLY ? 1 : 0); + pointer++; + + flags |= R5_MESSAGE_FLAG_INCLUDE_REPLY; + } + + if (header->flags & MESSAGE_FLAG_HAS_SPECIFIERS) + flags |= R5_MESSAGE_FLAG_SCRIPT_MESSAGE; + + r5header->flags = flags; + + // store the header size - used for the checksum later + ssize_t headerSize = (uint32)pointer - (uint32)buffer; + + // collect and add the data + BMessage::field_header *field = messagePrivate.GetMessageFields(); + for (int32 i = 0; i < header->field_count; i++, field++) { + flags = R5_FIELD_FLAG_VALID; + + if (field->count == 1) + flags |= R5_FIELD_FLAG_SINGLE_ITEM; + // ToDo: we don't really know the data size now (padding missing) + if (field->data_size <= 255 && field->count <= 255) + ;//flags |= R5_FIELD_FLAG_MINI_DATA; + if (field->flags & FIELD_FLAG_FIXED_SIZE) + flags |= R5_FIELD_FLAG_FIXED_SIZE; + + *pointer = flags; + pointer++; + + *(type_code *)pointer = field->type; + pointer += sizeof(type_code); + + if (!(flags & R5_FIELD_FLAG_SINGLE_ITEM)) { + if (flags & R5_FIELD_FLAG_MINI_DATA) { + *pointer = (uint8)field->count; + pointer++; + } else { + *(int32 *)pointer = field->count; + pointer += sizeof(int32); + } + } + + // we may have to adjust this to account for padding later + uint8 *fieldSize = pointer; + if (flags & R5_FIELD_FLAG_MINI_DATA) { + *pointer = (uint8)field->data_size; + pointer++; + } else { + *(ssize_t *)pointer = field->data_size; + pointer += sizeof(ssize_t); + } + + // name + int32 nameLength = min_c(field->name_length - 1, 255); + *pointer = (uint8)nameLength; + pointer++; + + strncpy((char *)pointer, (char *)data + field->offset, nameLength); + pointer += nameLength; + + // data + uint8 *source = data + field->offset + field->name_length; + if (flags & R5_FIELD_FLAG_FIXED_SIZE) { + memcpy(pointer, source, field->data_size); + pointer += field->data_size; + } else { + uint8 *previous = pointer; + for (int32 i = 0; i < field->count; i++) { + ssize_t itemSize = *(ssize_t *)source + sizeof(ssize_t); + memcpy(pointer, source, itemSize); + pointer += pad_to_8(itemSize); + source += itemSize; + } + + // adjust the field size to the padded value + if (flags & R5_FIELD_FLAG_MINI_DATA) + *fieldSize = (uint8)(pointer - previous); + else + *(ssize_t *)fieldSize = (pointer - previous); + } + } + + // terminate the fields with a pseudo field with flags 0 (not valid) + *pointer = 0; + pointer++; + + // calculate the flattened size from the pointers + r5header->flattened_size = (uint32)pointer - (uint32)buffer; + r5header->checksum = CalculateChecksum((uint8 *)(buffer + 8), + headerSize - 8); + + if (size) + *size = r5header->flattened_size; + + return B_OK; +} + + +status_t +MessageAdapter::_UnflattenR5Message(uint32 format, BMessage *into, + BDataIO *stream) +{ + into->MakeEmpty(); + + BMessage::Private messagePrivate(into); + BMessage::message_header *header = messagePrivate.GetMessageHeader(); + + TReadHelper reader(stream); + if (format == MESSAGE_FORMAT_R5_SWAPPED) + reader.SetSwap(true); + + // the stream is already advanced by the size of the "format" + r5_message_header r5header; + reader(((uint8 *)&r5header) + sizeof(uint32), + sizeof(r5header) - sizeof(uint32)); + + header->what = into->what = r5header.what; + if (r5header.flags & R5_MESSAGE_FLAG_INCLUDE_TARGET) + reader(header->target); + + if (r5header.flags & R5_MESSAGE_FLAG_INCLUDE_REPLY) { + // reply info + reader(header->reply_port); + reader(header->reply_target); + reader(header->reply_team); + + // big flags + uint8 bigFlag; + reader(bigFlag); + if (bigFlag) + header->reply_target = B_PREFERRED_TOKEN; + + reader(bigFlag); + if (bigFlag) + header->flags |= MESSAGE_FLAG_REPLY_REQUIRED; + + reader(bigFlag); + if (bigFlag) + header->flags |= MESSAGE_FLAG_REPLY_DONE; + + reader(bigFlag); + if (bigFlag) + header->flags |= MESSAGE_FLAG_IS_REPLY; + } + + if (r5header.flags & R5_MESSAGE_FLAG_SCRIPT_MESSAGE) + header->flags |= MESSAGE_FLAG_HAS_SPECIFIERS; + + uint8 flags; + reader(flags); + while (flags & R5_FIELD_FLAG_VALID) { + bool fixedSize = flags & R5_FIELD_FLAG_FIXED_SIZE; + bool miniData = flags & R5_FIELD_FLAG_MINI_DATA; + bool singleItem = flags & R5_FIELD_FLAG_SINGLE_ITEM; + + type_code type; + reader(type); + + int32 itemCount; + if (!singleItem) { + if (miniData) { + uint8 miniCount; + reader(miniCount); + itemCount = miniCount; + } else + reader(itemCount); + } else + itemCount = 1; + + ssize_t dataSize; + if (miniData) { + uint8 miniSize; + reader(miniSize); + dataSize = miniSize; + } else + reader(dataSize); + + if (dataSize <= 0) + return B_ERROR; + + // name + uint8 nameLength; + reader(nameLength); + + char nameBuffer[256]; + reader(nameBuffer, nameLength); + nameBuffer[nameLength] = '\0'; + + uint8 *buffer = (uint8 *)malloc(dataSize); + uint8 *pointer = buffer; + reader(buffer, dataSize); + + status_t result = B_OK; + ssize_t itemSize = 0; + if (fixedSize) + itemSize = dataSize / itemCount; + + for (int32 i = 0; i < itemCount; i++) { + if (!fixedSize) { + itemSize = *(ssize_t *)pointer; + pointer += sizeof(ssize_t); + } + + result = into->AddData(nameBuffer, type, pointer, itemSize, + fixedSize, itemCount); + + if (result < B_OK) { + free(buffer); + return result; + } + + if (fixedSize) + pointer += itemSize; + else + pointer += pad_to_8(itemSize + sizeof(ssize_t)) - sizeof(ssize_t); + } + + free(buffer); + + // flags of next field or termination byte + reader(flags); + } + + return B_OK; +} + + +status_t +MessageAdapter::_UnflattenDanoMessage(uint32 format, BMessage *into, + BDataIO *stream) +{ + into->MakeEmpty(); + + TReadHelper reader(stream); + if (format == MESSAGE_FORMAT_DANO_SWAPPED) + reader.SetSwap(true); + + ssize_t size; + reader(size); + + dano_message_header header; + reader(header); + into->what = header.what; + + size -= sizeof(dano_section_header) + sizeof(dano_message_header); + int32 offset = 0; + + while (offset < size) { + dano_section_header sectionHeader; + reader(sectionHeader); + + // be safe. this shouldn't be necessary but in some testcases it was. + sectionHeader.size = pad_to_8(sectionHeader.size); + + if (offset + sectionHeader.size > size || sectionHeader.size < 0) + return B_BAD_DATA; + + ssize_t fieldSize = sectionHeader.size - sizeof(dano_section_header); + uint8 *fieldBuffer = NULL; + if (fieldSize > 0) { + // there may be no data. we shouldn't fail because of that + fieldBuffer = (uint8 *)malloc(fieldSize); + if (fieldBuffer == NULL) + throw (status_t)B_NO_MEMORY; + + reader(fieldBuffer, fieldSize); + } + + switch (sectionHeader.code) { + case SECTION_OFFSET_TABLE: + case SECTION_TARGET_INFORMATION: + case SECTION_SORTED_INDEX_TABLE: + case SECTION_END_OF_DATA: + // discard + break; + + case SECTION_SINGLE_ITEM_DATA: { + dano_single_item *field = (dano_single_item *)fieldBuffer; + + int32 dataOffset = sizeof(dano_single_item) + + field->name_length + 1; + dataOffset = pad_to_8(dataOffset); + + if (offset + dataOffset + field->item_size > size) + return B_BAD_DATA; + + // support for fixed size is not possible with a single item + bool fixedSize = false; + switch (field->type) { + case B_RECT_TYPE: + case B_POINT_TYPE: + case B_INT8_TYPE: + case B_INT16_TYPE: + case B_INT32_TYPE: + case B_INT64_TYPE: + case B_BOOL_TYPE: + case B_FLOAT_TYPE: + case B_DOUBLE_TYPE: + case B_POINTER_TYPE: + case B_MESSENGER_TYPE: + fixedSize = true; + break; + default: + break; + } + + status_t result = into->AddData(field->name, field->type, + fieldBuffer + dataOffset, field->item_size, fixedSize); + + if (result < B_OK) { + free(fieldBuffer); + throw result; + } + break; + } + + case SECTION_FIXED_SIZE_ARRAY_DATA: { + dano_fixed_size_array *field + = (dano_fixed_size_array *)fieldBuffer; + + int32 dataOffset = sizeof(dano_fixed_size_array) + + field->name_length + 1; + dataOffset = pad_to_8(dataOffset); + int32 count = *(int32 *)(fieldBuffer + dataOffset); + dataOffset += 8; /* count and padding */ + + if (offset + dataOffset + count * field->size_per_item > size) + return B_BAD_DATA; + + status_t result = B_OK; + for (int32 i = 0; i < count; i++) { + result = into->AddData(field->name, field->type, + fieldBuffer + dataOffset, field->size_per_item, true, + count); + + if (result < B_OK) { + free(fieldBuffer); + throw result; + } + + dataOffset += field->size_per_item; + } + break; + } + + case SECTION_VARIABLE_SIZE_ARRAY_DATA: { + dano_variable_size_array *field + = (dano_variable_size_array *)fieldBuffer; + + int32 dataOffset = sizeof(dano_variable_size_array) + + field->name_length + 1; + dataOffset = pad_to_8(dataOffset); + int32 count = *(int32 *)(fieldBuffer + dataOffset); + dataOffset += sizeof(int32); + ssize_t totalSize = *(ssize_t *)(fieldBuffer + dataOffset); + dataOffset += sizeof(ssize_t); + + int32 *endPoints = (int32 *)(fieldBuffer + dataOffset + + totalSize); + + status_t result = B_OK; + for (int32 i = 0; i < count; i++) { + int32 itemOffset = (i > 0 ? pad_to_8(endPoints[i - 1]) : 0); + + result = into->AddData(field->name, field->type, + fieldBuffer + dataOffset + itemOffset, + endPoints[i] - itemOffset, false, count); + + if (result < B_OK) { + free(fieldBuffer); + throw result; + } + } + break; + } + } + + free(fieldBuffer); + offset += sectionHeader.size; + } + + return B_OK; +} + +} // namespace BPrivate diff --git a/src/build/libbe/app/MessageBody.cpp b/src/build/libbe/app/MessageBody.cpp deleted file mode 100644 index 38bfa514f8..0000000000 --- a/src/build/libbe/app/MessageBody.cpp +++ /dev/null @@ -1,412 +0,0 @@ -//------------------------------------------------------------------------------ -// Copyright (c) 2001-2002, OpenBeOS -// -// Permission is hereby granted, free of charge, to any person obtaining a -// copy of this software and associated documentation files (the "Software"), -// to deal in the Software without restriction, including without limitation -// the rights to use, copy, modify, merge, publish, distribute, sublicense, -// and/or sell copies of the Software, and to permit persons to whom the -// Software is furnished to do so, subject to the following conditions: -// -// The above copyright notice and this permission notice shall be included in -// all copies or substantial portions of the Software. -// -// THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR -// IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY, -// FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE -// AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER -// LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING -// FROM, OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER -// DEALINGS IN THE SOFTWARE. -// -// File Name: MessageBody.cpp -// Author(s): Erik Jaesler (erik@cgsoftware.com) -// Description: BMessageBody handles data storage and retrieval for -// BMessage. -//------------------------------------------------------------------------------ - -// Standard Includes ----------------------------------------------------------- -#include - -// System Includes ------------------------------------------------------------- -#include - -// Project Includes ------------------------------------------------------------ -#include - -// Local Includes -------------------------------------------------------------- - -// Local Defines --------------------------------------------------------------- - -// Globals --------------------------------------------------------------------- - -namespace BPrivate { - -//------------------------------------------------------------------------------ -BMessageBody::BMessageBody() - : fFlattenedSize(0) -{ -} -//------------------------------------------------------------------------------ -BMessageBody::BMessageBody(const BMessageBody &rhs) -{ - *this = rhs; -} -//------------------------------------------------------------------------------ -BMessageBody::~BMessageBody() -{ - MakeEmpty(); -} -//------------------------------------------------------------------------------ -BMessageBody& BMessageBody::operator=(const BMessageBody &rhs) -{ - if (this != &rhs) - { - MakeEmpty(); - for (TMsgDataMap::const_iterator i = rhs.fData.begin(); - i != rhs.fData.end(); - ++i) - { - BMessageField* BMF = i->second; - fData[BMF->Name()] = BMF->Clone(); - } - fFlattenedSize = rhs.fFlattenedSize; - } - - return *this; -} -//------------------------------------------------------------------------------ -status_t BMessageBody::GetInfo(type_code typeRequested, int32 which, - char** name, type_code* typeReturned, - int32* count) const -{ - TMsgDataMap::const_iterator i = fData.begin(); - int32 index = 0; - for (index = 0; i != fData.end(); ++i) - { - if (B_ANY_TYPE == typeRequested || i->second->Type() == typeRequested) - { - if (index == which) - { - break; - } - ++index; - } - } - - // We couldn't find any appropriate data - if (i == fData.end()) - { - // TODO: research - // Which gets returned on an empty message with - // typeRequested == B_ANY_TYPE? - if (index) - { - // TODO: research - // Is B_NAME_NOT_FOUND ever really returned from this function, as - // the BeBook claims? - return B_BAD_INDEX; - } - else - { - if (count) *count = 0; - return B_BAD_TYPE; - } - } - - // TODO: BC Break - // Change 'name' parameter to const char* - *name = const_cast(i->first.c_str()); - *typeReturned = i->second->Type(); - if (count) *count = i->second->CountItems(); - - return B_OK; -} -//------------------------------------------------------------------------------ -status_t BMessageBody::GetInfo(const char* name, type_code* type, - int32* c) const -{ - status_t err; - BMessageField* BMF = FindData(name, B_ANY_TYPE, err); - if (BMF) - { - *type = BMF->Type(); - if (c) - { - *c = BMF->CountItems(); - } - } - else - { - if (c) - { - *c = 0; - } - } - - return err; -} -//------------------------------------------------------------------------------ -status_t BMessageBody::GetInfo(const char* name, type_code* type, - bool* fixed_size) const -{ - status_t err; - BMessageField* BMF = FindData(name, B_ANY_TYPE, err); - if (BMF) - { - *type = BMF->Type(); - *fixed_size = BMF->FixedSize(); - } - - return err; -} -//------------------------------------------------------------------------------ -int32 BMessageBody::CountNames(type_code type) const -{ - if (type == B_ANY_TYPE) - { - return fData.size(); - } - - int32 count = 0; - for (TMsgDataMap::const_iterator i = fData.begin(); i != fData.end(); ++i) - { - if (type == B_ANY_TYPE || i->second->Type() == type) - { - ++count; - } - } - - return count; -} -//------------------------------------------------------------------------------ -bool BMessageBody::IsEmpty() const -{ - return fData.empty(); -} -//------------------------------------------------------------------------------ -void BMessageBody::PrintToStream() const -{ - // TODO: test - for (TMsgDataMap::const_iterator i = fData.begin(); i != fData.end(); ++i) - { - i->second->PrintToStream(i->first.c_str()); - printf("\n"); - } -} -//------------------------------------------------------------------------------ -status_t BMessageBody::Rename(const char* old_entry, const char* new_entry) -{ - TMsgDataMap::iterator i = fData.find(old_entry); - if (i == fData.end()) - { - return B_NAME_NOT_FOUND; - } - BMessageField* BMF = i->second; - RemoveName(new_entry); - fData[new_entry] = BMF; - fData.erase(old_entry); - - return B_OK; -} -//------------------------------------------------------------------------------ -ssize_t BMessageBody::FlattenedSize() const -{ - ssize_t size = 1; // For MSG_LAST_ENTRY - - for (TMsgDataMap::const_iterator i = fData.begin(); i != fData.end(); ++i) - { - BMessageField* BMF = i->second; - size += BMF->FlattenedSize(); - } - - return size; -} -//------------------------------------------------------------------------------ -status_t BMessageBody::Flatten(BDataIO* stream) const -{ - status_t err = B_OK; - - for (TMsgDataMap::const_iterator i = fData.begin(); - i != fData.end() && !err; - ++i) - { - BMessageField* BMF = i->second; - err = BMF->Flatten(*stream); - } - - if (!err) - { - err = stream->Write("", 1); // For MSG_LAST_ENTRY - if (err >= 0) - err = B_OK; - } - - return err; -} -//------------------------------------------------------------------------------ -status_t BMessageBody::AddData(const char* name, type_code type, - const void* data, ssize_t numBytes, - bool is_fixed_size, int32 /* count */) -{ -/** - @note The same logic applies here are in AddFlat(): is_fixed_size and - count aren't useful to us because dynamically adding items isn't - an issue. Nevertheless, we keep is_fixed_size to set flags - appropriately when flattening the message. - */ - - // TODO: test - // In particular, we want to see what happens if is_fixed_size == true and - // the user attempts to add something bigger or smaller. We may need to - // enforce the size thing. - return B_ERROR; -} -//------------------------------------------------------------------------------ -status_t BMessageBody::RemoveData(const char* name, int32 index) -{ - if (index < 0) - { - return B_BAD_VALUE; - } - - status_t err = B_OK; - BMessageField* BMF = FindData(name, B_ANY_TYPE, err); - if (BMF) - { - if (index < BMF->CountItems()) - { - BMF->RemoveItem(index); - if (!BMF->CountItems()) - { - RemoveName(name); - } - } - else - { - err = B_BAD_INDEX; - } - } - - return err; -} -//------------------------------------------------------------------------------ -status_t BMessageBody::RemoveName(const char* name) -{ - TMsgDataMap::iterator i = fData.find(name); - if (i == fData.end()) - { - return B_NAME_NOT_FOUND; - } - - delete i->second; - fData.erase(i); - - return B_OK; -} -//------------------------------------------------------------------------------ -status_t BMessageBody::MakeEmpty() -{ - for (TMsgDataMap::iterator i = fData.begin(); - i != fData.end(); - ++i) - { - delete i->second; - } - - fData.clear(); - return B_OK; -} -//------------------------------------------------------------------------------ -#if 0 -void* BMessageBody::operator new(size_t size) -{ - return ::new BMessageBody; -} -//------------------------------------------------------------------------------ -void BMessageBody::operator delete(void* ptr, size_t size) -{ - ::delete(ptr); -} -#endif -//------------------------------------------------------------------------------ -bool BMessageBody::HasData(const char* name, type_code t, int32 n) const -{ - if (!name || n < 0) - { - return false; - } - - status_t err; - BMessageField* BMF = FindData(name, t, err); - if (!BMF) - { - return false; - } - - if (n >= BMF->CountItems()) - { - return false; - } - - return true; -} -//------------------------------------------------------------------------------ -status_t BMessageBody::FindData(const char *name, type_code type, int32 index, - const void **data, ssize_t *numBytes) const -{ - status_t err; - *data = NULL; - BMessageField* Field = FindData(name, type, err); - if (!err) - { - *data = Field->DataAt(index, numBytes); - // TODO: verify - if (!*data) - { - err = B_BAD_INDEX; - } - } - - return err; -} -//------------------------------------------------------------------------------ -BMessageField* BMessageBody::FindData(const char* name, type_code type, - status_t& err) const -{ - BMessageField* Item = NULL; - if (!name) - { - err = B_BAD_VALUE; - return Item; - } - - err = B_OK; - TMsgDataMap::const_iterator i = fData.find(name); - if (i == fData.end()) - { - err = B_NAME_NOT_FOUND; - } - else - { - Item = i->second; - if (type != B_ANY_TYPE && Item->Type() != type) - { - err = B_BAD_TYPE; - Item = NULL; - } - } - - return Item; -} -//------------------------------------------------------------------------------ - -} // namespace BPrivate - -/* - * $Log $ - * - * $Id $ - * - */ - diff --git a/src/build/libbe/app/MessageField.cpp b/src/build/libbe/app/MessageField.cpp deleted file mode 100644 index e7eead9b88..0000000000 --- a/src/build/libbe/app/MessageField.cpp +++ /dev/null @@ -1,50 +0,0 @@ -//------------------------------------------------------------------------------ -// MessageField.cpp -// -//------------------------------------------------------------------------------ - -// Standard Includes ----------------------------------------------------------- - -// System Includes ------------------------------------------------------------- -#include - -// Project Includes ------------------------------------------------------------ -#include "MessageField.h" - -// Local Includes -------------------------------------------------------------- - -// Local Defines --------------------------------------------------------------- - -// Globals --------------------------------------------------------------------- - -namespace BPrivate { - -const char* BMessageField::sNullData = "\0\0\0\0\0\0\0\0"; - -//------------------------------------------------------------------------------ -void BMessageField::PrintToStream(const char* name) const -{ - int32 type = B_BENDIAN_TO_HOST_INT32(Type()); - printf(" entry %14s, type='%.4s', c=%2ld, ", - name, (char*)&type, CountItems()); - - for (int32 i = 0; i < CountItems(); ++i) - { - if (i) - { - printf(" "); - } - PrintDataItem(i); - } -} -//------------------------------------------------------------------------------ - -} // namespace BPrivate - -/* - * $Log $ - * - * $Id $ - * - */ - diff --git a/src/build/libbe/app/MessageUtils.cpp b/src/build/libbe/app/MessageUtils.cpp index 428d81ca3c..d9f6115c5b 100644 --- a/src/build/libbe/app/MessageUtils.cpp +++ b/src/build/libbe/app/MessageUtils.cpp @@ -13,26 +13,26 @@ #include +namespace BPrivate { uint32 -_checksum_(const uchar* buf, int32 size) +CalculateChecksum(const uint8 *buffer, int32 size) { uint32 sum = 0; uint32 temp = 0; while (size > 3) { #if defined(__INTEL__) - sum += B_SWAP_INT32(*(int*)buf); + sum += B_SWAP_INT32(*(int32 *)buffer); #else - sum += *(int*)buf; + sum += *(int32 *)buffer; #endif - - buf += 4; + buffer += 4; size -= 4; } while (size > 0) { - temp = (temp << 8) + *buf++; + temp = (temp << 8) + *buffer++; size -= 1; } @@ -40,43 +40,41 @@ _checksum_(const uchar* buf, int32 size) } -namespace BPrivate { // Only putting these here because Be did - +/* entry_ref support functions */ status_t -entry_ref_flatten(char* buffer, size_t* size, const entry_ref* ref) +entry_ref_flatten(char *buffer, size_t *size, const entry_ref *ref) { - memcpy((void*)buffer, (const void*)&ref->device, sizeof (ref->device)); - buffer += sizeof (ref->device); - memcpy((void*)buffer, (const void*)&ref->directory, sizeof (ref->directory)); + memcpy((void *)buffer, (const void *)&ref->device, sizeof(ref->device)); + buffer += sizeof(ref->device); + memcpy((void *)buffer, (const void *)&ref->directory, sizeof(ref->directory)); buffer += sizeof (ref->directory); - size_t len = 0; + size_t nameLength = 0; if (ref->name) { - len = strlen(ref->name) + 1; // extra for NULL terminator - memcpy((void*)buffer, (const void*)ref->name, len); + nameLength = strlen(ref->name) + 1; + memcpy((void *)buffer, (const void *)ref->name, nameLength); } - *size = sizeof (ref->device) + sizeof (ref->directory) + len; + *size = sizeof(ref->device) + sizeof(ref->directory) + nameLength; return B_OK; } status_t -entry_ref_unflatten(entry_ref* ref, const char* buffer, size_t size) +entry_ref_unflatten(entry_ref *ref, const char *buffer, size_t size) { - if (size < (sizeof (ref->device) + sizeof (ref->directory))) { + if (size < sizeof(ref->device) + sizeof(ref->directory)) { *ref = entry_ref(); return B_BAD_VALUE; } - memcpy((void*)&ref->device, (const void*)buffer, sizeof (ref->device)); + memcpy((void *)&ref->device, (const void *)buffer, sizeof(ref->device)); buffer += sizeof (ref->device); - memcpy((void*)&ref->directory, (const void*)buffer, - sizeof (ref->directory)); - buffer += sizeof (ref->directory); + memcpy((void *)&ref->directory, (const void *)buffer, sizeof(ref->directory)); + buffer += sizeof(ref->directory); - if (ref->device != -1 - && size > (sizeof (ref->device) + sizeof (ref->directory))) { + if (ref->device != -1 && size > sizeof(ref->device) + + sizeof(ref->directory)) { ref->set_name(buffer); if (ref->name == NULL) { *ref = entry_ref(); @@ -90,41 +88,19 @@ entry_ref_unflatten(entry_ref* ref, const char* buffer, size_t size) status_t -entry_ref_swap(char* buffer, size_t size) +entry_ref_swap(char *buffer, size_t size) { - if (size < (sizeof (dev_t) + sizeof (ino_t))) - return B_BAD_DATA; + if (size < sizeof(dev_t) + sizeof(ino_t)) + return B_BAD_VALUE; - dev_t* dev = (dev_t*)buffer; + dev_t *dev = (dev_t *)buffer; *dev = B_SWAP_INT32(*dev); - buffer += sizeof (dev_t); + buffer += sizeof(dev_t); - ino_t* ino = (ino_t*)buffer; + ino_t *ino = (ino_t *)buffer; *ino = B_SWAP_INT64(*ino); return B_OK; } - -size_t -calc_padding(size_t size, size_t boundary) -{ - size_t pad = size % boundary; - if (pad) - pad = boundary - pad; - - return pad; -} - -} // namespace BPrivate - - -// #pragma mark - - - -int32 -TChecksumHelper::CheckSum() -{ - return _checksum_(fBuffer, fBufPtr - fBuffer); -} - +} // namespace BPrivate diff --git a/src/build/libbe/app/Messenger.cpp b/src/build/libbe/app/Messenger.cpp index 20a08fea5f..ddec18b48a 100644 --- a/src/build/libbe/app/Messenger.cpp +++ b/src/build/libbe/app/Messenger.cpp @@ -41,6 +41,7 @@ #include #include #include +#include #include #include #include