From c757d363afe2efd3eb224d7894d2bd82178297de Mon Sep 17 00:00:00 2001 From: JoelKatz Date: Tue, 25 Sep 2012 16:48:24 -0700 Subject: [PATCH 01/53] Parts of the new serialization code. Does not compile yet. --- src/Amount.cpp | 6 +- src/FieldNames.cpp | 40 ++++++ src/FieldNames.h | 48 +++++++- src/LedgerFormats.cpp | 134 ++++++++++---------- src/LedgerFormats.h | 6 +- src/SerializeProto.h | 23 ++-- src/SerializedLedger.h | 1 - src/SerializedObject.cpp | 92 +++++--------- src/SerializedObject.h | 102 ++++++++++------ src/SerializedTypes.cpp | 45 +++---- src/SerializedTypes.h | 174 ++++++++++++-------------- src/TransactionFormats.cpp | 242 ++++++++++++++++++------------------- src/TransactionFormats.h | 6 +- 13 files changed, 478 insertions(+), 441 deletions(-) diff --git a/src/Amount.cpp b/src/Amount.cpp index f0692f2af7..56b0104a3b 100644 --- a/src/Amount.cpp +++ b/src/Amount.cpp @@ -298,7 +298,7 @@ void STAmount::add(Serializer& s) const } } -STAmount::STAmount(const char* name, int64 value) : SerializedType(name), mOffset(0), mIsNative(true) +STAmount::STAmount(FieldName* name, int64 value) : SerializedType(name), mOffset(0), mIsNative(true) { if (value >= 0) { @@ -330,7 +330,7 @@ uint64 STAmount::toUInt64() const return mValue | (static_cast(mOffset + 256 + 97) << (64 - 10)); } -STAmount* STAmount::construct(SerializerIterator& sit, const char *name) +STAmount* STAmount::construct(SerializerIterator& sit, FieldName* name) { uint64 value = sit.get64(); @@ -883,7 +883,7 @@ uint64 STAmount::convertToDisplayAmount(const STAmount& internalAmount, uint64 t } STAmount STAmount::convertToInternalAmount(uint64 displayAmount, uint64 totalNow, uint64 totalInit, - const char *name) + FieldName* name) { // Convert a display/request currency amount to an internal amount return STAmount(name, muldiv(displayAmount, totalNow, totalInit)); } diff --git a/src/FieldNames.cpp b/src/FieldNames.cpp index a65ce1bc93..72589d0004 100644 --- a/src/FieldNames.cpp +++ b/src/FieldNames.cpp @@ -1,13 +1,53 @@ #include "FieldNames.h" +#include + +#include + #define FIELD(name, type, index) { sf##name, #name, STI_##type, index }, #define TYPE(name, type, index) FieldName FieldNames[]= { #include "SerializeProto.h" + + { sfInvalid, 0, STI_DONE, 0 } }; #undef FIELD #undef TYPE + +static std::map unknownFieldMap; +static boost::mutex unknownFieldMutex; + +FieldName* getFieldName(SOE_Field f) +{ // OPTIMIZEME + for (FieldName* n = FieldNames; n->fieldName != 0; ++n) + if (n->field == f) + return n; + return NULL; +} + +FieldName* getFieldName(int type, int field) +{ // OPTIMIZEME + int f = (type << 16) | field; + for (FieldName* n = FieldNames; n->fieldName != 0; ++n) + if (n->field == f) + return n; + if ((type <= 0) || (type >= 256) || (field <= 0) || (field >= 256 + return NULL; + + boost::mutex::scoped_lock sl(unknownFieldMutex); + std::map it = unknownFieldMap.Find(f); + if (it != unknownFieldMap.end()) + return it->second; + + FieldName* n = new FieldName(); + n->field = f; + n->fieldName = "unknown"; + n->fieldType = static_cast(type); + n->fieldNum = field; + unknownFieldMap[f] = n; + return n; +} diff --git a/src/FieldNames.h b/src/FieldNames.h index af760127f6..b056b237fb 100644 --- a/src/FieldNames.h +++ b/src/FieldNames.h @@ -1,16 +1,56 @@ #ifndef __FIELDNAMES__ #define __FIELDNAMES__ -#include "SerializedTypes.h" -#include "SerializedObject.h" +enum SerializedTypeID +{ + // special types + STI_DONE = -1, + STI_NOTPRESENT = 0, + +#define TYPE(name, field, value) STI_##field = value, +#define FIELD(name, field, value) +#include "SerializeProto.h" +#undef TYPE +#undef FIELD + + // high level types + STI_TRANSACTION = 100001, + STI_LEDGERENTRY = 100002, + STI_VALIDATION = 100003, +}; + +enum SOE_Flags +{ + SOE_END = -1, // marks end of object + SOE_REQUIRED = 0, // required + SOE_OPTIONAL = 1, // optional +}; + +enum SOE_Field +{ + sfInvalid = -1, + sfGeneric = 0, + +#define FIELD(name, type, index) sf##name = (STI_##type << 16) | index, +#define TYPE(name, type, index) +#include "SerializeProto.h" +#undef FIELD +#undef TYPE + + // test fields + sfTest1=100000, sfTest2, sfTest3, sfTest4 +}; struct FieldName { SOE_Field field; const char *fieldName; SerializedTypeID fieldType; - int fieldValue; - int fieldID; + int fieldNum; }; +extern FieldName FieldNames[]; +extern FieldName* getFieldName(SOE_Field); +extern FieldName* getFieldName(int type, int field); + #endif diff --git a/src/LedgerFormats.cpp b/src/LedgerFormats.cpp index 1db310a4c1..37cc7906e4 100644 --- a/src/LedgerFormats.cpp +++ b/src/LedgerFormats.cpp @@ -1,89 +1,87 @@ #include "LedgerFormats.h" -#define S_FIELD(x) sf##x, #x - LedgerEntryFormat LedgerFormats[]= { { "AccountRoot", ltACCOUNT_ROOT, { - { S_FIELD(Flags), STI_UINT32, SOE_FLAGS, 0 }, - { S_FIELD(Account), STI_ACCOUNT, SOE_REQUIRED, 0 }, - { S_FIELD(Sequence), STI_UINT32, SOE_REQUIRED, 0 }, - { S_FIELD(Balance), STI_AMOUNT, SOE_REQUIRED, 0 }, - { S_FIELD(LastTxnID), STI_HASH256, SOE_REQUIRED, 0 }, - { S_FIELD(LastTxnSeq), STI_UINT32, SOE_REQUIRED, 0 }, - { S_FIELD(AuthorizedKey), STI_ACCOUNT, SOE_IFFLAG, 1 }, - { S_FIELD(EmailHash), STI_HASH128, SOE_IFFLAG, 2 }, - { S_FIELD(WalletLocator), STI_HASH256, SOE_IFFLAG, 4 }, - { S_FIELD(MessageKey), STI_VL, SOE_IFFLAG, 8 }, - { S_FIELD(TransferRate), STI_UINT32, SOE_IFFLAG, 16 }, - { S_FIELD(Domain), STI_VL, SOE_IFFLAG, 32 }, - { S_FIELD(PublishHash), STI_HASH256, SOE_IFFLAG, 64 }, - { S_FIELD(PublishSize), STI_UINT32, SOE_IFFLAG, 128 }, - { sfInvalid, NULL, STI_DONE, SOE_NEVER, -1 } } + { sfFlags, SOE_REQUIRED }, + { sfAccount, SOE_REQUIRED }, + { sfSequence, SOE_REQUIRED }, + { sfBalance, SOE_REQUIRED }, + { sfLastTxnID, SOE_REQUIRED }, + { sfLastTxnSeq, SOE_REQUIRED }, + { sfAuthorizedKey, SOE_OPTIONAL }, + { sfEmailHash, SOE_OPTIONAL }, + { sfWalletLocator, SOE_OPTIONAL }, + { sfMessageKey, SOE_OPTIONAL }, + { sfTransferRate, SOE_OPTIONAL }, + { sfDomain, SOE_OPTIONAL }, + { sfPublishHash, SOE_OPTIONAL }, + { sfPublishSize, SOE_OPTIONAL }, + { sfInvalid, SOE_END } } }, { "Contract", ltCONTRACT, { - { S_FIELD(Flags), STI_UINT32, SOE_FLAGS, 0 }, - { S_FIELD(Account), STI_ACCOUNT, SOE_REQUIRED, 0 }, - { S_FIELD(Balance), STI_AMOUNT, SOE_REQUIRED, 0 }, - { S_FIELD(LastTxnID), STI_HASH256, SOE_REQUIRED, 0 }, - { S_FIELD(LastTxnSeq), STI_UINT32, SOE_REQUIRED, 0 }, - { S_FIELD(Issuer), STI_ACCOUNT, SOE_REQUIRED, 0 }, - { S_FIELD(Owner), STI_ACCOUNT, SOE_REQUIRED, 0 }, - { S_FIELD(Expiration), STI_UINT32, SOE_REQUIRED, 0 }, - { S_FIELD(BondAmount), STI_UINT32, SOE_REQUIRED, 0 }, - { S_FIELD(CreateCode), STI_VL, SOE_REQUIRED, 0 }, - { S_FIELD(FundCode), STI_VL, SOE_REQUIRED, 0 }, - { S_FIELD(RemoveCode), STI_VL, SOE_REQUIRED, 0 }, - { S_FIELD(ExpireCode), STI_VL, SOE_REQUIRED, 0 }, - { sfInvalid, NULL, STI_DONE, SOE_NEVER, -1 } } + { sfFlags, SOE_REQUIRED }, + { sfAccount, SOE_REQUIRED }, + { sfBalance, SOE_REQUIRED }, + { sfLastTxnID, SOE_REQUIRED }, + { sfLastTxnSeq, SOE_REQUIRED }, + { sfIssuer, SOE_REQUIRED }, + { sfOwner, SOE_REQUIRED }, + { sfExpiration, SOE_REQUIRED }, + { sfBondAmount, SOE_REQUIRED }, + { sfCreateCode, SOE_REQUIRED }, + { sfFundCode, SOE_REQUIRED }, + { sfRemoveCode, SOE_REQUIRED }, + { sfExpireCode, SOE_REQUIRED }, + { sfInvalid, SOE_END } } }, { "DirectoryNode", ltDIR_NODE, { - { S_FIELD(Flags), STI_UINT32, SOE_FLAGS, 0 }, - { S_FIELD(Indexes), STI_VECTOR256, SOE_REQUIRED, 0 }, - { S_FIELD(IndexNext), STI_UINT64, SOE_IFFLAG, 1 }, - { S_FIELD(IndexPrevious), STI_UINT64, SOE_IFFLAG, 2 }, - { sfInvalid, NULL, STI_DONE, SOE_NEVER, -1 } } + { sfFlags, SOE_REQUIRED }, + { sfIndexes, SOE_REQUIRED }, + { sfIndexNext, SOE_OPTIONAL }, + { sfIndexPrevious, SOE_OPTIONAL }, + { sfInvalid, SOE_END } } }, { "GeneratorMap", ltGENERATOR_MAP, { - { S_FIELD(Flags), STI_UINT32, SOE_FLAGS, 0 }, - { S_FIELD(Generator), STI_VL, SOE_REQUIRED, 0 }, - { sfInvalid, NULL, STI_DONE, SOE_NEVER, -1 } } + { sfFlags, SOE_REQUIRED }, + { sfGenerator, SOE_REQUIRED }, + { sfInvalid, SOE_END } } }, { "Nickname", ltNICKNAME, { - { S_FIELD(Flags), STI_UINT32, SOE_FLAGS, 0 }, - { S_FIELD(Account), STI_ACCOUNT, SOE_REQUIRED, 0 }, - { S_FIELD(MinimumOffer), STI_AMOUNT, SOE_IFFLAG, 1 }, - { sfInvalid, NULL, STI_DONE, SOE_NEVER, -1 } } + { sfFlags, SOE_REQUIRED }, + { sfAccount, SOE_REQUIRED }, + { sfMinimumOffer, SOE_OPTIONAL }, + { sfInvalid, SOE_END } } }, { "Offer", ltOFFER, { - { S_FIELD(Flags), STI_UINT32, SOE_FLAGS, 0 }, - { S_FIELD(Account), STI_ACCOUNT, SOE_REQUIRED, 0 }, - { S_FIELD(Sequence), STI_UINT32, SOE_REQUIRED, 0 }, - { S_FIELD(TakerPays), STI_AMOUNT, SOE_REQUIRED, 0 }, - { S_FIELD(TakerGets), STI_AMOUNT, SOE_REQUIRED, 0 }, - { S_FIELD(BookDirectory), STI_HASH256, SOE_REQUIRED, 0 }, - { S_FIELD(BookNode), STI_UINT64, SOE_REQUIRED, 0 }, - { S_FIELD(OwnerNode), STI_UINT64, SOE_REQUIRED, 0 }, - { S_FIELD(LastTxnID), STI_HASH256, SOE_REQUIRED, 0 }, - { S_FIELD(LastTxnSeq), STI_UINT32, SOE_REQUIRED, 0 }, - { S_FIELD(Expiration), STI_UINT32, SOE_IFFLAG, 1 }, - { sfInvalid, NULL, STI_DONE, SOE_NEVER, -1 } } + { sfFlags, SOE_REQUIRED }, + { sfAccount, SOE_REQUIRED }, + { sfSequence, SOE_REQUIRED }, + { sfTakerPays, SOE_REQUIRED }, + { sfTakerGets, SOE_REQUIRED }, + { sfBookDirectory, SOE_REQUIRED }, + { sfBookNode, SOE_REQUIRED }, + { sfOwnerNode, SOE_REQUIRED }, + { sfLastTxnID, SOE_REQUIRED }, + { sfLastTxnSeq, SOE_REQUIRED }, + { sfExpiration, SOE_OPTIONAL }, + { sfInvalid, SOE_END } } }, { "RippleState", ltRIPPLE_STATE, { - { S_FIELD(Flags), STI_UINT32, SOE_FLAGS, 0 }, - { S_FIELD(Balance), STI_AMOUNT, SOE_REQUIRED, 0 }, - { S_FIELD(LowID), STI_ACCOUNT, SOE_REQUIRED, 0 }, - { S_FIELD(LowLimit), STI_AMOUNT, SOE_REQUIRED, 0 }, - { S_FIELD(HighID), STI_ACCOUNT, SOE_REQUIRED, 0 }, - { S_FIELD(HighLimit), STI_AMOUNT, SOE_REQUIRED, 0 }, - { S_FIELD(LastTxnID), STI_HASH256, SOE_REQUIRED, 0 }, - { S_FIELD(LastTxnSeq), STI_UINT32, SOE_REQUIRED, 0 }, - { S_FIELD(LowQualityIn), STI_UINT32, SOE_IFFLAG, 1 }, - { S_FIELD(LowQualityOut), STI_UINT32, SOE_IFFLAG, 2 }, - { S_FIELD(HighQualityIn), STI_UINT32, SOE_IFFLAG, 4 }, - { S_FIELD(HighQualityOut), STI_UINT32, SOE_IFFLAG, 8 }, - { sfInvalid, NULL, STI_DONE, SOE_NEVER, -1 } } + { sfFlags, SOE_REQUIRED }, + { sfBalance, SOE_REQUIRED }, + { sfLowID, SOE_REQUIRED }, + { sfLowLimit, SOE_REQUIRED }, + { sfHighID, SOE_REQUIRED }, + { sfHighLimit, SOE_REQUIRED }, + { sfLastTxnID, SOE_REQUIRED }, + { sfLastTxnSeq, SOE_REQUIRED }, + { sfLowQualityIn, SOE_OPTIONAL }, + { sfLowQualityOut, SOE_OPTIONAL }, + { sfHighQualityIn, SOE_OPTIONAL }, + { sfHighQualityOut, SOE_OPTIONAL }, + { sfInvalid, SOE_END } } }, { NULL, ltINVALID } }; diff --git a/src/LedgerFormats.h b/src/LedgerFormats.h index c1cdc505b6..82221ca31d 100644 --- a/src/LedgerFormats.h +++ b/src/LedgerFormats.h @@ -41,9 +41,9 @@ enum LedgerSpecificFlags struct LedgerEntryFormat { - const char *t_name; - LedgerEntryType t_type; - SOElement elements[20]; + const char * t_name; + LedgerEntryType t_type; + SOElement elements[24]; }; extern LedgerEntryFormat LedgerFormats[]; diff --git a/src/SerializeProto.h b/src/SerializeProto.h index d2336e8971..bf60039fb8 100644 --- a/src/SerializeProto.h +++ b/src/SerializeProto.h @@ -27,17 +27,18 @@ FIELD(CloseResolution, UINT8, 1) // 32-bit integers (common) - FIELD(Flags, UINT32, 1) - FIELD(SourceTag, UINT32, 2) - FIELD(Sequence, UINT32, 3) - FIELD(LastTxnSeq, UINT32, 4) - FIELD(LedgerSequence, UINT32, 5) - FIELD(CloseTime, UINT32, 6) - FIELD(ParentCloseTime, UINT32, 7) - FIELD(SigningTime, UINT32, 8) - FIELD(Expiration, UINT32, 9) - FIELD(TransferRate, UINT32, 10) - FIELD(PublishSize, UINT32, 11) + FIELD(ObjectType, UINT32, 1) + FIELD(Flags, UINT32, 2) + FIELD(SourceTag, UINT32, 3) + FIELD(Sequence, UINT32, 4) + FIELD(LastTxnSeq, UINT32, 5) + FIELD(LedgerSequence, UINT32, 6) + FIELD(CloseTime, UINT32, 7) + FIELD(ParentCloseTime, UINT32, 8) + FIELD(SigningTime, UINT32, 9) + FIELD(Expiration, UINT32, 10) + FIELD(TransferRate, UINT32, 11) + FIELD(PublishSize, UINT32, 12) // 32-bit integers (uncommon) FIELD(HighQualityIn, UINT32, 16) diff --git a/src/SerializedLedger.h b/src/SerializedLedger.h index 1069887cc2..e60662d2db 100644 --- a/src/SerializedLedger.h +++ b/src/SerializedLedger.h @@ -25,7 +25,6 @@ public: SerializedLedgerEntry(SerializerIterator& sit, const uint256& index); SerializedLedgerEntry(LedgerEntryType type); - int getLength() const { return mVersion.getLength() + mObject.getLength(); } SerializedTypeID getSType() const { return STI_LEDGERENTRY; } std::string getFullText() const; std::string getText() const; diff --git a/src/SerializedObject.cpp b/src/SerializedObject.cpp index eaf7ec4006..c1167a6d62 100644 --- a/src/SerializedObject.cpp +++ b/src/SerializedObject.cpp @@ -8,7 +8,7 @@ #include "Log.h" -std::auto_ptr STObject::makeDefaultObject(SerializedTypeID id, const char *name) +std::auto_ptr STObject::makeDefaultObject(SerializedTypeID id, FieldName* name) { switch(id) { @@ -53,8 +53,8 @@ std::auto_ptr STObject::makeDefaultObject(SerializedTypeID id, c } } -std::auto_ptr STObject::makeDeserializedObject(SerializedTypeID id, const char *name, - SerializerIterator& sit) +std::auto_ptr STObject::makeDeserializedObject(SerializedTypeID id, FieldName* name, + SerializerIterator& sit, int depth) { switch(id) { @@ -94,6 +94,12 @@ std::auto_ptr STObject::makeDeserializedObject(SerializedTypeID case STI_PATHSET: return STPathSet::deserialize(sit, name); + case STI_ARRAY: + return STArray::deserialize(sit, name); + + case STI_OBJECT: + return STObject::deserialize(sit, name); + default: throw std::runtime_error("Unknown object type"); } @@ -103,13 +109,11 @@ void STObject::set(const SOElement* elem) { mData.empty(); mType.empty(); - mFlagIdx = -1; - while (elem->e_id != STI_DONE) + while (elem->flags != SOE_END) { - if (elem->e_type == SOE_FLAGS) mFlagIdx = mType.size(); mType.push_back(elem); - if (elem->e_type == SOE_IFFLAG) + if (elem->flags == SOE_OPTIONAL) giveObject(makeDefaultObject(STI_NOTPRESENT, elem->e_name)); else giveObject(makeDefaultObject(elem->e_id, elem->e_name)); @@ -117,55 +121,30 @@ void STObject::set(const SOElement* elem) } } -STObject::STObject(const SOElement* elem, const char *name) : SerializedType(name) +STObject::STObject(const SOElement* elem, FieldName* name) : SerializedType(name) { set(elem); } -void STObject::set(const SOElement* elem, SerializerIterator& sit) +void STObject::set(FieldName* name, SerializerIterator& sit, int depth = 0) { mData.empty(); mType.empty(); - mFlagIdx = -1; - int flags = -1; - while (elem->e_id != STI_DONE) + fName = name; + + while(1) { - mType.push_back(elem); - bool done = false; - if (elem->e_type == SOE_IFFLAG) - { - assert(flags >= 0); - if ((flags&elem->e_flags) == 0) - { - done = true; - giveObject(makeDefaultObject(STI_NOTPRESENT, elem->e_name)); - } - } - else if (elem->e_type == SOE_IFNFLAG) - { - assert(flags >= 0); - if ((flags&elem->e_flags) != 0) - { - done = true; - giveObject(makeDefaultObject(elem->e_id, elem->e_name)); - } - } - else if (elem->e_type == SOE_FLAGS) - { - assert(elem->e_id == STI_UINT32); - flags = sit.get32(); - mFlagIdx = giveObject(new STUInt32(elem->e_name, flags)); - done = true; - } - if (!done) - giveObject(makeDeserializedObject(elem->e_id, elem->e_name, sit)); - elem++; + int type, field. + sit.getFieldID(type, field); + if ((type == STI_ARRAY) && (field == 1)) + return; + FieldName* fn = getFieldName(type, field); + giveObject(makeDeserializedObject(static_cast type, fn, sit, depth + 1); } } -STObject::STObject(const SOElement* elem, SerializerIterator& sit, const char *name) - : SerializedType(name), mFlagIdx(-1) +STObject::STObject(const SOElement* elem, SerializerIterator& sit, FieldName*name) : SerializedType(name) { set(elem, sit); } @@ -193,14 +172,6 @@ std::string STObject::getFullText() const return ret; } -int STObject::getLength() const -{ - int ret = 0; - BOOST_FOREACH(const SerializedType& it, mData) - ret += it.getLength(); - return ret; -} - void STObject::add(Serializer& s) const { BOOST_FOREACH(const SerializedType& it, mData) @@ -295,9 +266,9 @@ bool STObject::isFieldPresent(SOE_Field field) const bool STObject::setFlag(uint32 f) { - if (mFlagIdx < 0) return false; - STUInt32* t = dynamic_cast(getPIndex(mFlagIdx)); - assert(t); + STUInt32* t = dynamic_cast(getPField(sfFlags)); + if (!t) + return false; t->setValue(t->getValue() | f); return true; } @@ -305,17 +276,18 @@ bool STObject::setFlag(uint32 f) bool STObject::clearFlag(uint32 f) { if (mFlagIdx < 0) return false; - STUInt32* t = dynamic_cast(getPIndex(mFlagIdx)); - assert(t); + STUInt32* t = dynamic_cast(getPField(sfFlags)); + if (!t) + return false; t->setValue(t->getValue() & ~f); return true; } uint32 STObject::getFlags(void) const { - if (mFlagIdx < 0) return 0; - const STUInt32* t = dynamic_cast(peekAtPIndex(mFlagIdx)); - assert(t); + const STUInt32* t = dynamic_cast(peekAtPField(mFlagIdx)); + if (!t) + return 0; return t->getValue(); } diff --git a/src/SerializedObject.h b/src/SerializedObject.h index 3ff352a793..f4f372ac5d 100644 --- a/src/SerializedObject.h +++ b/src/SerializedObject.h @@ -9,56 +9,30 @@ #include "SerializedTypes.h" -enum SOE_Type -{ - SOE_NEVER = -1, // never occurs (marks end of object) - SOE_REQUIRED = 0, // required - SOE_FLAGS = 1, // flags field - SOE_IFFLAG = 2, // present if flag set - SOE_IFNFLAG = 3 // present if flag not set -}; - -enum SOE_Field -{ - sfInvalid = -1, - sfGeneric = 0, - -#define FIELD(name, type, index) sf##name, -#define TYPE(name, type, index) -#include "SerializeProto.h" -#undef FIELD -#undef TYPE - - // test fields - sfTest1, sfTest2, sfTest3, sfTest4 -}; +// Serializable object/array types struct SOElement { // An element in the description of a serialized object SOE_Field e_field; - const char *e_name; - SerializedTypeID e_id; - SOE_Type e_type; - int e_flags; + SOE_Flags flags; }; class STObject : public SerializedType { protected: - int mFlagIdx; // the offset to the flags object, -1 if none boost::ptr_vector mData; std::vector mType; STObject* duplicate() const { return new STObject(*this); } public: - STObject(const char *n = NULL) : SerializedType(n), mFlagIdx(-1) { ; } - STObject(const SOElement *t, const char *n = NULL); - STObject(const SOElement *t, SerializerIterator& u, const char *n = NULL); + STObject(FieldName *n = NULL) : SerializedType(n) { ; } + STObject(const SOElement *t, FieldName *n = NULL); + STObject(const SOElement *t, SerializerIterator& u, FieldName *n = NULL); virtual ~STObject() { ; } void set(const SOElement* t); - void set(const SOElement* t, SerializerIterator& u); + void set(const SOElement* t, SerializerIterator& u, int depth = 0); int getLength() const; virtual SerializedTypeID getSType() const { return STI_OBJECT; } @@ -133,13 +107,71 @@ public: SerializedType* makeFieldPresent(SOE_Field field); void makeFieldAbsent(SOE_Field field); - static std::auto_ptr makeDefaultObject(SerializedTypeID id, const char *name); - static std::auto_ptr makeDeserializedObject(SerializedTypeID id, const char *name, - SerializerIterator&); + static std::auto_ptr makeDefaultObject(SerializedTypeID id, FieldName *name); + static std::auto_ptr makeDeserializedObject(SerializedTypeID id, FieldName *name, + SerializerIterator&, int depth); static void unitTest(); }; +class STArray : public SerializedType +{ +public: + typedef std::vector vector; + typedef std::vector::iterator iterator; + typedef std::vector::const_iterator const_iterator; + typedef std::vector::reverse_iterator reverse_iterator; + typedef std::vector::const_reverse_iterator const_reverse_iterator; + typedef std::vector::size_type size_type; + +protected: + + vector value; + + STArray* duplicate() const { return new STArray(fName, value); } + static STArray* construct(SerializerIterator&, FieldName* name = NULL); + +public: + + STArray() { ; } + STArray(FieldName* f, const vector& v) : SerializedType(f), value(v) { ; } + STArray(vector& v) : value(v) { ; } + + static std::auto_ptr deserialize(SerializerIterator& sit, FieldName* name) + { return std::auto_ptr(construct(sit, name)); } + + const vector& getValue() const { return value; } + vector& getValue() { return value; } + + // vector-like functions + void push_back(const STObject& object) { value.push_back(object); } + STObject& operator[](int j) { return value[j]; } + const STObject& operator[](int j) const { return value[j]; } + iterator begin() { return value.begin(); } + const_iterator begin() const { return value.begin(); } + iterator end() { return value.end(); } + const_iterator end() const { return value.end(); } + size_type size() const { return value.size(); } + reverse_iterator rbegin() { return value.rbegin(); } + const_reverse_iterator rbegin() const { return value.rbegin(); } + reverse_iterator rend() { return value.rend(); } + const_reverse_iterator rend() const { return value.rend(); } + iterator erase(iterator pos) { return value.erase(pos); } + void pop_back() { value.pop_back(); } + bool empty() const { return value.empty(); } + void clear() { value.clear(); } + + virtual std::string getFullText() const; + virtual std::string getText() const; + virtual Json::Value getJson(int) const; + virtual void add(Serializer& s) const; + + bool operator==(const STArray &s) { return value == s.value; } + bool operator!=(const STArray &s) { return value != s.value; } + + virtual SerializedTypeID getSType() const { return STI_ARRAY; } + virtual bool isEquivalent(const SerializedType& t) const; +}; #endif // vim:ts=4 diff --git a/src/SerializedTypes.cpp b/src/SerializedTypes.cpp index dde47265c0..25339b92e7 100644 --- a/src/SerializedTypes.cpp +++ b/src/SerializedTypes.cpp @@ -17,9 +17,9 @@ std::string SerializedType::getFullText() const std::string ret; if (getSType() != STI_NOTPRESENT) { - if(name != NULL) + if(fName != NULL) { - ret = name; + ret = fName->fieldName; ret += " = "; } ret += getText(); @@ -27,7 +27,7 @@ std::string SerializedType::getFullText() const return ret; } -STUInt8* STUInt8::construct(SerializerIterator& u, const char *name) +STUInt8* STUInt8::construct(SerializerIterator& u, FieldName* name) { return new STUInt8(name, u.get8()); } @@ -43,7 +43,7 @@ bool STUInt8::isEquivalent(const SerializedType& t) const return v && (value == v->value); } -STUInt16* STUInt16::construct(SerializerIterator& u, const char *name) +STUInt16* STUInt16::construct(SerializerIterator& u, FieldName* name) { return new STUInt16(name, u.get16()); } @@ -59,7 +59,7 @@ bool STUInt16::isEquivalent(const SerializedType& t) const return v && (value == v->value); } -STUInt32* STUInt32::construct(SerializerIterator& u, const char *name) +STUInt32* STUInt32::construct(SerializerIterator& u, FieldName* name) { return new STUInt32(name, u.get32()); } @@ -75,7 +75,7 @@ bool STUInt32::isEquivalent(const SerializedType& t) const return v && (value == v->value); } -STUInt64* STUInt64::construct(SerializerIterator& u, const char *name) +STUInt64* STUInt64::construct(SerializerIterator& u, FieldName* name) { return new STUInt64(name, u.get64()); } @@ -91,7 +91,7 @@ bool STUInt64::isEquivalent(const SerializedType& t) const return v && (value == v->value); } -STHash128* STHash128::construct(SerializerIterator& u, const char *name) +STHash128* STHash128::construct(SerializerIterator& u, FieldName* name) { return new STHash128(name, u.get128()); } @@ -107,7 +107,7 @@ bool STHash128::isEquivalent(const SerializedType& t) const return v && (value == v->value); } -STHash160* STHash160::construct(SerializerIterator& u, const char *name) +STHash160* STHash160::construct(SerializerIterator& u, FieldName* name) { return new STHash160(name, u.get160()); } @@ -123,7 +123,7 @@ bool STHash160::isEquivalent(const SerializedType& t) const return v && (value == v->value); } -STHash256* STHash256::construct(SerializerIterator& u, const char *name) +STHash256* STHash256::construct(SerializerIterator& u, FieldName* name) { return new STHash256(name, u.get256()); } @@ -139,7 +139,7 @@ bool STHash256::isEquivalent(const SerializedType& t) const return v && (value == v->value); } -STVariableLength::STVariableLength(SerializerIterator& st, const char *name) : SerializedType(name) +STVariableLength::STVariableLength(SerializerIterator& st, FieldName* name) : SerializedType(name) { value = st.getVL(); } @@ -149,16 +149,11 @@ std::string STVariableLength::getText() const return strHex(value); } -STVariableLength* STVariableLength::construct(SerializerIterator& u, const char *name) +STVariableLength* STVariableLength::construct(SerializerIterator& u, FieldName* name) { return new STVariableLength(name, u.getVL()); } -int STVariableLength::getLength() const -{ - return Serializer::encodeLengthLength(value.size()) + value.size(); -} - bool STVariableLength::isEquivalent(const SerializedType& t) const { const STVariableLength* v = dynamic_cast(&t); @@ -176,7 +171,7 @@ std::string STAccount::getText() const return a.humanAccountID(); } -STAccount* STAccount::construct(SerializerIterator& u, const char *name) +STAccount* STAccount::construct(SerializerIterator& u, FieldName* name) { return new STAccount(name, u.getVL()); } @@ -186,7 +181,7 @@ STAccount* STAccount::construct(SerializerIterator& u, const char *name) // // Return a new object from a SerializerIterator. -STVector256* STVector256::construct(SerializerIterator& u, const char *name) +STVector256* STVector256::construct(SerializerIterator& u, FieldName* name) { std::vector data = u.getVL(); std::vector value; @@ -255,7 +250,7 @@ void STAccount::setValueNCA(const NewcoinAddress& nca) setValueH160(nca.getAccountID()); } -STPathSet* STPathSet::construct(SerializerIterator& s, const char *name) +STPathSet* STPathSet::construct(SerializerIterator& s, FieldName* name) { std::vector paths; std::vector path; @@ -342,18 +337,6 @@ int STPath::getSerializeSize() const return iBytes; } -int STPathSet::getLength() const -{ - int iBytes = 0; - - BOOST_FOREACH(const STPath& spPath, value) - { - iBytes += spPath.getSerializeSize(); - } - - return iBytes ? iBytes : 1; -} - Json::Value STPath::getJson(int) const { Json::Value ret(Json::arrayValue); diff --git a/src/SerializedTypes.h b/src/SerializedTypes.h index 28a3063677..f31a468d85 100644 --- a/src/SerializedTypes.h +++ b/src/SerializedTypes.h @@ -8,28 +8,13 @@ #include "uint256.h" #include "Serializer.h" +#include "FieldNames.h" -enum SerializedTypeID -{ - // special types - STI_DONE = -1, - STI_NOTPRESENT = 0, - -#define TYPE(name, field, value) STI_##field = value, -#define FIELD(name, field, value) -#include "SerializeProto.h" -#undef TYPE -#undef FIELD - - // high level types - STI_TRANSACTION = 100001, - STI_LEDGERENTRY = 100002 -}; enum PathFlags { PF_END = 0x00, // End of current path & path list. - PF_BOUNDRY = 0xFF, // End of current path & new path follows. + PF_BOUNDARY = 0xFF, // End of current path & new path follows. PF_ACCOUNT = 0x01, PF_OFFER = 0x02, @@ -48,24 +33,24 @@ enum PathFlags class SerializedType { protected: - const char* name; + FieldName* fName; - virtual SerializedType* duplicate() const { return new SerializedType(name); } + virtual SerializedType* duplicate() const { return new SerializedType(fName); } public: - SerializedType() : name(NULL) { ; } - SerializedType(const char* n) : name(n) { ; } - SerializedType(const SerializedType& n) : name(n.name) { ; } + SerializedType() : fName(NULL) { ; } + SerializedType(FieldName* n) : fName(n) { ; } + SerializedType(const SerializedType& n) : fName(n.fName) { ; } virtual ~SerializedType() { ; } - static std::auto_ptr deserialize(const char* name) + static std::auto_ptr deserialize(FieldName* name) { return std::auto_ptr(new SerializedType(name)); } - void setName(const char* n) { name=n; } - const char *getName() const { return name; } + void setFName(FieldName* n) { fName=n; } + FieldName* getFName() { return fName; } + const char *getName() const { return (fName != NULL) ? fName->fieldName : NULL; } - virtual int getLength() const { return 0; } virtual SerializedTypeID getSType() const { return STI_NOTPRESENT; } std::auto_ptr clone() const { return std::auto_ptr(duplicate()); } @@ -81,7 +66,7 @@ public: { assert(getSType() == STI_NOTPRESENT); return t.getSType() == STI_NOTPRESENT; } SerializedType& operator=(const SerializedType& t) - { name = (name == NULL) ? t.name : name; return *this; } + { if (fName == NULL) fName = t.fName; return *this; } bool operator==(const SerializedType& t) const { return (getSType() == t.getSType()) && isEquivalent(t); } bool operator!=(const SerializedType& t) const @@ -97,23 +82,22 @@ class STUInt8 : public SerializedType protected: unsigned char value; - STUInt8* duplicate() const { return new STUInt8(name, value); } - static STUInt8* construct(SerializerIterator&, const char* name = NULL); + STUInt8* duplicate() const { return new STUInt8(fName, value); } + static STUInt8* construct(SerializerIterator&, FieldName* name = NULL); public: STUInt8(unsigned char v=0) : value(v) { ; } - STUInt8(const char* n, unsigned char v=0) : SerializedType(n), value(v) { ; } - static std::auto_ptr deserialize(SerializerIterator& sit, const char* name) + STUInt8(FieldName* n, unsigned char v=0) : SerializedType(n), value(v) { ; } + static std::auto_ptr deserialize(SerializerIterator& sit, FieldName* name) { return std::auto_ptr(construct(sit, name)); } - int getLength() const { return 1; } SerializedTypeID getSType() const { return STI_UINT8; } std::string getText() const; void add(Serializer& s) const { s.add8(value); } unsigned char getValue() const { return value; } - void setValue(unsigned char v) { value=v; } + void setValue(unsigned char v) { value = v; } operator unsigned char() const { return value; } virtual bool isEquivalent(const SerializedType& t) const; @@ -124,17 +108,16 @@ class STUInt16 : public SerializedType protected: uint16 value; - STUInt16* duplicate() const { return new STUInt16(name, value); } - static STUInt16* construct(SerializerIterator&, const char* name = NULL); + STUInt16* duplicate() const { return new STUInt16(fName, value); } + static STUInt16* construct(SerializerIterator&, FieldName* name = NULL); public: STUInt16(uint16 v=0) : value(v) { ; } - STUInt16(const char* n, uint16 v=0) : SerializedType(n), value(v) { ; } - static std::auto_ptr deserialize(SerializerIterator& sit, const char* name) + STUInt16(FieldName* n, uint16 v=0) : SerializedType(n), value(v) { ; } + static std::auto_ptr deserialize(SerializerIterator& sit, FieldName* name) { return std::auto_ptr(construct(sit, name)); } - int getLength() const { return 2; } SerializedTypeID getSType() const { return STI_UINT16; } std::string getText() const; void add(Serializer& s) const { s.add16(value); } @@ -151,17 +134,16 @@ class STUInt32 : public SerializedType protected: uint32 value; - STUInt32* duplicate() const { return new STUInt32(name, value); } - static STUInt32* construct(SerializerIterator&, const char* name = NULL); + STUInt32* duplicate() const { return new STUInt32(fName, value); } + static STUInt32* construct(SerializerIterator&, FieldName* name = NULL); public: STUInt32(uint32 v=0) : value(v) { ; } - STUInt32(const char* n, uint32 v=0) : SerializedType(n), value(v) { ; } - static std::auto_ptr deserialize(SerializerIterator& sit, const char* name) + STUInt32(FieldName* n, uint32 v=0) : SerializedType(n), value(v) { ; } + static std::auto_ptr deserialize(SerializerIterator& sit, FieldName* name) { return std::auto_ptr(construct(sit, name)); } - int getLength() const { return 4; } SerializedTypeID getSType() const { return STI_UINT32; } std::string getText() const; void add(Serializer& s) const { s.add32(value); } @@ -178,17 +160,16 @@ class STUInt64 : public SerializedType protected: uint64 value; - STUInt64* duplicate() const { return new STUInt64(name, value); } - static STUInt64* construct(SerializerIterator&, const char* name = NULL); + STUInt64* duplicate() const { return new STUInt64(fName, value); } + static STUInt64* construct(SerializerIterator&, FieldName* name = NULL); public: STUInt64(uint64 v=0) : value(v) { ; } - STUInt64(const char* n, uint64 v=0) : SerializedType(n), value(v) { ; } - static std::auto_ptr deserialize(SerializerIterator& sit, const char* name) + STUInt64(FieldName* n, uint64 v=0) : SerializedType(n), value(v) { ; } + static std::auto_ptr deserialize(SerializerIterator& sit, FieldName* name) { return std::auto_ptr(construct(sit, name)); } - int getLength() const { return 8; } SerializedTypeID getSType() const { return STI_UINT64; } std::string getText() const; void add(Serializer& s) const { s.add64(value); } @@ -224,7 +205,7 @@ protected: void canonicalize(); STAmount* duplicate() const { return new STAmount(*this); } - static STAmount* construct(SerializerIterator&, const char* name = NULL); + static STAmount* construct(SerializerIterator&, FieldName* name = NULL); static const int cMinOffset = -96, cMaxOffset = 80; static const uint64 cMinValue = 1000000000000000ull, cMaxValue = 9999999999999999ull; @@ -234,10 +215,10 @@ protected: STAmount(bool isNeg, uint64 value) : mValue(value), mOffset(0), mIsNative(true), mIsNegative(isNeg) { ; } - STAmount(const char *name, uint64 value, bool isNegative) - : SerializedType(name), mValue(value), mOffset(0), mIsNative(true), mIsNegative(isNegative) + STAmount(FieldName *name, uint64 value, bool isNegative) + : SerializedType(fName), mValue(value), mOffset(0), mIsNative(true), mIsNegative(isNegative) { ; } - STAmount(const char *n, const uint160& cur, const uint160& iss, uint64 val, int off, bool isNat, bool isNeg) + STAmount(FieldName *n, const uint160& cur, const uint160& iss, uint64 val, int off, bool isNat, bool isNeg) : SerializedType(n), mCurrency(cur), mIssuer(iss), mValue(val), mOffset(off), mIsNative(isNat), mIsNegative(isNeg) { ; } @@ -250,7 +231,7 @@ public: STAmount(uint64 v = 0, bool isNeg = false) : mValue(v), mOffset(0), mIsNative(true), mIsNegative(isNeg) { if (v==0) mIsNegative = false; } - STAmount(const char* n, uint64 v = 0) + STAmount(FieldName* n, uint64 v = 0) : SerializedType(n), mValue(v), mOffset(0), mIsNative(true), mIsNegative(false) { ; } @@ -259,14 +240,14 @@ public: { canonicalize(); } // YYY This should probably require issuer too. - STAmount(const char* n, const uint160& currency, const uint160& issuer, + STAmount(FieldName* n, const uint160& currency, const uint160& issuer, uint64 v = 0, int off = 0, bool isNeg = false) : SerializedType(n), mCurrency(currency), mIssuer(issuer), mValue(v), mOffset(off), mIsNegative(isNeg) { canonicalize(); } - STAmount(const char* n, int64 v); + STAmount(FieldName* n, int64 v); - static std::auto_ptr deserialize(SerializerIterator& sit, const char* name) + static std::auto_ptr deserialize(SerializerIterator& sit, FieldName* name) { return std::auto_ptr(construct(sit, name)); } static STAmount saFromRate(uint64 uRate = 0) @@ -279,7 +260,6 @@ public: return STAmount(uCurrencyID, uIssuerID, iV < 0 ? -iV : iV, iOff, iV < 0); } - int getLength() const { return mIsNative ? 8 : 28; } SerializedTypeID getSType() const { return STI_AMOUNT; } std::string getText() const; std::string getRaw() const; @@ -377,7 +357,7 @@ public: // Native currency conversions, to/from display format static uint64 convertToDisplayAmount(const STAmount& internalAmount, uint64 totalNow, uint64 totalInit); static STAmount convertToInternalAmount(uint64 displayAmount, uint64 totalNow, uint64 totalInit, - const char* name = NULL); + FieldName* name = NULL); static std::string createHumanCurrency(const uint160& uCurrency); static STAmount deserialize(SerializerIterator&); @@ -394,19 +374,18 @@ class STHash128 : public SerializedType protected: uint128 value; - STHash128* duplicate() const { return new STHash128(name, value); } - static STHash128* construct(SerializerIterator&, const char* name = NULL); + STHash128* duplicate() const { return new STHash128(fName, value); } + static STHash128* construct(SerializerIterator&, FieldName* name = NULL); public: STHash128(const uint128& v) : value(v) { ; } - STHash128(const char* n, const uint128& v) : SerializedType(n), value(v) { ; } - STHash128(const char* n) : SerializedType(n) { ; } + STHash128(FieldName* n, const uint128& v) : SerializedType(n), value(v) { ; } + STHash128(FieldName* n) : SerializedType(n) { ; } STHash128() { ; } - static std::auto_ptr deserialize(SerializerIterator& sit, const char* name) + static std::auto_ptr deserialize(SerializerIterator& sit, FieldName* name) { return std::auto_ptr(construct(sit, name)); } - int getLength() const { return 20; } SerializedTypeID getSType() const { return STI_HASH128; } virtual std::string getText() const; void add(Serializer& s) const { s.add128(value); } @@ -423,19 +402,18 @@ class STHash160 : public SerializedType protected: uint160 value; - STHash160* duplicate() const { return new STHash160(name, value); } - static STHash160* construct(SerializerIterator&, const char* name = NULL); + STHash160* duplicate() const { return new STHash160(fName, value); } + static STHash160* construct(SerializerIterator&, FieldName* name = NULL); public: STHash160(const uint160& v) : value(v) { ; } - STHash160(const char* n, const uint160& v) : SerializedType(n), value(v) { ; } - STHash160(const char* n) : SerializedType(n) { ; } + STHash160(FieldName* n, const uint160& v) : SerializedType(n), value(v) { ; } + STHash160(FieldName* n) : SerializedType(n) { ; } STHash160() { ; } - static std::auto_ptr deserialize(SerializerIterator& sit, const char* name) + static std::auto_ptr deserialize(SerializerIterator& sit, FieldName* name) { return std::auto_ptr(construct(sit, name)); } - int getLength() const { return 20; } SerializedTypeID getSType() const { return STI_HASH160; } virtual std::string getText() const; void add(Serializer& s) const { s.add160(value); } @@ -452,19 +430,18 @@ class STHash256 : public SerializedType protected: uint256 value; - STHash256* duplicate() const { return new STHash256(name, value); } - static STHash256* construct(SerializerIterator&, const char* name = NULL); + STHash256* duplicate() const { return new STHash256(fName, value); } + static STHash256* construct(SerializerIterator&, FieldName* name = NULL); public: STHash256(const uint256& v) : value(v) { ; } - STHash256(const char* n, const uint256& v) : SerializedType(n), value(v) { ; } - STHash256(const char* n) : SerializedType(n) { ; } + STHash256(FieldName* n, const uint256& v) : SerializedType(n), value(v) { ; } + STHash256(FieldName* n) : SerializedType(n) { ; } STHash256() { ; } - static std::auto_ptr deserialize(SerializerIterator& sit, const char* name) + static std::auto_ptr deserialize(SerializerIterator& sit, FieldName* name) { return std::auto_ptr(construct(sit, name)); } - int getLength() const { return 32; } SerializedTypeID getSType() const { return STI_HASH256; } std::string getText() const; void add(Serializer& s) const { s.add256(value); } @@ -481,20 +458,19 @@ class STVariableLength : public SerializedType protected: std::vector value; - virtual STVariableLength* duplicate() const { return new STVariableLength(name, value); } - static STVariableLength* construct(SerializerIterator&, const char* name = NULL); + virtual STVariableLength* duplicate() const { return new STVariableLength(fName, value); } + static STVariableLength* construct(SerializerIterator&, FieldName* name = NULL); public: STVariableLength(const std::vector& v) : value(v) { ; } - STVariableLength(const char* n, const std::vector& v) : SerializedType(n), value(v) { ; } - STVariableLength(const char* n) : SerializedType(n) { ; } - STVariableLength(SerializerIterator&, const char* name = NULL); + STVariableLength(FieldName* n, const std::vector& v) : SerializedType(n), value(v) { ; } + STVariableLength(FieldName* n) : SerializedType(n) { ; } + STVariableLength(SerializerIterator&, FieldName* name = NULL); STVariableLength() { ; } - static std::auto_ptr deserialize(SerializerIterator& sit, const char* name) + static std::auto_ptr deserialize(SerializerIterator& sit, FieldName* name) { return std::auto_ptr(construct(sit, name)); } - int getLength() const; virtual SerializedTypeID getSType() const { return STI_VL; } virtual std::string getText() const; void add(Serializer& s) const { s.addVL(value); } @@ -511,16 +487,16 @@ public: class STAccount : public STVariableLength { protected: - virtual STAccount* duplicate() const { return new STAccount(name, value); } - static STAccount* construct(SerializerIterator&, const char* name = NULL); + virtual STAccount* duplicate() const { return new STAccount(fName, value); } + static STAccount* construct(SerializerIterator&, FieldName* name = NULL); public: STAccount(const std::vector& v) : STVariableLength(v) { ; } - STAccount(const char* n, const std::vector& v) : STVariableLength(n, v) { ; } - STAccount(const char* n) : STVariableLength(n) { ; } + STAccount(FieldName* n, const std::vector& v) : STVariableLength(n, v) { ; } + STAccount(FieldName* n) : STVariableLength(n) { ; } STAccount() { ; } - static std::auto_ptr deserialize(SerializerIterator& sit, const char* name) + static std::auto_ptr deserialize(SerializerIterator& sit, FieldName* name) { return std::auto_ptr(construct(sit, name)); } SerializedTypeID getSType() const { return STI_ACCOUNT; } @@ -649,19 +625,18 @@ class STPathSet : public SerializedType protected: std::vector value; - STPathSet* duplicate() const { return new STPathSet(name, value); } - static STPathSet* construct(SerializerIterator&, const char* name = NULL); + STPathSet* duplicate() const { return new STPathSet(fName, value); } + static STPathSet* construct(SerializerIterator&, FieldName* name = NULL); public: STPathSet() { ; } - STPathSet(const char* n) : SerializedType(n) { ; } + STPathSet(FieldName* n) : SerializedType(n) { ; } STPathSet(const std::vector& v) : value(v) { ; } - STPathSet(const char* n, const std::vector& v) : SerializedType(n), value(v) { ; } - static std::auto_ptr deserialize(SerializerIterator& sit, const char* name) + STPathSet(FieldName* n, const std::vector& v) : SerializedType(n), value(v) { ; } + static std::auto_ptr deserialize(SerializerIterator& sit, FieldName* name) { return std::auto_ptr(construct(sit, name)); } - int getLength() const; // std::string getText() const; void add(Serializer& s) const; virtual Json::Value getJson(int) const; @@ -722,20 +697,19 @@ class STVector256 : public SerializedType protected: std::vector mValue; - STVector256* duplicate() const { return new STVector256(name, mValue); } - static STVector256* construct(SerializerIterator&, const char* name = NULL); + STVector256* duplicate() const { return new STVector256(fName, mValue); } + static STVector256* construct(SerializerIterator&, FieldName* name = NULL); public: STVector256() { ; } - STVector256(const char* n) : SerializedType(n) { ; } - STVector256(const char* n, const std::vector& v) : SerializedType(n), mValue(v) { ; } + STVector256(FieldName* n) : SerializedType(n) { ; } + STVector256(FieldName* n, const std::vector& v) : SerializedType(n), mValue(v) { ; } STVector256(const std::vector& vector) : mValue(vector) { ; } SerializedTypeID getSType() const { return STI_VECTOR256; } - int getLength() const { return Serializer::lengthVL(mValue.size() * (256 / 8)); } void add(Serializer& s) const; - static std::auto_ptr deserialize(SerializerIterator& sit, const char* name) + static std::auto_ptr deserialize(SerializerIterator& sit, FieldName* name) { return std::auto_ptr(construct(sit, name)); } const std::vector& peekValue() const { return mValue; } diff --git a/src/TransactionFormats.cpp b/src/TransactionFormats.cpp index 3ab00f7dea..a23d82320c 100644 --- a/src/TransactionFormats.cpp +++ b/src/TransactionFormats.cpp @@ -1,134 +1,132 @@ -#include "TransactionFormats.h" +#include "TransactionFormats.h" -#define S_FIELD(x) sf##x, #x - -TransactionFormat InnerTxnFormats[]= +TransactionFormat InnerTxnFormats[]= { - { "AccountSet", ttACCOUNT_SET, { - { S_FIELD(Flags), STI_UINT32, SOE_FLAGS, 0 }, - { S_FIELD(SourceTag), STI_UINT32, SOE_IFFLAG, 1 }, - { S_FIELD(EmailHash), STI_HASH128, SOE_IFFLAG, 2 }, - { S_FIELD(WalletLocator), STI_HASH256, SOE_IFFLAG, 4 }, - { S_FIELD(MessageKey), STI_VL, SOE_IFFLAG, 8 }, - { S_FIELD(Domain), STI_VL, SOE_IFFLAG, 16 }, - { S_FIELD(TransferRate), STI_UINT32, SOE_IFFLAG, 32 }, - { S_FIELD(PublishHash), STI_HASH256, SOE_IFFLAG, 64 }, - { S_FIELD(PublishSize), STI_UINT32, SOE_IFFLAG, 128 }, - { sfInvalid, NULL, STI_DONE, SOE_NEVER, -1 } } - }, - { "Claim", ttCLAIM, { - { S_FIELD(Flags), STI_UINT32, SOE_FLAGS, 0 }, - { S_FIELD(Generator), STI_VL, SOE_REQUIRED, 0 }, - { S_FIELD(PublicKey), STI_VL, SOE_REQUIRED, 0 }, - { S_FIELD(Signature), STI_VL, SOE_REQUIRED, 0 }, - { S_FIELD(SourceTag), STI_UINT32, SOE_IFFLAG, 1 }, - { sfInvalid, NULL, STI_DONE, SOE_NEVER, -1 } } - }, - { "CreditSet", ttCREDIT_SET, { - { S_FIELD(Flags), STI_UINT32, SOE_FLAGS, 0 }, - { S_FIELD(Destination), STI_ACCOUNT, SOE_REQUIRED, 0 }, - { S_FIELD(SourceTag), STI_UINT32, SOE_IFFLAG, 1 }, - { S_FIELD(LimitAmount), STI_AMOUNT, SOE_IFFLAG, 2 }, - { S_FIELD(QualityIn), STI_UINT32, SOE_IFFLAG, 4 }, - { S_FIELD(QualityOut), STI_UINT32, SOE_IFFLAG, 8 }, - { sfInvalid, NULL, STI_DONE, SOE_NEVER, -1 } } - }, + { "AccountSet", ttACCOUNT_SET, { + { sfFlags, SOE_REQUIRED }, + { sfSourceTag, SOE_OPTIONAL }, + { sfEmailHash, SOE_OPTIONAL }, + { sfWalletLocator, SOE_OPTIONAL }, + { sfMessageKey, SOE_OPTIONAL }, + { sfDomain, SOE_OPTIONAL }, + { sfTransferRate, SOE_OPTIONAL }, + { sfPublishHash, SOE_OPTIONAL }, + { sfPublishSize, SOE_OPTIONAL }, + { sfInvalid, SOE_END } } + }, + { "Claim", ttCLAIM, { + { sfFlags, SOE_REQUIRED }, + { sfGenerator, SOE_REQUIRED }, + { sfPublicKey, SOE_REQUIRED }, + { sfSignature, SOE_REQUIRED }, + { sfSourceTag, SOE_OPTIONAL }, + { sfInvalid, SOE_END } } + }, + { "CreditSet", ttCREDIT_SET, { + { sfFlags, SOE_REQUIRED }, + { sfDestination, SOE_REQUIRED }, + { sfSourceTag, SOE_OPTIONAL }, + { sfLimitAmount, SOE_OPTIONAL }, + { sfQualityIn, SOE_OPTIONAL }, + { sfQualityOut, SOE_OPTIONAL }, + { sfInvalid, SOE_END } } + }, /* - { "Invoice", ttINVOICE, { - { S_FIELD(Flags), STI_UINT32, SOE_FLAGS, 0 }, - { S_FIELD(Target), STI_ACCOUNT, SOE_REQUIRED, 0 }, - { S_FIELD(Amount), STI_AMOUNT, SOE_REQUIRED, 0 }, - { S_FIELD(SourceTag), STI_UINT32, SOE_IFFLAG, 1 }, - { S_FIELD(Destination), STI_ACCOUNT, SOE_IFFLAG, 2 }, - { S_FIELD(Identifier), STI_VL, SOE_IFFLAG, 4 }, - { sfInvalid, NULL, STI_DONE, SOE_NEVER, -1 } } - }, + { "Invoice", ttINVOICE, { + { sfFlags, SOE_REQUIRED }, + { sfTarget, SOE_REQUIRED }, + { sfAmount, SOE_REQUIRED }, + { sfSourceTag, SOE_OPTIONAL }, + { sfDestination, SOE_OPTIONAL }, + { sfIdentifier, SOE_OPTIONAL }, + { sfInvalid, SOE_END } } + }, */ - { "NicknameSet", ttNICKNAME_SET, { - { S_FIELD(Flags), STI_UINT32, SOE_FLAGS, 0 }, - { S_FIELD(Nickname), STI_HASH256, SOE_REQUIRED, 0 }, - { S_FIELD(MinimumOffer), STI_AMOUNT, SOE_IFFLAG, 1 }, - { S_FIELD(Signature), STI_VL, SOE_IFFLAG, 2 }, - { S_FIELD(SourceTag), STI_UINT32, SOE_IFFLAG, 4 }, - { sfInvalid, NULL, STI_DONE, SOE_NEVER, -1 } } - }, - { "OfferCreate", ttOFFER_CREATE, { - { S_FIELD(Flags), STI_UINT32, SOE_FLAGS, 0 }, - { S_FIELD(TakerPays), STI_AMOUNT, SOE_REQUIRED, 0 }, - { S_FIELD(TakerGets), STI_AMOUNT, SOE_REQUIRED, 0 }, - { S_FIELD(SourceTag), STI_UINT32, SOE_IFFLAG, 1 }, - { S_FIELD(Expiration), STI_UINT32, SOE_IFFLAG, 2 }, - { sfInvalid, NULL, STI_DONE, SOE_NEVER, -1 } } - }, - { "OfferCancel", ttOFFER_CANCEL, { - { S_FIELD(Flags), STI_UINT32, SOE_FLAGS, 0 }, - { S_FIELD(OfferSequence), STI_UINT32, SOE_REQUIRED, 0 }, - { S_FIELD(SourceTag), STI_UINT32, SOE_IFFLAG, 1 }, - { sfInvalid, NULL, STI_DONE, SOE_NEVER, -1 } } - }, - { "PasswordFund", ttPASSWORD_FUND, { - { S_FIELD(Flags), STI_UINT32, SOE_FLAGS, 0 }, - { S_FIELD(Destination), STI_ACCOUNT, SOE_REQUIRED, 0 }, - { S_FIELD(SourceTag), STI_UINT32, SOE_IFFLAG, 1 }, - { sfInvalid, NULL, STI_DONE, SOE_NEVER, -1 } } - }, - { "PasswordSet", ttPASSWORD_SET, { - { S_FIELD(Flags), STI_UINT32, SOE_FLAGS, 0 }, - { S_FIELD(AuthorizedKey), STI_ACCOUNT, SOE_REQUIRED, 0 }, - { S_FIELD(Generator), STI_VL, SOE_REQUIRED, 0 }, - { S_FIELD(PublicKey), STI_VL, SOE_REQUIRED, 0 }, - { S_FIELD(Signature), STI_VL, SOE_REQUIRED, 0 }, - { S_FIELD(SourceTag), STI_UINT32, SOE_IFFLAG, 1 }, - { sfInvalid, NULL, STI_DONE, SOE_NEVER, -1 } } - }, - { "Payment", ttPAYMENT, { - { S_FIELD(Flags), STI_UINT32, SOE_FLAGS, 0 }, - { S_FIELD(Destination), STI_ACCOUNT, SOE_REQUIRED, 0 }, - { S_FIELD(Amount), STI_AMOUNT, SOE_REQUIRED, 0 }, - { S_FIELD(SendMax), STI_AMOUNT, SOE_IFFLAG, 1 }, - { S_FIELD(Paths), STI_PATHSET, SOE_IFFLAG, 2 }, - { S_FIELD(SourceTag), STI_UINT32, SOE_IFFLAG, 4 }, - { S_FIELD(InvoiceID), STI_HASH256, SOE_IFFLAG, 8 }, - { sfInvalid, NULL, STI_DONE, SOE_NEVER, -1 } } - }, - { "WalletAdd", ttWALLET_ADD, { - { S_FIELD(Flags), STI_UINT32, SOE_FLAGS, 0 }, - { S_FIELD(Amount), STI_AMOUNT, SOE_REQUIRED, 0 }, - { S_FIELD(AuthorizedKey), STI_ACCOUNT, SOE_REQUIRED, 0 }, - { S_FIELD(PublicKey), STI_VL, SOE_REQUIRED, 0 }, - { S_FIELD(Signature), STI_VL, SOE_REQUIRED, 0 }, - { S_FIELD(SourceTag), STI_UINT32, SOE_IFFLAG, 1 }, - { sfInvalid, NULL, STI_DONE, SOE_NEVER, -1 } } - }, - { "Contract", ttCONTRACT, { - { S_FIELD(Flags), STI_UINT32, SOE_FLAGS, 0 }, - { S_FIELD(Expiration), STI_UINT32, SOE_REQUIRED, 0 }, - { S_FIELD(BondAmount), STI_UINT32, SOE_REQUIRED, 0 }, - { S_FIELD(StampEscrow), STI_UINT32, SOE_REQUIRED, 0 }, - { S_FIELD(RippleEscrow), STI_AMOUNT, SOE_REQUIRED, 0 }, - { S_FIELD(CreateCode), STI_VL, SOE_REQUIRED, 0 }, - { S_FIELD(FundCode), STI_VL, SOE_REQUIRED, 0 }, - { S_FIELD(RemoveCode), STI_VL, SOE_REQUIRED, 0 }, - { S_FIELD(ExpireCode), STI_VL, SOE_REQUIRED, 0 }, - { sfInvalid, NULL, STI_DONE, SOE_NEVER, -1 } } - }, - { "Contract", ttCONTRACT_REMOVE, { - { S_FIELD(Flags), STI_UINT32, SOE_FLAGS, 0 }, - { S_FIELD(Target), STI_ACCOUNT, SOE_REQUIRED, 0 }, - { sfInvalid, NULL, STI_DONE, SOE_NEVER, -1 } } - }, + { "NicknameSet", ttNICKNAME_SET, { + { sfFlags, SOE_REQUIRED }, + { sfNickname, SOE_REQUIRED }, + { sfMinimumOffer, SOE_OPTIONAL }, + { sfSignature, SOE_OPTIONAL }, + { sfSourceTag, SOE_OPTIONAL }, + { sfInvalid, SOE_END } } + }, + { "OfferCreate", ttOFFER_CREATE, { + { sfFlags, SOE_REQUIRED}, + { sfTakerPays, SOE_REQUIRED }, + { sfTakerGets, SOE_REQUIRED }, + { sfSourceTag, SOE_OPTIONAL }, + { sfExpiration, SOE_OPTIONAL }, + { sfInvalid, SOE_END } } + }, + { "OfferCancel", ttOFFER_CANCEL, { + { sfFlags, SOE_REQUIRED }, + { sfOfferSequence, SOE_REQUIRED }, + { sfSourceTag, SOE_OPTIONAL }, + { sfInvalid, SOE_END } } + }, + { "PasswordFund", ttPASSWORD_FUND, { + { sfFlags, SOE_REQUIRED }, + { sfDestination, SOE_REQUIRED }, + { sfSourceTag, SOE_OPTIONAL }, + { sfInvalid, SOE_END } } + }, + { "PasswordSet", ttPASSWORD_SET, { + { sfFlags, SOE_REQUIRED }, + { sfAuthorizedKey, SOE_REQUIRED }, + { sfGenerator, SOE_REQUIRED }, + { sfPublicKey, SOE_REQUIRED }, + { sfSignature, SOE_REQUIRED }, + { sfSourceTag, SOE_OPTIONAL }, + { sfInvalid, SOE_END } } + }, + { "Payment", ttPAYMENT, { + { sfFlags, SOE_REQUIRED }, + { sfDestination, SOE_REQUIRED }, + { sfAmount, SOE_REQUIRED }, + { sfSendMax, SOE_OPTIONAL }, + { sfPaths, SOE_OPTIONAL }, + { sfSourceTag, SOE_OPTIONAL }, + { sfInvoiceID, SOE_OPTIONAL }, + { sfInvalid, SOE_END } } + }, + { "WalletAdd", ttWALLET_ADD, { + { sfFlags, SOE_REQUIRED }, + { sfAmount, SOE_REQUIRED }, + { sfAuthorizedKey, SOE_REQUIRED }, + { sfPublicKey, SOE_REQUIRED }, + { sfSignature, SOE_REQUIRED }, + { sfSourceTag, SOE_OPTIONAL }, + { sfInvalid, SOE_END } } + }, + { "Contract", ttCONTRACT, { + { sfFlags, SOE_REQUIRED }, + { sfExpiration, SOE_REQUIRED }, + { sfBondAmount, SOE_REQUIRED }, + { sfStampEscrow, SOE_REQUIRED }, + { sfRippleEscrow, SOE_REQUIRED }, + { sfCreateCode, SOE_OPTIONAL }, + { sfFundCode, SOE_OPTIONAL }, + { sfRemoveCode, SOE_OPTIONAL }, + { sfExpireCode, SOE_OPTIONAL }, + { sfInvalid, SOE_END } } + }, + { "RemoveContract", ttCONTRACT_REMOVE, { + { sfFlags, SOE_REQUIRED }, + { sfTarget, SOE_REQUIRED }, + { sfInvalid, SOE_END } } + }, { NULL, ttINVALID } }; -TransactionFormat* getTxnFormat(TransactionType t) +TransactionFormat* getTxnFormat(TransactionType t) { - TransactionFormat* f = InnerTxnFormats; - while (f->t_name != NULL) + TransactionFormat* f = InnerTxnFormats; + while (f->t_name != NULL) { - if (f->t_type == t) return f; + if (f->t_type == t) return f; ++f; - } - return NULL; + } + return NULL; } -// vim:ts=4 +// vim:ts=4 diff --git a/src/TransactionFormats.h b/src/TransactionFormats.h index 72ff3f6e3f..0efaf03397 100644 --- a/src/TransactionFormats.h +++ b/src/TransactionFormats.h @@ -23,9 +23,9 @@ enum TransactionType struct TransactionFormat { - const char *t_name; - TransactionType t_type; - SOElement elements[16]; + const char * t_name; + TransactionType t_type; + SOElement elements[24]; }; const int TransactionISigningPubKey = 0; From 2446db0bbe362c2e1f1575fbb024b5e858d66635 Mon Sep 17 00:00:00 2001 From: JoelKatz Date: Tue, 25 Sep 2012 19:27:09 -0700 Subject: [PATCH 02/53] More serialization work. --- src/Amount.cpp | 7 +- src/FieldNames.cpp | 50 ++++--------- src/FieldNames.h | 57 +++++++++----- src/LedgerEntrySet.h | 3 +- src/SerializedLedger.h | 66 ++++++++--------- src/SerializedObject.cpp | 16 ++-- src/SerializedObject.h | 100 +++++++++++++------------ src/SerializedTransaction.h | 64 ++++++++-------- src/SerializedTypes.cpp | 24 +++--- src/SerializedTypes.h | 143 ++++++++++++++++++------------------ src/TransactionMeta.cpp | 2 +- 11 files changed, 266 insertions(+), 266 deletions(-) diff --git a/src/Amount.cpp b/src/Amount.cpp index 56b0104a3b..c9e3e4475c 100644 --- a/src/Amount.cpp +++ b/src/Amount.cpp @@ -298,7 +298,7 @@ void STAmount::add(Serializer& s) const } } -STAmount::STAmount(FieldName* name, int64 value) : SerializedType(name), mOffset(0), mIsNative(true) +STAmount::STAmount(SField::ref name, int64 value) : SerializedType(name), mOffset(0), mIsNative(true) { if (value >= 0) { @@ -330,7 +330,7 @@ uint64 STAmount::toUInt64() const return mValue | (static_cast(mOffset + 256 + 97) << (64 - 10)); } -STAmount* STAmount::construct(SerializerIterator& sit, FieldName* name) +STAmount* STAmount::construct(SerializerIterator& sit, SField::ref name) { uint64 value = sit.get64(); @@ -882,8 +882,7 @@ uint64 STAmount::convertToDisplayAmount(const STAmount& internalAmount, uint64 t return muldiv(internalAmount.getNValue(), totalInit, totalNow); } -STAmount STAmount::convertToInternalAmount(uint64 displayAmount, uint64 totalNow, uint64 totalInit, - FieldName* name) +STAmount STAmount::convertToInternalAmount(uint64 displayAmount, uint64 totalNow, uint64 totalInit, SField::ref name) { // Convert a display/request currency amount to an internal amount return STAmount(name, muldiv(displayAmount, totalNow, totalInit)); } diff --git a/src/FieldNames.cpp b/src/FieldNames.cpp index 72589d0004..c8388ad02d 100644 --- a/src/FieldNames.cpp +++ b/src/FieldNames.cpp @@ -5,49 +5,27 @@ #include -#define FIELD(name, type, index) { sf##name, #name, STI_##type, index }, + +SField sfInvalid(-1), sfGeneric(0); + +#define FIELD(name, type, index) SField sf##name(FIELD_CODE(STI_##type, index), STI_##type, index, naem); #define TYPE(name, type, index) - -FieldName FieldNames[]= -{ #include "SerializeProto.h" - - { sfInvalid, 0, STI_DONE, 0 } -}; - #undef FIELD #undef TYPE -static std::map unknownFieldMap; -static boost::mutex unknownFieldMutex; +static std::map SField::codeToField; +static boost::mutex SField::mapMutex; -FieldName* getFieldName(SOE_Field f) -{ // OPTIMIZEME - for (FieldName* n = FieldNames; n->fieldName != 0; ++n) - if (n->field == f) - return n; - return NULL; -} - -FieldName* getFieldName(int type, int field) -{ // OPTIMIZEME - int f = (type << 16) | field; - for (FieldName* n = FieldNames; n->fieldName != 0; ++n) - if (n->field == f) - return n; +SField::ref SField::getField(int code); +{ if ((type <= 0) || (type >= 256) || (field <= 0) || (field >= 256 - return NULL; + return sfInvalid; + boost::mutex::scoped_lock sl(mapMutex); - boost::mutex::scoped_lock sl(unknownFieldMutex); - std::map it = unknownFieldMap.Find(f); - if (it != unknownFieldMap.end()) - return it->second; + std::map it = unknownFieldMap.Find(code); + if (it != codeToField.end()) + return *(it->second); - FieldName* n = new FieldName(); - n->field = f; - n->fieldName = "unknown"; - n->fieldType = static_cast(type); - n->fieldNum = field; - unknownFieldMap[f] = n; - return n; + return *(new SField(code, static_cast(code>>16), code&0xffff, NULL)); } diff --git a/src/FieldNames.h b/src/FieldNames.h index b056b237fb..db29e0ebdf 100644 --- a/src/FieldNames.h +++ b/src/FieldNames.h @@ -1,9 +1,14 @@ #ifndef __FIELDNAMES__ #define __FIELDNAMES__ +#include + +#define FIELD_CODE(type, index) ((static_cast(type) << 16) | index) + enum SerializedTypeID { // special types + STI_UNKNOWN = -2, STI_DONE = -1, STI_NOTPRESENT = 0, @@ -26,31 +31,43 @@ enum SOE_Flags SOE_OPTIONAL = 1, // optional }; -enum SOE_Field +class SField { - sfInvalid = -1, - sfGeneric = 0, +public: + typedef const SField& ref; + typedef SField const * ptr; -#define FIELD(name, type, index) sf##name = (STI_##type << 16) | index, +protected: + static std::map codeToField; + static boost::mutex mapMutex; + +public: + + const int fieldCode; // (type<<16)|index + const SerializedTypeID fieldType; // STI_* + const int fieldValue; // Code number for protocol + const char* fieldName; + + SField(int fc, SerializedTypeID tid, int fv, const char* fn) : + fieldCode(fc), fieldType(tid), fieldValue(fv), fieldName(fn) + { codeToField[fc] = this; } + + SField(int fc) : fieldCode(fc), fieldType(STI_UNKNOWN), fieldValue(0), fieldName(NULL) { ; } + + static SField::ref getField(int fieldCode); + static SField::ref getField(SerializedTypeID type, int value) { return getField(FIELD_CODE(type, value)); } + + bool isGeneric() const { return fieldCode == 0; } + bool isInvalid() const { return fieldCode == -1; } + bool isKnown() const { return fieldType != STI_UNKNOWN; } +}; + +extern SField sfInvalid, sfGeneric; + +#define FIELD(name, type, index) extern SField sf##name; #define TYPE(name, type, index) #include "SerializeProto.h" #undef FIELD #undef TYPE - // test fields - sfTest1=100000, sfTest2, sfTest3, sfTest4 -}; - -struct FieldName -{ - SOE_Field field; - const char *fieldName; - SerializedTypeID fieldType; - int fieldNum; -}; - -extern FieldName FieldNames[]; -extern FieldName* getFieldName(SOE_Field); -extern FieldName* getFieldName(int type, int field); - #endif diff --git a/src/LedgerEntrySet.h b/src/LedgerEntrySet.h index 150a5ae891..8a7c926c4e 100644 --- a/src/LedgerEntrySet.h +++ b/src/LedgerEntrySet.h @@ -104,7 +104,8 @@ public: uint32 rippleTransferRate(const uint160& uIssuerID); STAmount rippleOwed(const uint160& uToAccountID, const uint160& uFromAccountID, const uint160& uCurrencyID); STAmount rippleLimit(const uint160& uToAccountID, const uint160& uFromAccountID, const uint160& uCurrencyID); - uint32 rippleQualityIn(const uint160& uToAccountID, const uint160& uFromAccountID, const uint160& uCurrencyID, const SOE_Field sfLow=sfLowQualityIn, const SOE_Field sfHigh=sfHighQualityIn); + uint32 rippleQualityIn(const uint160& uToAccountID, const uint160& uFromAccountID, const uint160& uCurrencyID, + SField::ref sfLow = sfLowQualityIn, SField::ref sfHigh = sfHighQualityIn); uint32 rippleQualityOut(const uint160& uToAccountID, const uint160& uFromAccountID, const uint160& uCurrencyID) { return rippleQualityIn(uToAccountID, uFromAccountID, uCurrencyID, sfLowQualityOut, sfHighQualityOut); } diff --git a/src/SerializedLedger.h b/src/SerializedLedger.h index e60662d2db..813e4dccb9 100644 --- a/src/SerializedLedger.h +++ b/src/SerializedLedger.h @@ -43,25 +43,25 @@ public: uint16 getVersion() const { return mVersion.getValue(); } const LedgerEntryFormat* getFormat() { return mFormat; } - int getIFieldIndex(SOE_Field field) const { return mObject.getFieldIndex(field); } + int getIFieldIndex(SField::ref field) const { return mObject.getFieldIndex(field); } int getIFieldCount() const { return mObject.getCount(); } - const SerializedType& peekIField(SOE_Field field) const { return mObject.peekAtField(field); } - SerializedType& getIField(SOE_Field field) { return mObject.getField(field); } - SOE_Field getIFieldSType(int index) { return mObject.getFieldSType(index); } + const SerializedType& peekIField(SField::ref field) const { return mObject.peekAtField(field); } + SerializedType& getIField(SField::ref field) { return mObject.getField(field); } + SField::ref getIFieldSType(int index) { return mObject.getFieldSType(index); } - std::string getIFieldString(SOE_Field field) const { return mObject.getFieldString(field); } - unsigned char getIFieldU8(SOE_Field field) const { return mObject.getValueFieldU8(field); } - uint16 getIFieldU16(SOE_Field field) const { return mObject.getValueFieldU16(field); } - uint32 getIFieldU32(SOE_Field field) const { return mObject.getValueFieldU32(field); } - uint64 getIFieldU64(SOE_Field field) const { return mObject.getValueFieldU64(field); } - uint128 getIFieldH128(SOE_Field field) const { return mObject.getValueFieldH128(field); } - uint160 getIFieldH160(SOE_Field field) const { return mObject.getValueFieldH160(field); } - uint256 getIFieldH256(SOE_Field field) const { return mObject.getValueFieldH256(field); } - std::vector getIFieldVL(SOE_Field field) const { return mObject.getValueFieldVL(field); } - std::vector getIFieldTL(SOE_Field field) const { return mObject.getValueFieldTL(field); } - NewcoinAddress getIValueFieldAccount(SOE_Field field) const { return mObject.getValueFieldAccount(field); } - STAmount getIValueFieldAmount(SOE_Field field) const { return mObject.getValueFieldAmount(field); } - STVector256 getIFieldV256(SOE_Field field) { return mObject.getValueFieldV256(field); } + std::string getIFieldString(SField::ref field) const { return mObject.getFieldString(field); } + unsigned char getIFieldU8(SField::ref field) const { return mObject.getValueFieldU8(field); } + uint16 getIFieldU16(SField::ref field) const { return mObject.getValueFieldU16(field); } + uint32 getIFieldU32(SField::ref field) const { return mObject.getValueFieldU32(field); } + uint64 getIFieldU64(SField::ref field) const { return mObject.getValueFieldU64(field); } + uint128 getIFieldH128(SField::ref field) const { return mObject.getValueFieldH128(field); } + uint160 getIFieldH160(SField::ref field) const { return mObject.getValueFieldH160(field); } + uint256 getIFieldH256(SField::ref field) const { return mObject.getValueFieldH256(field); } + std::vector getIFieldVL(SField::ref field) const { return mObject.getValueFieldVL(field); } + std::vector getIFieldTL(SField::ref field) const { return mObject.getValueFieldTL(field); } + NewcoinAddress getIValueFieldAccount(SField::ref field) const { return mObject.getValueFieldAccount(field); } + STAmount getIValueFieldAmount(SField::ref field) const { return mObject.getValueFieldAmount(field); } + STVector256 getIFieldV256(SField::ref field) { return mObject.getValueFieldV256(field); } bool isThreadedType(); // is this a ledger entry that can be threaded bool isThreaded(); // is this ledger entry actually threaded @@ -75,28 +75,28 @@ public: bool thread(const uint256& txID, uint32 ledgerSeq, uint256& prevTxID, uint32& prevLedgerID); std::vector getOwners(); // nodes notified if this node is deleted - void setIFieldU8(SOE_Field field, unsigned char v) { return mObject.setValueFieldU8(field, v); } - void setIFieldU16(SOE_Field field, uint16 v) { return mObject.setValueFieldU16(field, v); } - void setIFieldU32(SOE_Field field, uint32 v) { return mObject.setValueFieldU32(field, v); } - void setIFieldU64(SOE_Field field, uint64 v) { return mObject.setValueFieldU64(field, v); } - void setIFieldH128(SOE_Field field, const uint128& v) { return mObject.setValueFieldH128(field, v); } - void setIFieldH160(SOE_Field field, const uint160& v) { return mObject.setValueFieldH160(field, v); } - void setIFieldH256(SOE_Field field, const uint256& v) { return mObject.setValueFieldH256(field, v); } - void setIFieldVL(SOE_Field field, const std::vector& v) + void setIFieldU8(SField::ref field, unsigned char v) { return mObject.setValueFieldU8(field, v); } + void setIFieldU16(SField::ref field, uint16 v) { return mObject.setValueFieldU16(field, v); } + void setIFieldU32(SField::ref field, uint32 v) { return mObject.setValueFieldU32(field, v); } + void setIFieldU64(SField::ref field, uint64 v) { return mObject.setValueFieldU64(field, v); } + void setIFieldH128(SField::ref field, const uint128& v) { return mObject.setValueFieldH128(field, v); } + void setIFieldH160(SField::ref field, const uint160& v) { return mObject.setValueFieldH160(field, v); } + void setIFieldH256(SField::ref field, const uint256& v) { return mObject.setValueFieldH256(field, v); } + void setIFieldVL(SField::ref field, const std::vector& v) { return mObject.setValueFieldVL(field, v); } - void setIFieldTL(SOE_Field field, const std::vector& v) + void setIFieldTL(SField::ref field, const std::vector& v) { return mObject.setValueFieldTL(field, v); } - void setIFieldAccount(SOE_Field field, const uint160& account) + void setIFieldAccount(SField::ref field, const uint160& account) { return mObject.setValueFieldAccount(field, account); } - void setIFieldAccount(SOE_Field field, const NewcoinAddress& account) + void setIFieldAccount(SField::ref field, const NewcoinAddress& account) { return mObject.setValueFieldAccount(field, account); } - void setIFieldAmount(SOE_Field field, const STAmount& amount) + void setIFieldAmount(SField::ref field, const STAmount& amount) { return mObject.setValueFieldAmount(field, amount); } - void setIFieldV256(SOE_Field field, const STVector256& v) { return mObject.setValueFieldV256(field, v); } + void setIFieldV256(SField::ref field, const STVector256& v) { return mObject.setValueFieldV256(field, v); } - bool getIFieldPresent(SOE_Field field) const { return mObject.isFieldPresent(field); } - void makeIFieldPresent(SOE_Field field) { mObject.makeFieldPresent(field); } - void makeIFieldAbsent(SOE_Field field) { return mObject.makeFieldAbsent(field); } + bool getIFieldPresent(SField::ref field) const { return mObject.isFieldPresent(field); } + void makeIFieldPresent(SField::ref field) { mObject.makeFieldPresent(field); } + void makeIFieldAbsent(SField::ref field) { return mObject.makeFieldAbsent(field); } }; typedef SerializedLedgerEntry SLE; diff --git a/src/SerializedObject.cpp b/src/SerializedObject.cpp index c1167a6d62..d935022cb9 100644 --- a/src/SerializedObject.cpp +++ b/src/SerializedObject.cpp @@ -8,7 +8,7 @@ #include "Log.h" -std::auto_ptr STObject::makeDefaultObject(SerializedTypeID id, FieldName* name) +std::auto_ptr STObject::makeDefaultObject(SerializedTypeID id, SField::ref name) { switch(id) { @@ -53,7 +53,7 @@ std::auto_ptr STObject::makeDefaultObject(SerializedTypeID id, F } } -std::auto_ptr STObject::makeDeserializedObject(SerializedTypeID id, FieldName* name, +std::auto_ptr STObject::makeDeserializedObject(SerializedTypeID id, SField::ref name, SerializerIterator& sit, int depth) { switch(id) @@ -114,19 +114,19 @@ void STObject::set(const SOElement* elem) { mType.push_back(elem); if (elem->flags == SOE_OPTIONAL) - giveObject(makeDefaultObject(STI_NOTPRESENT, elem->e_name)); + giveObject(makeDefaultObject(STI_NOTPRESENT, elem)); else - giveObject(makeDefaultObject(elem->e_id, elem->e_name)); + giveObject(makeDefaultObject(elem->e_field, elem)); ++elem; } } -STObject::STObject(const SOElement* elem, FieldName* name) : SerializedType(name) +STObject::STObject(const SOElement* elem, SField::ref name) : SerializedType(name) { set(elem); } -void STObject::set(FieldName* name, SerializerIterator& sit, int depth = 0) +void STObject::set(SField::ref name, SerializerIterator& sit, int depth = 0) { mData.empty(); mType.empty(); @@ -139,12 +139,12 @@ void STObject::set(FieldName* name, SerializerIterator& sit, int depth = 0) sit.getFieldID(type, field); if ((type == STI_ARRAY) && (field == 1)) return; - FieldName* fn = getFieldName(type, field); + SField::ref fn = SField::getField(type, field); giveObject(makeDeserializedObject(static_cast type, fn, sit, depth + 1); } } -STObject::STObject(const SOElement* elem, SerializerIterator& sit, FieldName*name) : SerializedType(name) +STObject::STObject(const SOElement* elem, SerializerIterator& sit, SField::refname) : SerializedType(name) { set(elem, sit); } diff --git a/src/SerializedObject.h b/src/SerializedObject.h index f4f372ac5d..491e85a599 100644 --- a/src/SerializedObject.h +++ b/src/SerializedObject.h @@ -13,7 +13,7 @@ struct SOElement { // An element in the description of a serialized object - SOE_Field e_field; + SField::ref e_field; SOE_Flags flags; }; @@ -24,13 +24,17 @@ protected: std::vector mType; STObject* duplicate() const { return new STObject(*this); } + static STObject* construct(SerializerIterator&, SField::ref); public: - STObject(FieldName *n = NULL) : SerializedType(n) { ; } - STObject(const SOElement *t, FieldName *n = NULL); - STObject(const SOElement *t, SerializerIterator& u, FieldName *n = NULL); + STObject(SField *n = NULL) : SerializedType(n) { ; } + STObject(const SOElement *t, SField *n = NULL); + STObject(const SOElement *t, SerializerIterator& u, SField *n = NULL); virtual ~STObject() { ; } + static std::auto_ptr deserialize(SerializerIterator& sit, SField::ref name) + { return std::auto_ptr(construct(sit, name)); } + void set(const SOElement* t); void set(const SOElement* t, SerializerIterator& u, int depth = 0); @@ -61,54 +65,54 @@ public: const SerializedType* peekAtPIndex(int offset) const { return &(mData[offset]); } SerializedType* getPIndex(int offset) { return &(mData[offset]); } - int getFieldIndex(SOE_Field field) const; - SOE_Field getFieldSType(int index) const; + int getFieldIndex(SField::ref field) const; + SField::ref getFieldSType(int index) const; - const SerializedType& peekAtField(SOE_Field field) const; - SerializedType& getField(SOE_Field field); - const SerializedType* peekAtPField(SOE_Field field) const; - SerializedType* getPField(SOE_Field field); - const SOElement* getFieldType(SOE_Field field) const; + const SerializedType& peekAtField(SField::ref field) const; + SerializedType& getField(SField::ref field); + const SerializedType* peekAtPField(SField::ref field) const; + SerializedType* getPField(SField::ref field); + const SOElement* getFieldType(SField::ref field) const; // these throw if the field type doesn't match, or return default values if the // field is optional but not present - std::string getFieldString(SOE_Field field) const; - unsigned char getValueFieldU8(SOE_Field field) const; - uint16 getValueFieldU16(SOE_Field field) const; - uint32 getValueFieldU32(SOE_Field field) const; - uint64 getValueFieldU64(SOE_Field field) const; - uint128 getValueFieldH128(SOE_Field field) const; - uint160 getValueFieldH160(SOE_Field field) const; - uint256 getValueFieldH256(SOE_Field field) const; - NewcoinAddress getValueFieldAccount(SOE_Field field) const; - std::vector getValueFieldVL(SOE_Field field) const; - std::vector getValueFieldTL(SOE_Field field) const; - STAmount getValueFieldAmount(SOE_Field field) const; - STPathSet getValueFieldPathSet(SOE_Field field) const; - STVector256 getValueFieldV256(SOE_Field field) const; + std::string getFieldString(SField::ref field) const; + unsigned char getValueFieldU8(SField::ref field) const; + uint16 getValueFieldU16(SField::ref field) const; + uint32 getValueFieldU32(SField::ref field) const; + uint64 getValueFieldU64(SField::ref field) const; + uint128 getValueFieldH128(SField::ref field) const; + uint160 getValueFieldH160(SField::ref field) const; + uint256 getValueFieldH256(SField::ref field) const; + NewcoinAddress getValueFieldAccount(SField::ref field) const; + std::vector getValueFieldVL(SField::ref field) const; + std::vector getValueFieldTL(SField::ref field) const; + STAmount getValueFieldAmount(SField::ref field) const; + STPathSet getValueFieldPathSet(SField::ref field) const; + STVector256 getValueFieldV256(SField::ref field) const; - void setValueFieldU8(SOE_Field field, unsigned char); - void setValueFieldU16(SOE_Field field, uint16); - void setValueFieldU32(SOE_Field field, uint32); - void setValueFieldU64(SOE_Field field, uint64); - void setValueFieldH128(SOE_Field field, const uint128&); - void setValueFieldH160(SOE_Field field, const uint160&); - void setValueFieldH256(SOE_Field field, const uint256&); - void setValueFieldVL(SOE_Field field, const std::vector&); - void setValueFieldTL(SOE_Field field, const std::vector&); - void setValueFieldAccount(SOE_Field field, const uint160&); - void setValueFieldAccount(SOE_Field field, const NewcoinAddress& addr) + void setValueFieldU8(SField::ref field, unsigned char); + void setValueFieldU16(SField::ref field, uint16); + void setValueFieldU32(SField::ref field, uint32); + void setValueFieldU64(SField::ref field, uint64); + void setValueFieldH128(SField::ref field, const uint128&); + void setValueFieldH160(SField::ref field, const uint160&); + void setValueFieldH256(SField::ref field, const uint256&); + void setValueFieldVL(SField::ref field, const std::vector&); + void setValueFieldTL(SField::ref field, const std::vector&); + void setValueFieldAccount(SField::ref field, const uint160&); + void setValueFieldAccount(SField::ref field, const NewcoinAddress& addr) { setValueFieldAccount(field, addr.getAccountID()); } - void setValueFieldAmount(SOE_Field field, const STAmount&); - void setValueFieldPathSet(SOE_Field field, const STPathSet&); - void setValueFieldV256(SOE_Field field, const STVector256& v); + void setValueFieldAmount(SField::ref field, const STAmount&); + void setValueFieldPathSet(SField::ref field, const STPathSet&); + void setValueFieldV256(SField::ref field, const STVector256& v); - bool isFieldPresent(SOE_Field field) const; - SerializedType* makeFieldPresent(SOE_Field field); - void makeFieldAbsent(SOE_Field field); + bool isFieldPresent(SField::ref field) const; + SerializedType* makeFieldPresent(SField::ref field); + void makeFieldAbsent(SField::ref field); - static std::auto_ptr makeDefaultObject(SerializedTypeID id, FieldName *name); - static std::auto_ptr makeDeserializedObject(SerializedTypeID id, FieldName *name, + static std::auto_ptr makeDefaultObject(SerializedTypeID id, SField *name); + static std::auto_ptr makeDeserializedObject(SerializedTypeID id, SField *name, SerializerIterator&, int depth); static void unitTest(); @@ -128,16 +132,16 @@ protected: vector value; - STArray* duplicate() const { return new STArray(fName, value); } - static STArray* construct(SerializerIterator&, FieldName* name = NULL); + STArray* duplicate() const { return new STArray(*this); } + static STArray* construct(SerializerIterator&, SField::ref); public: STArray() { ; } - STArray(FieldName* f, const vector& v) : SerializedType(f), value(v) { ; } + STArray(SField::ref f, const vector& v) : SerializedType(f), value(v) { ; } STArray(vector& v) : value(v) { ; } - static std::auto_ptr deserialize(SerializerIterator& sit, FieldName* name) + static std::auto_ptr deserialize(SerializerIterator& sit, SField::ref name) { return std::auto_ptr(construct(sit, name)); } const vector& getValue() const { return value; } diff --git a/src/SerializedTransaction.h b/src/SerializedTransaction.h index ee4ffb3ea4..d1278b8645 100644 --- a/src/SerializedTransaction.h +++ b/src/SerializedTransaction.h @@ -71,50 +71,50 @@ public: void setSequence(uint32); // inner transaction field functions - int getITFieldIndex(SOE_Field field) const; + int getITFieldIndex(SField::ref field) const; int getITFieldCount() const; - const SerializedType& peekITField(SOE_Field field) const; - SerializedType& getITField(SOE_Field field); + const SerializedType& peekITField(SField::ref field) const; + SerializedType& getITField(SField::ref field); // inner transaction field value functions - std::string getITFieldString(SOE_Field field) const { return mInnerTxn.getFieldString(field); } - unsigned char getITFieldU8(SOE_Field field) const { return mInnerTxn.getValueFieldU8(field); } - uint16 getITFieldU16(SOE_Field field) const { return mInnerTxn.getValueFieldU16(field); } - uint32 getITFieldU32(SOE_Field field) const { return mInnerTxn.getValueFieldU32(field); } - uint64 getITFieldU64(SOE_Field field) const { return mInnerTxn.getValueFieldU64(field); } - uint128 getITFieldH128(SOE_Field field) const { return mInnerTxn.getValueFieldH128(field); } - uint160 getITFieldH160(SOE_Field field) const { return mInnerTxn.getValueFieldH160(field); } - uint160 getITFieldAccount(SOE_Field field) const; - uint256 getITFieldH256(SOE_Field field) const { return mInnerTxn.getValueFieldH256(field); } - std::vector getITFieldVL(SOE_Field field) const { return mInnerTxn.getValueFieldVL(field); } - std::vector getITFieldTL(SOE_Field field) const { return mInnerTxn.getValueFieldTL(field); } - STAmount getITFieldAmount(SOE_Field field) const { return mInnerTxn.getValueFieldAmount(field); } - STPathSet getITFieldPathSet(SOE_Field field) const { return mInnerTxn.getValueFieldPathSet(field); } + std::string getITFieldString(SField::ref field) const { return mInnerTxn.getFieldString(field); } + unsigned char getITFieldU8(SField::ref field) const { return mInnerTxn.getValueFieldU8(field); } + uint16 getITFieldU16(SField::ref field) const { return mInnerTxn.getValueFieldU16(field); } + uint32 getITFieldU32(SField::ref field) const { return mInnerTxn.getValueFieldU32(field); } + uint64 getITFieldU64(SField::ref field) const { return mInnerTxn.getValueFieldU64(field); } + uint128 getITFieldH128(SField::ref field) const { return mInnerTxn.getValueFieldH128(field); } + uint160 getITFieldH160(SField::ref field) const { return mInnerTxn.getValueFieldH160(field); } + uint160 getITFieldAccount(SField::ref field) const; + uint256 getITFieldH256(SField::ref field) const { return mInnerTxn.getValueFieldH256(field); } + std::vector getITFieldVL(SField::ref field) const { return mInnerTxn.getValueFieldVL(field); } + std::vector getITFieldTL(SField::ref field) const { return mInnerTxn.getValueFieldTL(field); } + STAmount getITFieldAmount(SField::ref field) const { return mInnerTxn.getValueFieldAmount(field); } + STPathSet getITFieldPathSet(SField::ref field) const { return mInnerTxn.getValueFieldPathSet(field); } - void setITFieldU8(SOE_Field field, unsigned char v) { return mInnerTxn.setValueFieldU8(field, v); } - void setITFieldU16(SOE_Field field, uint16 v) { return mInnerTxn.setValueFieldU16(field, v); } - void setITFieldU32(SOE_Field field, uint32 v) { return mInnerTxn.setValueFieldU32(field, v); } - void setITFieldU64(SOE_Field field, uint32 v) { return mInnerTxn.setValueFieldU64(field, v); } - void setITFieldH128(SOE_Field field, const uint128& v) { return mInnerTxn.setValueFieldH128(field, v); } - void setITFieldH160(SOE_Field field, const uint160& v) { return mInnerTxn.setValueFieldH160(field, v); } - void setITFieldH256(SOE_Field field, const uint256& v) { return mInnerTxn.setValueFieldH256(field, v); } - void setITFieldVL(SOE_Field field, const std::vector& v) + void setITFieldU8(SField::ref field, unsigned char v) { return mInnerTxn.setValueFieldU8(field, v); } + void setITFieldU16(SField::ref field, uint16 v) { return mInnerTxn.setValueFieldU16(field, v); } + void setITFieldU32(SField::ref field, uint32 v) { return mInnerTxn.setValueFieldU32(field, v); } + void setITFieldU64(SField::ref field, uint32 v) { return mInnerTxn.setValueFieldU64(field, v); } + void setITFieldH128(SField::ref field, const uint128& v) { return mInnerTxn.setValueFieldH128(field, v); } + void setITFieldH160(SField::ref field, const uint160& v) { return mInnerTxn.setValueFieldH160(field, v); } + void setITFieldH256(SField::ref field, const uint256& v) { return mInnerTxn.setValueFieldH256(field, v); } + void setITFieldVL(SField::ref field, const std::vector& v) { return mInnerTxn.setValueFieldVL(field, v); } - void setITFieldTL(SOE_Field field, const std::vector& v) + void setITFieldTL(SField::ref field, const std::vector& v) { return mInnerTxn.setValueFieldTL(field, v); } - void setITFieldAccount(SOE_Field field, const uint160& v) + void setITFieldAccount(SField::ref field, const uint160& v) { return mInnerTxn.setValueFieldAccount(field, v); } - void setITFieldAccount(SOE_Field field, const NewcoinAddress& v) + void setITFieldAccount(SField::ref field, const NewcoinAddress& v) { return mInnerTxn.setValueFieldAccount(field, v); } - void setITFieldAmount(SOE_Field field, const STAmount& v) + void setITFieldAmount(SField::ref field, const STAmount& v) { return mInnerTxn.setValueFieldAmount(field, v); } - void setITFieldPathSet(SOE_Field field, const STPathSet& v) + void setITFieldPathSet(SField::ref field, const STPathSet& v) { return mInnerTxn.setValueFieldPathSet(field, v); } // optional field functions - bool getITFieldPresent(SOE_Field field) const; - void makeITFieldPresent(SOE_Field field); - void makeITFieldAbsent(SOE_Field field); + bool getITFieldPresent(SField::ref field) const; + void makeITFieldPresent(SField::ref field); + void makeITFieldAbsent(SField::ref field); std::vector getAffectedAccounts() const; diff --git a/src/SerializedTypes.cpp b/src/SerializedTypes.cpp index 25339b92e7..6eeb0c9120 100644 --- a/src/SerializedTypes.cpp +++ b/src/SerializedTypes.cpp @@ -27,7 +27,7 @@ std::string SerializedType::getFullText() const return ret; } -STUInt8* STUInt8::construct(SerializerIterator& u, FieldName* name) +STUInt8* STUInt8::construct(SerializerIterator& u, SField::ref name) { return new STUInt8(name, u.get8()); } @@ -43,7 +43,7 @@ bool STUInt8::isEquivalent(const SerializedType& t) const return v && (value == v->value); } -STUInt16* STUInt16::construct(SerializerIterator& u, FieldName* name) +STUInt16* STUInt16::construct(SerializerIterator& u, SField::ref name) { return new STUInt16(name, u.get16()); } @@ -59,7 +59,7 @@ bool STUInt16::isEquivalent(const SerializedType& t) const return v && (value == v->value); } -STUInt32* STUInt32::construct(SerializerIterator& u, FieldName* name) +STUInt32* STUInt32::construct(SerializerIterator& u, SField::ref name) { return new STUInt32(name, u.get32()); } @@ -75,7 +75,7 @@ bool STUInt32::isEquivalent(const SerializedType& t) const return v && (value == v->value); } -STUInt64* STUInt64::construct(SerializerIterator& u, FieldName* name) +STUInt64* STUInt64::construct(SerializerIterator& u, SField::ref name) { return new STUInt64(name, u.get64()); } @@ -91,7 +91,7 @@ bool STUInt64::isEquivalent(const SerializedType& t) const return v && (value == v->value); } -STHash128* STHash128::construct(SerializerIterator& u, FieldName* name) +STHash128* STHash128::construct(SerializerIterator& u, SField::ref name) { return new STHash128(name, u.get128()); } @@ -107,7 +107,7 @@ bool STHash128::isEquivalent(const SerializedType& t) const return v && (value == v->value); } -STHash160* STHash160::construct(SerializerIterator& u, FieldName* name) +STHash160* STHash160::construct(SerializerIterator& u, SField::ref name) { return new STHash160(name, u.get160()); } @@ -123,7 +123,7 @@ bool STHash160::isEquivalent(const SerializedType& t) const return v && (value == v->value); } -STHash256* STHash256::construct(SerializerIterator& u, FieldName* name) +STHash256* STHash256::construct(SerializerIterator& u, SField::ref name) { return new STHash256(name, u.get256()); } @@ -139,7 +139,7 @@ bool STHash256::isEquivalent(const SerializedType& t) const return v && (value == v->value); } -STVariableLength::STVariableLength(SerializerIterator& st, FieldName* name) : SerializedType(name) +STVariableLength::STVariableLength(SerializerIterator& st, SField::ref name) : SerializedType(name) { value = st.getVL(); } @@ -149,7 +149,7 @@ std::string STVariableLength::getText() const return strHex(value); } -STVariableLength* STVariableLength::construct(SerializerIterator& u, FieldName* name) +STVariableLength* STVariableLength::construct(SerializerIterator& u, SField::ref name) { return new STVariableLength(name, u.getVL()); } @@ -171,7 +171,7 @@ std::string STAccount::getText() const return a.humanAccountID(); } -STAccount* STAccount::construct(SerializerIterator& u, FieldName* name) +STAccount* STAccount::construct(SerializerIterator& u, SField::ref name) { return new STAccount(name, u.getVL()); } @@ -181,7 +181,7 @@ STAccount* STAccount::construct(SerializerIterator& u, FieldName* name) // // Return a new object from a SerializerIterator. -STVector256* STVector256::construct(SerializerIterator& u, FieldName* name) +STVector256* STVector256::construct(SerializerIterator& u, SField::ref name) { std::vector data = u.getVL(); std::vector value; @@ -250,7 +250,7 @@ void STAccount::setValueNCA(const NewcoinAddress& nca) setValueH160(nca.getAccountID()); } -STPathSet* STPathSet::construct(SerializerIterator& s, FieldName* name) +STPathSet* STPathSet::construct(SerializerIterator& s, SField::ref name) { std::vector paths; std::vector path; diff --git a/src/SerializedTypes.h b/src/SerializedTypes.h index f31a468d85..2085ab38ac 100644 --- a/src/SerializedTypes.h +++ b/src/SerializedTypes.h @@ -33,23 +33,24 @@ enum PathFlags class SerializedType { protected: - FieldName* fName; + SField::ptr fName; - virtual SerializedType* duplicate() const { return new SerializedType(fName); } + virtual SerializedType* duplicate() const { return new SerializedType(*fName); } + SerializedType(SField::ptr n) : fName(n) { assert(fName); } public: - SerializedType() : fName(NULL) { ; } - SerializedType(FieldName* n) : fName(n) { ; } + SerializedType() : fName(&sfGeneric) { ; } + SerializedType(SField::ref n) : fName(&n) { assert(fName); } SerializedType(const SerializedType& n) : fName(n.fName) { ; } virtual ~SerializedType() { ; } - static std::auto_ptr deserialize(FieldName* name) + static std::auto_ptr deserialize(SField::ref name) { return std::auto_ptr(new SerializedType(name)); } - void setFName(FieldName* n) { fName=n; } - FieldName* getFName() { return fName; } - const char *getName() const { return (fName != NULL) ? fName->fieldName : NULL; } + void setFName(SField::ref n) { fName = &n; assert(fName); } + SField::ref getFName() { return *fName; } + const char *getName() const { return fName->fieldName; } virtual SerializedTypeID getSType() const { return STI_NOTPRESENT; } std::auto_ptr clone() const { return std::auto_ptr(duplicate()); } @@ -66,7 +67,7 @@ public: { assert(getSType() == STI_NOTPRESENT); return t.getSType() == STI_NOTPRESENT; } SerializedType& operator=(const SerializedType& t) - { if (fName == NULL) fName = t.fName; return *this; } + { if (!fName->fieldCode) fName = t.fName; return *this; } bool operator==(const SerializedType& t) const { return (getSType() == t.getSType()) && isEquivalent(t); } bool operator!=(const SerializedType& t) const @@ -82,14 +83,14 @@ class STUInt8 : public SerializedType protected: unsigned char value; - STUInt8* duplicate() const { return new STUInt8(fName, value); } - static STUInt8* construct(SerializerIterator&, FieldName* name = NULL); + STUInt8* duplicate() const { return new STUInt8(*this); } + static STUInt8* construct(SerializerIterator&, SField::ref f); public: - STUInt8(unsigned char v=0) : value(v) { ; } - STUInt8(FieldName* n, unsigned char v=0) : SerializedType(n), value(v) { ; } - static std::auto_ptr deserialize(SerializerIterator& sit, FieldName* name) + STUInt8(unsigned char v = 0) : value(v) { ; } + STUInt8(SField::ref n, unsigned char v=0) : SerializedType(n), value(v) { ; } + static std::auto_ptr deserialize(SerializerIterator& sit, SField::ref name) { return std::auto_ptr(construct(sit, name)); } SerializedTypeID getSType() const { return STI_UINT8; } @@ -108,14 +109,14 @@ class STUInt16 : public SerializedType protected: uint16 value; - STUInt16* duplicate() const { return new STUInt16(fName, value); } - static STUInt16* construct(SerializerIterator&, FieldName* name = NULL); + STUInt16* duplicate() const { return new STUInt16(*this); } + static STUInt16* construct(SerializerIterator&, SField::ref name); public: STUInt16(uint16 v=0) : value(v) { ; } - STUInt16(FieldName* n, uint16 v=0) : SerializedType(n), value(v) { ; } - static std::auto_ptr deserialize(SerializerIterator& sit, FieldName* name) + STUInt16(SField::ref n, uint16 v=0) : SerializedType(n), value(v) { ; } + static std::auto_ptr deserialize(SerializerIterator& sit, SField::ref name) { return std::auto_ptr(construct(sit, name)); } SerializedTypeID getSType() const { return STI_UINT16; } @@ -134,14 +135,14 @@ class STUInt32 : public SerializedType protected: uint32 value; - STUInt32* duplicate() const { return new STUInt32(fName, value); } - static STUInt32* construct(SerializerIterator&, FieldName* name = NULL); + STUInt32* duplicate() const { return new STUInt32(*this); } + static STUInt32* construct(SerializerIterator&, SField::ref name); public: - STUInt32(uint32 v=0) : value(v) { ; } - STUInt32(FieldName* n, uint32 v=0) : SerializedType(n), value(v) { ; } - static std::auto_ptr deserialize(SerializerIterator& sit, FieldName* name) + STUInt32(uint32 v = 0) : value(v) { ; } + STUInt32(SField::ref n, uint32 v=0) : SerializedType(n), value(v) { ; } + static std::auto_ptr deserialize(SerializerIterator& sit, SField::ref name) { return std::auto_ptr(construct(sit, name)); } SerializedTypeID getSType() const { return STI_UINT32; } @@ -160,14 +161,14 @@ class STUInt64 : public SerializedType protected: uint64 value; - STUInt64* duplicate() const { return new STUInt64(fName, value); } - static STUInt64* construct(SerializerIterator&, FieldName* name = NULL); + STUInt64* duplicate() const { return new STUInt64(*this); } + static STUInt64* construct(SerializerIterator&, SField::ref name); public: STUInt64(uint64 v=0) : value(v) { ; } - STUInt64(FieldName* n, uint64 v=0) : SerializedType(n), value(v) { ; } - static std::auto_ptr deserialize(SerializerIterator& sit, FieldName* name) + STUInt64(SField::ref n, uint64 v=0) : SerializedType(n), value(v) { ; } + static std::auto_ptr deserialize(SerializerIterator& sit, SField::ref name) { return std::auto_ptr(construct(sit, name)); } SerializedTypeID getSType() const { return STI_UINT64; } @@ -205,7 +206,7 @@ protected: void canonicalize(); STAmount* duplicate() const { return new STAmount(*this); } - static STAmount* construct(SerializerIterator&, FieldName* name = NULL); + static STAmount* construct(SerializerIterator&, SField::ref name); static const int cMinOffset = -96, cMaxOffset = 80; static const uint64 cMinValue = 1000000000000000ull, cMaxValue = 9999999999999999ull; @@ -215,10 +216,10 @@ protected: STAmount(bool isNeg, uint64 value) : mValue(value), mOffset(0), mIsNative(true), mIsNegative(isNeg) { ; } - STAmount(FieldName *name, uint64 value, bool isNegative) + STAmount(SField *name, uint64 value, bool isNegative) : SerializedType(fName), mValue(value), mOffset(0), mIsNative(true), mIsNegative(isNegative) { ; } - STAmount(FieldName *n, const uint160& cur, const uint160& iss, uint64 val, int off, bool isNat, bool isNeg) + STAmount(SField *n, const uint160& cur, const uint160& iss, uint64 val, int off, bool isNat, bool isNeg) : SerializedType(n), mCurrency(cur), mIssuer(iss), mValue(val), mOffset(off), mIsNative(isNat), mIsNegative(isNeg) { ; } @@ -231,7 +232,7 @@ public: STAmount(uint64 v = 0, bool isNeg = false) : mValue(v), mOffset(0), mIsNative(true), mIsNegative(isNeg) { if (v==0) mIsNegative = false; } - STAmount(FieldName* n, uint64 v = 0) + STAmount(SField::ref n, uint64 v = 0) : SerializedType(n), mValue(v), mOffset(0), mIsNative(true), mIsNegative(false) { ; } @@ -240,14 +241,14 @@ public: { canonicalize(); } // YYY This should probably require issuer too. - STAmount(FieldName* n, const uint160& currency, const uint160& issuer, + STAmount(SField::ref n, const uint160& currency, const uint160& issuer, uint64 v = 0, int off = 0, bool isNeg = false) : SerializedType(n), mCurrency(currency), mIssuer(issuer), mValue(v), mOffset(off), mIsNegative(isNeg) { canonicalize(); } - STAmount(FieldName* n, int64 v); + STAmount(SField::ref n, int64 v); - static std::auto_ptr deserialize(SerializerIterator& sit, FieldName* name) + static std::auto_ptr deserialize(SerializerIterator& sit, SField::ref name) { return std::auto_ptr(construct(sit, name)); } static STAmount saFromRate(uint64 uRate = 0) @@ -357,7 +358,7 @@ public: // Native currency conversions, to/from display format static uint64 convertToDisplayAmount(const STAmount& internalAmount, uint64 totalNow, uint64 totalInit); static STAmount convertToInternalAmount(uint64 displayAmount, uint64 totalNow, uint64 totalInit, - FieldName* name = NULL); + SField::ref name = sfGeneric); static std::string createHumanCurrency(const uint160& uCurrency); static STAmount deserialize(SerializerIterator&); @@ -374,16 +375,16 @@ class STHash128 : public SerializedType protected: uint128 value; - STHash128* duplicate() const { return new STHash128(fName, value); } - static STHash128* construct(SerializerIterator&, FieldName* name = NULL); + STHash128* duplicate() const { return new STHash128(*this); } + static STHash128* construct(SerializerIterator&, SField::ref name); public: STHash128(const uint128& v) : value(v) { ; } - STHash128(FieldName* n, const uint128& v) : SerializedType(n), value(v) { ; } - STHash128(FieldName* n) : SerializedType(n) { ; } + STHash128(SField::ref n, const uint128& v) : SerializedType(n), value(v) { ; } + STHash128(SField::ref n) : SerializedType(n) { ; } STHash128() { ; } - static std::auto_ptr deserialize(SerializerIterator& sit, FieldName* name) + static std::auto_ptr deserialize(SerializerIterator& sit, SField::ref name) { return std::auto_ptr(construct(sit, name)); } SerializedTypeID getSType() const { return STI_HASH128; } @@ -402,16 +403,16 @@ class STHash160 : public SerializedType protected: uint160 value; - STHash160* duplicate() const { return new STHash160(fName, value); } - static STHash160* construct(SerializerIterator&, FieldName* name = NULL); + STHash160* duplicate() const { return new STHash160(*this); } + static STHash160* construct(SerializerIterator&, SField::ref name); public: STHash160(const uint160& v) : value(v) { ; } - STHash160(FieldName* n, const uint160& v) : SerializedType(n), value(v) { ; } - STHash160(FieldName* n) : SerializedType(n) { ; } + STHash160(SField::ref n, const uint160& v) : SerializedType(n), value(v) { ; } + STHash160(SField::ref n) : SerializedType(n) { ; } STHash160() { ; } - static std::auto_ptr deserialize(SerializerIterator& sit, FieldName* name) + static std::auto_ptr deserialize(SerializerIterator& sit, SField::ref name) { return std::auto_ptr(construct(sit, name)); } SerializedTypeID getSType() const { return STI_HASH160; } @@ -430,16 +431,16 @@ class STHash256 : public SerializedType protected: uint256 value; - STHash256* duplicate() const { return new STHash256(fName, value); } - static STHash256* construct(SerializerIterator&, FieldName* name = NULL); + STHash256* duplicate() const { return new STHash256(*this); } + static STHash256* construct(SerializerIterator&, SField::ref); public: STHash256(const uint256& v) : value(v) { ; } - STHash256(FieldName* n, const uint256& v) : SerializedType(n), value(v) { ; } - STHash256(FieldName* n) : SerializedType(n) { ; } + STHash256(SField::ref n, const uint256& v) : SerializedType(n), value(v) { ; } + STHash256(SField::ref n) : SerializedType(n) { ; } STHash256() { ; } - static std::auto_ptr deserialize(SerializerIterator& sit, FieldName* name) + static std::auto_ptr deserialize(SerializerIterator& sit, SField::ref name) { return std::auto_ptr(construct(sit, name)); } SerializedTypeID getSType() const { return STI_HASH256; } @@ -458,17 +459,17 @@ class STVariableLength : public SerializedType protected: std::vector value; - virtual STVariableLength* duplicate() const { return new STVariableLength(fName, value); } - static STVariableLength* construct(SerializerIterator&, FieldName* name = NULL); + virtual STVariableLength* duplicate() const { return new STVariableLength(*this); } + static STVariableLength* construct(SerializerIterator&, SField::ref); public: STVariableLength(const std::vector& v) : value(v) { ; } - STVariableLength(FieldName* n, const std::vector& v) : SerializedType(n), value(v) { ; } - STVariableLength(FieldName* n) : SerializedType(n) { ; } - STVariableLength(SerializerIterator&, FieldName* name = NULL); + STVariableLength(SField::ref n, const std::vector& v) : SerializedType(n), value(v) { ; } + STVariableLength(SField::ref n) : SerializedType(n) { ; } + STVariableLength(SerializerIterator&, SField::ref name = sfGeneric); STVariableLength() { ; } - static std::auto_ptr deserialize(SerializerIterator& sit, FieldName* name) + static std::auto_ptr deserialize(SerializerIterator& sit, SField::ref name) { return std::auto_ptr(construct(sit, name)); } virtual SerializedTypeID getSType() const { return STI_VL; } @@ -487,16 +488,16 @@ public: class STAccount : public STVariableLength { protected: - virtual STAccount* duplicate() const { return new STAccount(fName, value); } - static STAccount* construct(SerializerIterator&, FieldName* name = NULL); + virtual STAccount* duplicate() const { return new STAccount(*this); } + static STAccount* construct(SerializerIterator&, SField::ref); public: STAccount(const std::vector& v) : STVariableLength(v) { ; } - STAccount(FieldName* n, const std::vector& v) : STVariableLength(n, v) { ; } - STAccount(FieldName* n) : STVariableLength(n) { ; } + STAccount(SField::ref n, const std::vector& v) : STVariableLength(n, v) { ; } + STAccount(SField::ref n) : STVariableLength(n) { ; } STAccount() { ; } - static std::auto_ptr deserialize(SerializerIterator& sit, FieldName* name) + static std::auto_ptr deserialize(SerializerIterator& sit, SField::ref name) { return std::auto_ptr(construct(sit, name)); } SerializedTypeID getSType() const { return STI_ACCOUNT; } @@ -625,16 +626,16 @@ class STPathSet : public SerializedType protected: std::vector value; - STPathSet* duplicate() const { return new STPathSet(fName, value); } - static STPathSet* construct(SerializerIterator&, FieldName* name = NULL); + STPathSet* duplicate() const { return new STPathSet(*this); } + static STPathSet* construct(SerializerIterator&, SField::ref); public: STPathSet() { ; } - STPathSet(FieldName* n) : SerializedType(n) { ; } + STPathSet(SField::ref n) : SerializedType(n) { ; } STPathSet(const std::vector& v) : value(v) { ; } - STPathSet(FieldName* n, const std::vector& v) : SerializedType(n), value(v) { ; } - static std::auto_ptr deserialize(SerializerIterator& sit, FieldName* name) + STPathSet(SField::ref n, const std::vector& v) : SerializedType(n), value(v) { ; } + static std::auto_ptr deserialize(SerializerIterator& sit, SField::ref name) { return std::auto_ptr(construct(sit, name)); } // std::string getText() const; @@ -697,19 +698,19 @@ class STVector256 : public SerializedType protected: std::vector mValue; - STVector256* duplicate() const { return new STVector256(fName, mValue); } - static STVector256* construct(SerializerIterator&, FieldName* name = NULL); + STVector256* duplicate() const { return new STVector256(*this); } + static STVector256* construct(SerializerIterator&, SField::ref); public: STVector256() { ; } - STVector256(FieldName* n) : SerializedType(n) { ; } - STVector256(FieldName* n, const std::vector& v) : SerializedType(n), mValue(v) { ; } + STVector256(SField::ref n) : SerializedType(n) { ; } + STVector256(SField::ref n, const std::vector& v) : SerializedType(n), mValue(v) { ; } STVector256(const std::vector& vector) : mValue(vector) { ; } SerializedTypeID getSType() const { return STI_VECTOR256; } void add(Serializer& s) const; - static std::auto_ptr deserialize(SerializerIterator& sit, FieldName* name) + static std::auto_ptr deserialize(SerializerIterator& sit, SField::ref name) { return std::auto_ptr(construct(sit, name)); } const std::vector& peekValue() const { return mValue; } diff --git a/src/TransactionMeta.cpp b/src/TransactionMeta.cpp index 4c179f0b70..3f687897c1 100644 --- a/src/TransactionMeta.cpp +++ b/src/TransactionMeta.cpp @@ -66,7 +66,7 @@ Json::Value TMNEThread::getJson(int) const TMNEAmount::TMNEAmount(int type, SerializerIterator& sit) : TransactionMetaNodeEntry(type) { - mAmount = *dynamic_cast(STAmount::deserialize(sit, NULL).get()); // Ouch + mAmount = *dynamic_cast(STAmount::deserialize(sit, sfAmount).get()); // Ouch } void TMNEAmount::addRaw(Serializer& s) const From 8a5a9e09258496d73740a7c4dd25fd3cd6fb8958 Mon Sep 17 00:00:00 2001 From: JoelKatz Date: Tue, 25 Sep 2012 22:47:40 -0700 Subject: [PATCH 03/53] Small fixes. --- src/Serializer.h | 5 +++-- 1 file changed, 3 insertions(+), 2 deletions(-) diff --git a/src/Serializer.h b/src/Serializer.h index e1c251508c..30dfe1ceb8 100644 --- a/src/Serializer.h +++ b/src/Serializer.h @@ -92,7 +92,7 @@ public: int getDataLength() const { return mData.size(); } const void* getDataPtr() const { return &mData.front(); } void* getDataPtr() { return &mData.front(); } - int getLength() { return mData.size(); } + int getLength() const { return mData.size(); } const std::vector& peekData() const { return mData; } std::vector getData() const { return mData; } std::string getString() const { return std::string(static_cast(getDataPtr()), size()); } @@ -143,11 +143,12 @@ protected: public: SerializerIterator(const Serializer& s) : mSerializer(s), mPos(0) { ; } - void reset(void) { mPos=0; } + void reset(void) { mPos = 0; } void setPos(int p) { mPos = p; } const Serializer& operator*(void) { return mSerializer; } int getPos(void) { return mPos; } + bool empty() { return mPos == mSerializer.getLength(); } int getBytesLeft(); // get functions throw on error From e0587a44b85ef7093232eb412ddffc6057be6174 Mon Sep 17 00:00:00 2001 From: JoelKatz Date: Tue, 25 Sep 2012 22:47:59 -0700 Subject: [PATCH 04/53] More work on new serializer code. --- src/FieldNames.cpp | 36 ++++++++++++++- src/FieldNames.h | 9 ++++ src/SerializedObject.cpp | 87 +++++++++++++++++++++++++++---------- src/SerializedObject.h | 37 +++++++++++----- src/SerializedTransaction.h | 1 - src/SerializedTypes.h | 2 +- 6 files changed, 134 insertions(+), 38 deletions(-) diff --git a/src/FieldNames.cpp b/src/FieldNames.cpp index c8388ad02d..14827bf7f2 100644 --- a/src/FieldNames.cpp +++ b/src/FieldNames.cpp @@ -4,6 +4,7 @@ #include #include +#include SField sfInvalid(-1), sfGeneric(0); @@ -19,13 +20,46 @@ static boost::mutex SField::mapMutex; SField::ref SField::getField(int code); { + int type = code >> 16; + int field = code % 0xffff; + if ((type <= 0) || (type >= 256) || (field <= 0) || (field >= 256 return sfInvalid; + boost::mutex::scoped_lock sl(mapMutex); std::map it = unknownFieldMap.Find(code); if (it != codeToField.end()) return *(it->second); - return *(new SField(code, static_cast(code>>16), code&0xffff, NULL)); + switch(type) + { // types we are willing to dynamically extend + +#define FIELD(name, type, index) +#define TYPE(name, type, index) case sf##name: +#include "SerializeProto.h" +#undef FIELD +#undef TYPE + + break; + default: + return sfInvalid; + } + + return *(new SField(code, static_cast(type), field, NULL)); +} + +SField::ref SField::getField(int type, int value) +{ + return getField(FIELD_CODE(type, value)); +} + +std::string SField::getName() cosnt +{ + if (fieldName != NULL) + return fieldName; + if (fieldValue == 0) + return ""; + return boost::lexical_cast(static_cast(fieldType)) + "/" + + boost::lexical_cast(fieldValue); } diff --git a/src/FieldNames.h b/src/FieldNames.h index db29e0ebdf..4432320447 100644 --- a/src/FieldNames.h +++ b/src/FieldNames.h @@ -1,6 +1,8 @@ #ifndef __FIELDNAMES__ #define __FIELDNAMES__ +#include + #include #define FIELD_CODE(type, index) ((static_cast(type) << 16) | index) @@ -55,11 +57,18 @@ public: SField(int fc) : fieldCode(fc), fieldType(STI_UNKNOWN), fieldValue(0), fieldName(NULL) { ; } static SField::ref getField(int fieldCode); + static SField::ref getField(int fieldType, int fieldValue); static SField::ref getField(SerializedTypeID type, int value) { return getField(FIELD_CODE(type, value)); } + std::string getName() const; + bool hasName() const { return (fieldName != NULL) || (fieldValue != 0); } + bool isGeneric() const { return fieldCode == 0; } bool isInvalid() const { return fieldCode == -1; } bool isKnown() const { return fieldType != STI_UNKNOWN; } + + bool operator==(const SField& f) const { return fieldCode == f.fieldCode; } + bool operator!=(const SField& f) const { return fieldCode != f.fieldCode; } }; extern SField sfInvalid, sfGeneric; diff --git a/src/SerializedObject.cpp b/src/SerializedObject.cpp index d935022cb9..5ec0c8ad49 100644 --- a/src/SerializedObject.cpp +++ b/src/SerializedObject.cpp @@ -10,6 +10,8 @@ std::auto_ptr STObject::makeDefaultObject(SerializedTypeID id, SField::ref name) { + assert((id == STI_NOTPRESENT) || (id == name.fieldType)); + switch(id) { case STI_NOTPRESENT: @@ -48,6 +50,12 @@ std::auto_ptr STObject::makeDefaultObject(SerializedTypeID id, S case STI_PATHSET: return std::auto_ptr(new STPathSet(name)); + case STI_OBJECT: + return std::auto_ptr(new STObject(name)); + + case STI_ARRAY: + return std::auto_ptr(new STArray(name)); + default: throw std::runtime_error("Unknown object type"); } @@ -105,7 +113,7 @@ std::auto_ptr STObject::makeDeserializedObject(SerializedTypeID } } -void STObject::set(const SOElement* elem) +void STObject::set(SOElement::ptr elem) { mData.empty(); mType.empty(); @@ -114,39 +122,70 @@ void STObject::set(const SOElement* elem) { mType.push_back(elem); if (elem->flags == SOE_OPTIONAL) - giveObject(makeDefaultObject(STI_NOTPRESENT, elem)); + giveObject(makeDefaultObject(STI_NOTPRESENT, elem->e_field)); else - giveObject(makeDefaultObject(elem->e_field, elem)); + giveObject(makeDefaultObject(elem->e_field.fieldType, elem->e_field)); ++elem; } } -STObject::STObject(const SOElement* elem, SField::ref name) : SerializedType(name) -{ - set(elem); -} - -void STObject::set(SField::ref name, SerializerIterator& sit, int depth = 0) +void STObject::setType(SOElement::ptrList t) { mData.empty(); - mType.empty(); - - fName = name; - - while(1) - { - int type, field. - sit.getFieldID(type, field); - if ((type == STI_ARRAY) && (field == 1)) - return; - SField::ref fn = SField::getField(type, field); - giveObject(makeDeserializedObject(static_cast type, fn, sit, depth + 1); - } + while (t->flags != SOE_END) + mType.push_back(t++); } -STObject::STObject(const SOElement* elem, SerializerIterator& sit, SField::refname) : SerializedType(name) +bool STObject::isValidForType() { - set(elem, sit); + BOOST_FOREACH(SOElement::ptr elem, mType) + { // are any required elemnents missing + if ((elem->flags == SOE_REQUIRED) && (getPField(elem->e_field) == NULL)) + { + Log(lsWARNING) << getName() << " missing required element " << elem->e_field.fieldName; + return false; + } + } + + BOOST_FOREACH(const SerializedType& elem, mData) + { // are any non-permitted elements present + if (!isFieldAllowed(elem.getFName())) + { + Log(lsWARNING) << getName() << " has non-permitted element " << elem.getName(); + return false; + } + } + + return true; +} + +bool STObject::isFieldAllowed(SField::ref field) +{ + BOOST_FOREACH(SOElement::ptr elem, mType) + { // are any required elemnents missing + if (elem->e_field == field) + return true; + } + return false; +} + +bool STObject::set(SOElement::ptrList elem, SerializerIterator& sit, int depth) +{ // return true = terminated with end-of-object + setType(elem); + + mData.empty(); + while (!sit.empty()) + { + int type, field; + sit.getFieldID(type, field); + if ((type == STI_OBJECT) && (field == 1)) // end of object indicator + return true; + SField::ref fn = SField::getField(type, field); + if (fn.isInvalid()) + throw std::runtime_error("Unknown field"); + giveObject(makeDeserializedObject(fn.fieldType, fn, sit, depth + 1)); + } + return false; } std::string STObject::getFullText() const diff --git a/src/SerializedObject.h b/src/SerializedObject.h index 491e85a599..47e0d9639e 100644 --- a/src/SerializedObject.h +++ b/src/SerializedObject.h @@ -11,34 +11,48 @@ // Serializable object/array types -struct SOElement +class SOElement { // An element in the description of a serialized object +public: + typedef SOElement const * ptr; // used to point to one element + typedef SOElement const * ptrList; // used to point to a terminated list of elements + SField::ref e_field; - SOE_Flags flags; + const SOE_Flags flags; }; class STObject : public SerializedType { protected: boost::ptr_vector mData; - std::vector mType; + std::vector mType; STObject* duplicate() const { return new STObject(*this); } static STObject* construct(SerializerIterator&, SField::ref); public: - STObject(SField *n = NULL) : SerializedType(n) { ; } - STObject(const SOElement *t, SField *n = NULL); - STObject(const SOElement *t, SerializerIterator& u, SField *n = NULL); + STObject() { ; } + + STObject(SField::ref name) : SerializedType(name) { ; } + + STObject(SOElement::ptrList type, SField::ref name) : SerializedType(name) + { set(type); } + + STObject(SOElement::ptrList type, SerializerIterator& sit, SField::ref name) : SerializedType(name) + { set(type, sit); } + virtual ~STObject() { ; } static std::auto_ptr deserialize(SerializerIterator& sit, SField::ref name) { return std::auto_ptr(construct(sit, name)); } - void set(const SOElement* t); - void set(const SOElement* t, SerializerIterator& u, int depth = 0); + void setType(SOElement const * t); + bool isValidForType(); + bool isFieldAllowed(SField::ref); + + void set(SOElement::ptrList); + bool set(SOElement::ptrList, SerializerIterator& u, int depth = 0); - int getLength() const; virtual SerializedTypeID getSType() const { return STI_OBJECT; } virtual bool isEquivalent(const SerializedType& t) const; @@ -111,8 +125,8 @@ public: SerializedType* makeFieldPresent(SField::ref field); void makeFieldAbsent(SField::ref field); - static std::auto_ptr makeDefaultObject(SerializedTypeID id, SField *name); - static std::auto_ptr makeDeserializedObject(SerializedTypeID id, SField *name, + static std::auto_ptr makeDefaultObject(SerializedTypeID id, SField::ref name); + static std::auto_ptr makeDeserializedObject(SerializedTypeID id, SField::ref name, SerializerIterator&, int depth); static void unitTest(); @@ -138,6 +152,7 @@ protected: public: STArray() { ; } + STArray(SField::ref f) : SerializedType(f) { ; } STArray(SField::ref f, const vector& v) : SerializedType(f), value(v) { ; } STArray(vector& v) : value(v) { ; } diff --git a/src/SerializedTransaction.h b/src/SerializedTransaction.h index d1278b8645..ce997b5b8c 100644 --- a/src/SerializedTransaction.h +++ b/src/SerializedTransaction.h @@ -37,7 +37,6 @@ public: SerializedTransaction(TransactionType type); // STObject functions - int getLength() const; SerializedTypeID getSType() const { return STI_TRANSACTION; } std::string getFullText() const; std::string getText() const; diff --git a/src/SerializedTypes.h b/src/SerializedTypes.h index 2085ab38ac..d9bc627abb 100644 --- a/src/SerializedTypes.h +++ b/src/SerializedTypes.h @@ -49,7 +49,7 @@ public: { return std::auto_ptr(new SerializedType(name)); } void setFName(SField::ref n) { fName = &n; assert(fName); } - SField::ref getFName() { return *fName; } + SField::ref getFName() const { return *fName; } const char *getName() const { return fName->fieldName; } virtual SerializedTypeID getSType() const { return STI_NOTPRESENT; } From fbb0baaca04d2350cdbee806ee4ba73cb2a4d0f1 Mon Sep 17 00:00:00 2001 From: JoelKatz Date: Wed, 26 Sep 2012 00:28:58 -0700 Subject: [PATCH 05/53] Cleanups. --- src/FieldNames.cpp | 14 ++++++++++++++ src/FieldNames.h | 2 ++ src/SerializedObject.cpp | 11 +++++++++-- src/SerializedObject.h | 3 ++- src/SerializedTypes.h | 2 ++ src/Serializer.h | 2 ++ 6 files changed, 31 insertions(+), 3 deletions(-) diff --git a/src/FieldNames.cpp b/src/FieldNames.cpp index 14827bf7f2..57f823de3e 100644 --- a/src/FieldNames.cpp +++ b/src/FieldNames.cpp @@ -49,6 +49,20 @@ SField::ref SField::getField(int code); return *(new SField(code, static_cast(type), field, NULL)); } +int SField::compare(SField::ref f1, SField::ref f2) +{ // -1 = f1 comes before f2, 0 = illegal combination, 1 = f1 comes after f2 + if ((f1.fieldCode <= 0) || (f2.fieldCode <= 0)) + return 0; + + if (f1.fieldCode < f2.fieldCode) + return -1; + + if (f2.fieldCode < f1.fieldCode) + return 1; + + return 0; +} + SField::ref SField::getField(int type, int value) { return getField(FIELD_CODE(type, value)); diff --git a/src/FieldNames.h b/src/FieldNames.h index 4432320447..cd035f1330 100644 --- a/src/FieldNames.h +++ b/src/FieldNames.h @@ -69,6 +69,8 @@ public: bool operator==(const SField& f) const { return fieldCode == f.fieldCode; } bool operator!=(const SField& f) const { return fieldCode != f.fieldCode; } + + static int compare(SField::ref f1, SField::ref f2); }; extern SField sfInvalid, sfGeneric; diff --git a/src/SerializedObject.cpp b/src/SerializedObject.cpp index 5ec0c8ad49..c5713494d2 100644 --- a/src/SerializedObject.cpp +++ b/src/SerializedObject.cpp @@ -192,9 +192,9 @@ std::string STObject::getFullText() const { std::string ret; bool first = true; - if (name != NULL) + if (fName->hasName()) { - ret = name; + ret = fName->getName(); ret += " = {"; } else ret = "{"; @@ -213,6 +213,13 @@ std::string STObject::getFullText() const void STObject::add(Serializer& s) const { + addFieldID(s); + addRaw(s); + s.addFieldID(STI_OBJECT, 1); +} + +void STObject::addRaw(Serializer& s) const +{ // FIXME: need to add in sorted order BOOST_FOREACH(const SerializedType& it, mData) it.add(s); } diff --git a/src/SerializedObject.h b/src/SerializedObject.h index 47e0d9639e..3242802fe0 100644 --- a/src/SerializedObject.h +++ b/src/SerializedObject.h @@ -56,7 +56,8 @@ public: virtual SerializedTypeID getSType() const { return STI_OBJECT; } virtual bool isEquivalent(const SerializedType& t) const; - void add(Serializer& s) const; + void add(Serializer& s) const; // with start/end of object + virtual void addRaw(Serializer& s) const; // just inner elements Serializer getSerializer() const { Serializer s; add(s); return s; } std::string getFullText() const; std::string getText() const; diff --git a/src/SerializedTypes.h b/src/SerializedTypes.h index d9bc627abb..64dae0d73b 100644 --- a/src/SerializedTypes.h +++ b/src/SerializedTypes.h @@ -66,6 +66,8 @@ public: virtual bool isEquivalent(const SerializedType& t) const { assert(getSType() == STI_NOTPRESENT); return t.getSType() == STI_NOTPRESENT; } + void addFieldID(Serializer& s) const { s.addFieldID(fName->fieldType, fName->fieldValue); } + SerializedType& operator=(const SerializedType& t) { if (!fName->fieldCode) fName = t.fName; return *this; } bool operator==(const SerializedType& t) const diff --git a/src/Serializer.h b/src/Serializer.h index 30dfe1ceb8..ec762e52c7 100644 --- a/src/Serializer.h +++ b/src/Serializer.h @@ -9,6 +9,7 @@ #include "key.h" #include "uint256.h" +#include "FieldNames.h" typedef std::pair > TaggedListItem; @@ -69,6 +70,7 @@ public: bool getFieldID(int& type, int& name, int offset) const; int addFieldID(int type, int name); + int addFieldID(SerializedTypeID type, int name); // normal hash functions uint160 getRIPEMD160(int size=-1) const; From 96eef8388ffe97d60b8b14dadbed9d3f180076e4 Mon Sep 17 00:00:00 2001 From: JoelKatz Date: Wed, 26 Sep 2012 12:46:53 -0700 Subject: [PATCH 06/53] Remove a line of dead code. Add two convenience functions. --- src/SerializedObject.h | 6 +++++- 1 file changed, 5 insertions(+), 1 deletion(-) diff --git a/src/SerializedObject.h b/src/SerializedObject.h index 3242802fe0..58914bfb78 100644 --- a/src/SerializedObject.h +++ b/src/SerializedObject.h @@ -87,7 +87,6 @@ public: SerializedType& getField(SField::ref field); const SerializedType* peekAtPField(SField::ref field) const; SerializedType* getPField(SField::ref field); - const SOElement* getFieldType(SField::ref field) const; // these throw if the field type doesn't match, or return default values if the // field is optional but not present @@ -130,6 +129,11 @@ public: static std::auto_ptr makeDeserializedObject(SerializedTypeID id, SField::ref name, SerializerIterator&, int depth); + static std::auto_ptr makeNonPresentObject(SField::ref name) + { return makeDefaultObject(STI_NOTPRESENT, name); } + static std::auto_ptr makeDefaultObject(SField::ref name) + { return makeDefaultObject(name.fieldType, name); } + static void unitTest(); }; From 19b9facdef8dc85c6520b0ef8e6c1c2a445415ed Mon Sep 17 00:00:00 2001 From: JoelKatz Date: Wed, 26 Sep 2012 12:47:17 -0700 Subject: [PATCH 07/53] name -> fName --- src/Amount.cpp | 20 ++++++++++---------- 1 file changed, 10 insertions(+), 10 deletions(-) diff --git a/src/Amount.cpp b/src/Amount.cpp index c9e3e4475c..7af2d28e71 100644 --- a/src/Amount.cpp +++ b/src/Amount.cpp @@ -519,7 +519,7 @@ STAmount& STAmount::operator-=(const STAmount& a) STAmount STAmount::operator-(void) const { if (mValue == 0) return *this; - return STAmount(name, mCurrency, mIssuer, mValue, mOffset, mIsNative, !mIsNegative); + return STAmount(fName, mCurrency, mIssuer, mValue, mOffset, mIsNative, !mIsNegative); } STAmount& STAmount::operator=(uint64 v) @@ -572,12 +572,12 @@ bool STAmount::operator>=(uint64 v) const STAmount STAmount::operator+(uint64 v) const { - return STAmount(name, getSNValue() + static_cast(v)); + return STAmount(fName, getSNValue() + static_cast(v)); } STAmount STAmount::operator-(uint64 v) const { - return STAmount(name, getSNValue() - static_cast(v)); + return STAmount(fName, getSNValue() - static_cast(v)); } STAmount::operator double() const @@ -595,7 +595,7 @@ STAmount operator+(const STAmount& v1, const STAmount& v2) v1.throwComparable(v2); if (v1.mIsNative) - return STAmount(v1.name, v1.getSNValue() + v2.getSNValue()); + return STAmount(v1.fName, v1.getSNValue() + v2.getSNValue()); int ov1 = v1.mOffset, ov2 = v2.mOffset; @@ -617,9 +617,9 @@ STAmount operator+(const STAmount& v1, const STAmount& v2) int64 fv = vv1 + vv2; if (fv >= 0) - return STAmount(v1.name, v1.mCurrency, v1.mIssuer, fv, ov1, false); + return STAmount(v1.fName, v1.mCurrency, v1.mIssuer, fv, ov1, false); else - return STAmount(v1.name, v1.mCurrency, v1.mIssuer, -fv, ov1, true); + return STAmount(v1.fName, v1.mCurrency, v1.mIssuer, -fv, ov1, true); } STAmount operator-(const STAmount& v1, const STAmount& v2) @@ -628,7 +628,7 @@ STAmount operator-(const STAmount& v1, const STAmount& v2) v1.throwComparable(v2); if (v2.mIsNative) - return STAmount(v1.name, v1.getSNValue() - v2.getSNValue()); + return STAmount(v1.fName, v1.getSNValue() - v2.getSNValue()); int ov1 = v1.mOffset, ov2 = v2.mOffset; int64 vv1 = static_cast(v1.mValue), vv2 = static_cast(v2.mValue); @@ -649,9 +649,9 @@ STAmount operator-(const STAmount& v1, const STAmount& v2) int64 fv = vv1 - vv2; if (fv >= 0) - return STAmount(v1.name, v1.mCurrency, v1.mIssuer, fv, ov1, false); + return STAmount(v1.fName, v1.mCurrency, v1.mIssuer, fv, ov1, false); else - return STAmount(v1.name, v1.mCurrency, v1.mIssuer, -fv, ov1, true); + return STAmount(v1.fName, v1.mCurrency, v1.mIssuer, -fv, ov1, true); } STAmount STAmount::divide(const STAmount& num, const STAmount& den, const uint160& uCurrencyID, const uint160& uIssuerID) @@ -703,7 +703,7 @@ STAmount STAmount::multiply(const STAmount& v1, const STAmount& v2, const uint16 return STAmount(uCurrencyID, uIssuerID); if (v1.mIsNative && v2.mIsNative) // FIXME: overflow - return STAmount(v1.name, v1.getSNValue() * v2.getSNValue()); + return STAmount(v1.fName, v1.getSNValue() * v2.getSNValue()); uint64 value1 = v1.mValue, value2 = v2.mValue; int offset1 = v1.mOffset, offset2 = v2.mOffset; From 0c0069f77c0b79fc68535a8c1ba4e3de88c54e41 Mon Sep 17 00:00:00 2001 From: JoelKatz Date: Wed, 26 Sep 2012 12:47:28 -0700 Subject: [PATCH 08/53] Small bugfixes. --- src/FieldNames.cpp | 16 ++++++++-------- 1 file changed, 8 insertions(+), 8 deletions(-) diff --git a/src/FieldNames.cpp b/src/FieldNames.cpp index 57f823de3e..483694c2d2 100644 --- a/src/FieldNames.cpp +++ b/src/FieldNames.cpp @@ -9,34 +9,34 @@ SField sfInvalid(-1), sfGeneric(0); -#define FIELD(name, type, index) SField sf##name(FIELD_CODE(STI_##type, index), STI_##type, index, naem); +#define FIELD(name, type, index) SField sf##name(FIELD_CODE(STI_##type, index), STI_##type, index, #name); #define TYPE(name, type, index) #include "SerializeProto.h" #undef FIELD #undef TYPE -static std::map SField::codeToField; -static boost::mutex SField::mapMutex; +std::map SField::codeToField; +boost::mutex SField::mapMutex; -SField::ref SField::getField(int code); +SField::ref SField::getField(int code) { int type = code >> 16; int field = code % 0xffff; - if ((type <= 0) || (type >= 256) || (field <= 0) || (field >= 256 + if ((type <= 0) || (type >= 256) || (field <= 0) || (field >= 256)) return sfInvalid; boost::mutex::scoped_lock sl(mapMutex); - std::map it = unknownFieldMap.Find(code); + std::map it = codeToField.find(code); if (it != codeToField.end()) return *(it->second); switch(type) { // types we are willing to dynamically extend -#define FIELD(name, type, index) -#define TYPE(name, type, index) case sf##name: +#define FIELD(name, type, index) case sf##name: +#define TYPE(name, type, index) #include "SerializeProto.h" #undef FIELD #undef TYPE From 6d58bd52b14e0b901190f8cf7a45e5a852a9702a Mon Sep 17 00:00:00 2001 From: JoelKatz Date: Wed, 26 Sep 2012 12:47:42 -0700 Subject: [PATCH 09/53] Missing from SField::ref commit. --- src/LedgerEntrySet.cpp | 4 ++-- 1 file changed, 2 insertions(+), 2 deletions(-) diff --git a/src/LedgerEntrySet.cpp b/src/LedgerEntrySet.cpp index dbb364ebca..682f17d4d9 100644 --- a/src/LedgerEntrySet.cpp +++ b/src/LedgerEntrySet.cpp @@ -877,7 +877,7 @@ uint32 LedgerEntrySet::rippleTransferRate(const uint160& uIssuerID) } // XXX Might not need this, might store in nodes on calc reverse. -uint32 LedgerEntrySet::rippleQualityIn(const uint160& uToAccountID, const uint160& uFromAccountID, const uint160& uCurrencyID, const SOE_Field sfLow, const SOE_Field sfHigh) +uint32 LedgerEntrySet::rippleQualityIn(const uint160& uToAccountID, const uint160& uFromAccountID, const uint160& uCurrencyID, SField::ref sfLow, SField::ref sfHigh) { uint32 uQuality = QUALITY_ONE; SLE::pointer sleRippleState; @@ -892,7 +892,7 @@ uint32 LedgerEntrySet::rippleQualityIn(const uint160& uToAccountID, const uint16 if (sleRippleState) { - SOE_Field sfField = uToAccountID < uFromAccountID ? sfLow: sfHigh; + SField::ref sfField = uToAccountID < uFromAccountID ? sfLow: sfHigh; uQuality = sleRippleState->getIFieldPresent(sfField) ? sleRippleState->getIFieldU32(sfField) From ba77d3e438134e09e22b67abc3bf362e52520c2d Mon Sep 17 00:00:00 2001 From: JoelKatz Date: Wed, 26 Sep 2012 12:47:55 -0700 Subject: [PATCH 10/53] Make it compile. --- src/SerializedObject.cpp | 106 ++++++++++++++++++--------------------- 1 file changed, 49 insertions(+), 57 deletions(-) diff --git a/src/SerializedObject.cpp b/src/SerializedObject.cpp index c5713494d2..d7f360b962 100644 --- a/src/SerializedObject.cpp +++ b/src/SerializedObject.cpp @@ -122,9 +122,9 @@ void STObject::set(SOElement::ptr elem) { mType.push_back(elem); if (elem->flags == SOE_OPTIONAL) - giveObject(makeDefaultObject(STI_NOTPRESENT, elem->e_field)); + giveObject(makeNonPresentObject(elem->e_field)); else - giveObject(makeDefaultObject(elem->e_field.fieldType, elem->e_field)); + giveObject(makeDefaultObject(elem->e_field)); ++elem; } } @@ -257,7 +257,7 @@ bool STObject::isEquivalent(const SerializedType& t) const return (it1 == end1) && (it2 == end2); } -int STObject::getFieldIndex(SOE_Field field) const +int STObject::getFieldIndex(SField::ref field) const { int i = 0; for (std::vector::const_iterator it = mType.begin(), end = mType.end(); it != end; ++it, ++i) @@ -265,7 +265,7 @@ int STObject::getFieldIndex(SOE_Field field) const return -1; } -const SerializedType& STObject::peekAtField(SOE_Field field) const +const SerializedType& STObject::peekAtField(SField::ref field) const { int index = getFieldIndex(field); if (index == -1) @@ -273,7 +273,7 @@ const SerializedType& STObject::peekAtField(SOE_Field field) const return peekAtIndex(index); } -SerializedType& STObject::getField(SOE_Field field) +SerializedType& STObject::getField(SField::ref field) { int index = getFieldIndex(field); if (index == -1) @@ -281,12 +281,12 @@ SerializedType& STObject::getField(SOE_Field field) return getIndex(index); } -SOE_Field STObject::getFieldSType(int index) const +SField::ref STObject::getFieldSType(int index) const { return mType[index]->e_field; } -const SerializedType* STObject::peekAtPField(SOE_Field field) const +const SerializedType* STObject::peekAtPField(SField::ref field) const { int index = getFieldIndex(field); if (index == -1) @@ -294,7 +294,7 @@ const SerializedType* STObject::peekAtPField(SOE_Field field) const return peekAtPIndex(index); } -SerializedType* STObject::getPField(SOE_Field field) +SerializedType* STObject::getPField(SField::ref field) { int index = getFieldIndex(field); if (index == -1) @@ -302,7 +302,7 @@ SerializedType* STObject::getPField(SOE_Field field) return getPIndex(index); } -bool STObject::isFieldPresent(SOE_Field field) const +bool STObject::isFieldPresent(SField::ref field) const { int index = getFieldIndex(field); if (index == -1) @@ -321,7 +321,6 @@ bool STObject::setFlag(uint32 f) bool STObject::clearFlag(uint32 f) { - if (mFlagIdx < 0) return false; STUInt32* t = dynamic_cast(getPField(sfFlags)); if (!t) return false; @@ -331,58 +330,47 @@ bool STObject::clearFlag(uint32 f) uint32 STObject::getFlags(void) const { - const STUInt32* t = dynamic_cast(peekAtPField(mFlagIdx)); + const STUInt32* t = dynamic_cast(peekAtPField(sfFlags)); if (!t) return 0; return t->getValue(); } -SerializedType* STObject::makeFieldPresent(SOE_Field field) +SerializedType* STObject::makeFieldPresent(SField::ref field) { int index = getFieldIndex(field); if (index == -1) throw std::runtime_error("Field not found"); - if ((mType[index]->e_type != SOE_IFFLAG) && (mType[index]->e_type != SOE_IFNFLAG)) - throw std::runtime_error("field is not optional"); SerializedType* f = getPIndex(index); - if (f->getSType() != STI_NOTPRESENT) return f; - mData.replace(index, makeDefaultObject(mType[index]->e_id, mType[index]->e_name)); - f = getPIndex(index); - - if (mType[index]->e_type == SOE_IFFLAG) - setFlag(mType[index]->e_flags); - else if (mType[index]->e_type == SOE_IFNFLAG) - clearFlag(mType[index]->e_flags); - - return f; + if (f->getSType() != STI_NOTPRESENT) + return f; + mData.replace(index, makeDefaultObject(mType[index]->e_field)); + return getPIndex(index); } -void STObject::makeFieldAbsent(SOE_Field field) +void STObject::makeFieldAbsent(SField::ref field) { int index = getFieldIndex(field); if (index == -1) throw std::runtime_error("Field not found"); - if ((mType[index]->e_type != SOE_IFFLAG) && (mType[index]->e_type != SOE_IFNFLAG)) + if (mType[index]->flags != SOE_OPTIONAL) throw std::runtime_error("field is not optional"); - if (peekAtIndex(index).getSType() == STI_NOTPRESENT) return; - mData.replace(index, new SerializedType(mType[index]->e_name)); + if (peekAtIndex(index).getSType() == STI_NOTPRESENT) + return; - if (mType[index]->e_type == SOE_IFFLAG) - clearFlag(mType[index]->e_flags); - else if (mType[index]->e_type == SOE_IFNFLAG) - setFlag(mType[index]->e_flags); + mData.replace(index, makeDefaultObject(mType[index]->e_field)); } -std::string STObject::getFieldString(SOE_Field field) const +std::string STObject::getFieldString(SField::ref field) const { const SerializedType* rf = peekAtPField(field); if (!rf) throw std::runtime_error("Field not found"); return rf->getText(); } -unsigned char STObject::getValueFieldU8(SOE_Field field) const +unsigned char STObject::getValueFieldU8(SField::ref field) const { const SerializedType* rf = peekAtPField(field); if (!rf) throw std::runtime_error("Field not found"); @@ -393,7 +381,7 @@ unsigned char STObject::getValueFieldU8(SOE_Field field) const return cf->getValue(); } -uint16 STObject::getValueFieldU16(SOE_Field field) const +uint16 STObject::getValueFieldU16(SField::ref field) const { const SerializedType* rf = peekAtPField(field); if (!rf) throw std::runtime_error("Field not found"); @@ -404,7 +392,7 @@ uint16 STObject::getValueFieldU16(SOE_Field field) const return cf->getValue(); } -uint32 STObject::getValueFieldU32(SOE_Field field) const +uint32 STObject::getValueFieldU32(SField::ref field) const { const SerializedType* rf = peekAtPField(field); if (!rf) throw std::runtime_error("Field not found"); @@ -415,7 +403,7 @@ uint32 STObject::getValueFieldU32(SOE_Field field) const return cf->getValue(); } -uint64 STObject::getValueFieldU64(SOE_Field field) const +uint64 STObject::getValueFieldU64(SField::ref field) const { const SerializedType* rf = peekAtPField(field); if (!rf) throw std::runtime_error("Field not found"); @@ -426,7 +414,7 @@ uint64 STObject::getValueFieldU64(SOE_Field field) const return cf->getValue(); } -uint128 STObject::getValueFieldH128(SOE_Field field) const +uint128 STObject::getValueFieldH128(SField::ref field) const { const SerializedType* rf = peekAtPField(field); if (!rf) throw std::runtime_error("Field not found"); @@ -437,7 +425,7 @@ uint128 STObject::getValueFieldH128(SOE_Field field) const return cf->getValue(); } -uint160 STObject::getValueFieldH160(SOE_Field field) const +uint160 STObject::getValueFieldH160(SField::ref field) const { const SerializedType* rf = peekAtPField(field); if (!rf) throw std::runtime_error("Field not found"); @@ -448,7 +436,7 @@ uint160 STObject::getValueFieldH160(SOE_Field field) const return cf->getValue(); } -uint256 STObject::getValueFieldH256(SOE_Field field) const +uint256 STObject::getValueFieldH256(SField::ref field) const { const SerializedType* rf = peekAtPField(field); if (!rf) throw std::runtime_error("Field not found"); @@ -459,7 +447,7 @@ uint256 STObject::getValueFieldH256(SOE_Field field) const return cf->getValue(); } -NewcoinAddress STObject::getValueFieldAccount(SOE_Field field) const +NewcoinAddress STObject::getValueFieldAccount(SField::ref field) const { const SerializedType* rf = peekAtPField(field); if (!rf) @@ -477,7 +465,7 @@ NewcoinAddress STObject::getValueFieldAccount(SOE_Field field) const return cf->getValueNCA(); } -std::vector STObject::getValueFieldVL(SOE_Field field) const +std::vector STObject::getValueFieldVL(SField::ref field) const { const SerializedType* rf = peekAtPField(field); if (!rf) throw std::runtime_error("Field not found"); @@ -488,7 +476,7 @@ std::vector STObject::getValueFieldVL(SOE_Field field) const return cf->getValue(); } -STAmount STObject::getValueFieldAmount(SOE_Field field) const +STAmount STObject::getValueFieldAmount(SField::ref field) const { const SerializedType* rf = peekAtPField(field); if (!rf) throw std::runtime_error("Field not found"); @@ -499,7 +487,7 @@ STAmount STObject::getValueFieldAmount(SOE_Field field) const return *cf; } -STPathSet STObject::getValueFieldPathSet(SOE_Field field) const +STPathSet STObject::getValueFieldPathSet(SField::ref field) const { const SerializedType* rf = peekAtPField(field); if (!rf) throw std::runtime_error("Field not found"); @@ -510,7 +498,7 @@ STPathSet STObject::getValueFieldPathSet(SOE_Field field) const return *cf; } -STVector256 STObject::getValueFieldV256(SOE_Field field) const +STVector256 STObject::getValueFieldV256(SField::ref field) const { const SerializedType* rf = peekAtPField(field); if (!rf) throw std::runtime_error("Field not found"); @@ -521,7 +509,7 @@ STVector256 STObject::getValueFieldV256(SOE_Field field) const return *cf; } -void STObject::setValueFieldU8(SOE_Field field, unsigned char v) +void STObject::setValueFieldU8(SField::ref field, unsigned char v) { SerializedType* rf = getPField(field); if (!rf) throw std::runtime_error("Field not found"); @@ -531,7 +519,7 @@ void STObject::setValueFieldU8(SOE_Field field, unsigned char v) cf->setValue(v); } -void STObject::setValueFieldU16(SOE_Field field, uint16 v) +void STObject::setValueFieldU16(SField::ref field, uint16 v) { SerializedType* rf = getPField(field); if (!rf) throw std::runtime_error("Field not found"); @@ -541,7 +529,7 @@ void STObject::setValueFieldU16(SOE_Field field, uint16 v) cf->setValue(v); } -void STObject::setValueFieldU32(SOE_Field field, uint32 v) +void STObject::setValueFieldU32(SField::ref field, uint32 v) { SerializedType* rf = getPField(field); if (!rf) throw std::runtime_error("Field not found"); @@ -551,7 +539,7 @@ void STObject::setValueFieldU32(SOE_Field field, uint32 v) cf->setValue(v); } -void STObject::setValueFieldU64(SOE_Field field, uint64 v) +void STObject::setValueFieldU64(SField::ref field, uint64 v) { SerializedType* rf = getPField(field); if (!rf) throw std::runtime_error("Field not found"); @@ -561,7 +549,7 @@ void STObject::setValueFieldU64(SOE_Field field, uint64 v) cf->setValue(v); } -void STObject::setValueFieldH128(SOE_Field field, const uint128& v) +void STObject::setValueFieldH128(SField::ref field, const uint128& v) { SerializedType* rf = getPField(field); if (!rf) throw std::runtime_error("Field not found"); @@ -571,7 +559,7 @@ void STObject::setValueFieldH128(SOE_Field field, const uint128& v) cf->setValue(v); } -void STObject::setValueFieldH160(SOE_Field field, const uint160& v) +void STObject::setValueFieldH160(SField::ref field, const uint160& v) { SerializedType* rf = getPField(field); if (!rf) throw std::runtime_error("Field not found"); @@ -581,7 +569,7 @@ void STObject::setValueFieldH160(SOE_Field field, const uint160& v) cf->setValue(v); } -void STObject::setValueFieldH256(SOE_Field field, const uint256& v) +void STObject::setValueFieldH256(SField::ref field, const uint256& v) { SerializedType* rf = getPField(field); if (!rf) throw std::runtime_error("Field not found"); @@ -591,7 +579,7 @@ void STObject::setValueFieldH256(SOE_Field field, const uint256& v) cf->setValue(v); } -void STObject::setValueFieldV256(SOE_Field field, const STVector256& v) +void STObject::setValueFieldV256(SField::ref field, const STVector256& v) { SerializedType* rf = getPField(field); if (!rf) throw std::runtime_error("Field not found"); @@ -601,7 +589,7 @@ void STObject::setValueFieldV256(SOE_Field field, const STVector256& v) cf->setValue(v); } -void STObject::setValueFieldAccount(SOE_Field field, const uint160& v) +void STObject::setValueFieldAccount(SField::ref field, const uint160& v) { SerializedType* rf = getPField(field); if (!rf) throw std::runtime_error("Field not found"); @@ -611,7 +599,7 @@ void STObject::setValueFieldAccount(SOE_Field field, const uint160& v) cf->setValueH160(v); } -void STObject::setValueFieldVL(SOE_Field field, const std::vector& v) +void STObject::setValueFieldVL(SField::ref field, const std::vector& v) { SerializedType* rf = getPField(field); if (!rf) throw std::runtime_error("Field not found"); @@ -621,7 +609,7 @@ void STObject::setValueFieldVL(SOE_Field field, const std::vector cf->setValue(v); } -void STObject::setValueFieldAmount(SOE_Field field, const STAmount &v) +void STObject::setValueFieldAmount(SField::ref field, const STAmount &v) { SerializedType* rf = getPField(field); if (!rf) throw std::runtime_error("Field not found"); @@ -631,7 +619,7 @@ void STObject::setValueFieldAmount(SOE_Field field, const STAmount &v) (*cf) = v; } -void STObject::setValueFieldPathSet(SOE_Field field, const STPathSet &v) +void STObject::setValueFieldPathSet(SField::ref field, const STPathSet &v) { SerializedType* rf = getPField(field); if (!rf) throw std::runtime_error("Field not found"); @@ -667,6 +655,8 @@ Json::Value STVector256::getJson(int options) const return ret; } +#if 0 + static SOElement testSOElements[2][16] = { // field, name, id, type, flags { @@ -726,4 +716,6 @@ void STObject::unitTest() } +#endif + // vim:ts=4 From c10ff5bac9b67ddf5549fce7e1a31c93b7454877 Mon Sep 17 00:00:00 2001 From: JoelKatz Date: Wed, 26 Sep 2012 14:22:04 -0700 Subject: [PATCH 11/53] More serialization rework. --- src/Amount.cpp | 18 +++++++++--------- src/FieldNames.cpp | 12 ++++++------ src/FieldNames.h | 4 ++-- src/SerializedTypes.h | 6 +++--- 4 files changed, 20 insertions(+), 20 deletions(-) diff --git a/src/Amount.cpp b/src/Amount.cpp index 7af2d28e71..9b45507502 100644 --- a/src/Amount.cpp +++ b/src/Amount.cpp @@ -519,7 +519,7 @@ STAmount& STAmount::operator-=(const STAmount& a) STAmount STAmount::operator-(void) const { if (mValue == 0) return *this; - return STAmount(fName, mCurrency, mIssuer, mValue, mOffset, mIsNative, !mIsNegative); + return STAmount(getFName(), mCurrency, mIssuer, mValue, mOffset, mIsNative, !mIsNegative); } STAmount& STAmount::operator=(uint64 v) @@ -572,12 +572,12 @@ bool STAmount::operator>=(uint64 v) const STAmount STAmount::operator+(uint64 v) const { - return STAmount(fName, getSNValue() + static_cast(v)); + return STAmount(getFName(), getSNValue() + static_cast(v)); } STAmount STAmount::operator-(uint64 v) const { - return STAmount(fName, getSNValue() - static_cast(v)); + return STAmount(getFName(), getSNValue() - static_cast(v)); } STAmount::operator double() const @@ -595,7 +595,7 @@ STAmount operator+(const STAmount& v1, const STAmount& v2) v1.throwComparable(v2); if (v1.mIsNative) - return STAmount(v1.fName, v1.getSNValue() + v2.getSNValue()); + return STAmount(v1.getFName(), v1.getSNValue() + v2.getSNValue()); int ov1 = v1.mOffset, ov2 = v2.mOffset; @@ -617,9 +617,9 @@ STAmount operator+(const STAmount& v1, const STAmount& v2) int64 fv = vv1 + vv2; if (fv >= 0) - return STAmount(v1.fName, v1.mCurrency, v1.mIssuer, fv, ov1, false); + return STAmount(v1.getFName(), v1.mCurrency, v1.mIssuer, fv, ov1, false); else - return STAmount(v1.fName, v1.mCurrency, v1.mIssuer, -fv, ov1, true); + return STAmount(v1.getFName(), v1.mCurrency, v1.mIssuer, -fv, ov1, true); } STAmount operator-(const STAmount& v1, const STAmount& v2) @@ -649,9 +649,9 @@ STAmount operator-(const STAmount& v1, const STAmount& v2) int64 fv = vv1 - vv2; if (fv >= 0) - return STAmount(v1.fName, v1.mCurrency, v1.mIssuer, fv, ov1, false); + return STAmount(v1.getFName(), v1.mCurrency, v1.mIssuer, fv, ov1, false); else - return STAmount(v1.fName, v1.mCurrency, v1.mIssuer, -fv, ov1, true); + return STAmount(v1.getFName(), v1.mCurrency, v1.mIssuer, -fv, ov1, true); } STAmount STAmount::divide(const STAmount& num, const STAmount& den, const uint160& uCurrencyID, const uint160& uIssuerID) @@ -703,7 +703,7 @@ STAmount STAmount::multiply(const STAmount& v1, const STAmount& v2, const uint16 return STAmount(uCurrencyID, uIssuerID); if (v1.mIsNative && v2.mIsNative) // FIXME: overflow - return STAmount(v1.fName, v1.getSNValue() * v2.getSNValue()); + return STAmount(v1.getFName(), v1.getSNValue() * v2.getSNValue()); uint64 value1 = v1.mValue, value2 = v2.mValue; int offset1 = v1.mOffset, offset2 = v2.mOffset; diff --git a/src/FieldNames.cpp b/src/FieldNames.cpp index 483694c2d2..316410ffb6 100644 --- a/src/FieldNames.cpp +++ b/src/FieldNames.cpp @@ -15,7 +15,7 @@ SField sfInvalid(-1), sfGeneric(0); #undef FIELD #undef TYPE -std::map SField::codeToField; +std::map SField::codeToField; boost::mutex SField::mapMutex; SField::ref SField::getField(int code) @@ -28,15 +28,15 @@ SField::ref SField::getField(int code) boost::mutex::scoped_lock sl(mapMutex); - std::map it = codeToField.find(code); + std::map::iterator it = codeToField.find(code); if (it != codeToField.end()) return *(it->second); - switch(type) + switch (type) { // types we are willing to dynamically extend -#define FIELD(name, type, index) case sf##name: -#define TYPE(name, type, index) +#define FIELD(name, type, index) +#define TYPE(name, type, index) case STI_##type: #include "SerializeProto.h" #undef FIELD #undef TYPE @@ -68,7 +68,7 @@ SField::ref SField::getField(int type, int value) return getField(FIELD_CODE(type, value)); } -std::string SField::getName() cosnt +std::string SField::getName() const { if (fieldName != NULL) return fieldName; diff --git a/src/FieldNames.h b/src/FieldNames.h index cd035f1330..cfcb649f06 100644 --- a/src/FieldNames.h +++ b/src/FieldNames.h @@ -40,8 +40,8 @@ public: typedef SField const * ptr; protected: - static std::map codeToField; - static boost::mutex mapMutex; + static std::map codeToField; + static boost::mutex mapMutex; public: diff --git a/src/SerializedTypes.h b/src/SerializedTypes.h index 64dae0d73b..5df8b6fada 100644 --- a/src/SerializedTypes.h +++ b/src/SerializedTypes.h @@ -218,11 +218,11 @@ protected: STAmount(bool isNeg, uint64 value) : mValue(value), mOffset(0), mIsNative(true), mIsNegative(isNeg) { ; } - STAmount(SField *name, uint64 value, bool isNegative) + STAmount(SField::ref name, uint64 value, bool isNegative) : SerializedType(fName), mValue(value), mOffset(0), mIsNative(true), mIsNegative(isNegative) { ; } - STAmount(SField *n, const uint160& cur, const uint160& iss, uint64 val, int off, bool isNat, bool isNeg) - : SerializedType(n), mCurrency(cur), mIssuer(iss), mValue(val), mOffset(off), + STAmount(SField::ref name, const uint160& cur, const uint160& iss, uint64 val, int off, bool isNat, bool isNeg) + : SerializedType(name), mCurrency(cur), mIssuer(iss), mValue(val), mOffset(off), mIsNative(isNat), mIsNegative(isNeg) { ; } uint64 toUInt64() const; From 632d506234dcf9b661fa9581d687b8fa81dcff15 Mon Sep 17 00:00:00 2001 From: JoelKatz Date: Wed, 26 Sep 2012 15:08:43 -0700 Subject: [PATCH 12/53] Make this compile. --- src/Amount.cpp | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/src/Amount.cpp b/src/Amount.cpp index 9b45507502..793e71c250 100644 --- a/src/Amount.cpp +++ b/src/Amount.cpp @@ -889,7 +889,7 @@ STAmount STAmount::convertToInternalAmount(uint64 displayAmount, uint64 totalNow STAmount STAmount::deserialize(SerializerIterator& it) { - STAmount *s = construct(it); + STAmount *s = construct(it, sfGeneric); STAmount ret(*s); delete s; From 16cadaf43f0cf47fc6f3e1a31a755fc710387496 Mon Sep 17 00:00:00 2001 From: JoelKatz Date: Wed, 26 Sep 2012 15:09:00 -0700 Subject: [PATCH 13/53] Special types of high-level objects. --- src/FieldNames.cpp | 3 +++ src/FieldNames.h | 8 ++++---- 2 files changed, 7 insertions(+), 4 deletions(-) diff --git a/src/FieldNames.cpp b/src/FieldNames.cpp index 316410ffb6..98ba23616e 100644 --- a/src/FieldNames.cpp +++ b/src/FieldNames.cpp @@ -8,6 +8,9 @@ SField sfInvalid(-1), sfGeneric(0); +SField sfLedgerEntry(FIELD_CODE(STI_LEDGERENTRY, 1), STI_LEDGERENTRY, 1, "LedgerEntry"); +SField sfTransaction(FIELD_CODE(STI_TRANSACTION, 1), STI_TRANSACTION, 1, "Transaction"); +SField sfValidation(FIELD_CODE(STI_VALIDATION, 1), STI_VALIDATION, 1, "Validation"); #define FIELD(name, type, index) SField sf##name(FIELD_CODE(STI_##type, index), STI_##type, index, #name); #define TYPE(name, type, index) diff --git a/src/FieldNames.h b/src/FieldNames.h index cfcb649f06..8dbbb0bcd4 100644 --- a/src/FieldNames.h +++ b/src/FieldNames.h @@ -21,9 +21,9 @@ enum SerializedTypeID #undef FIELD // high level types - STI_TRANSACTION = 100001, - STI_LEDGERENTRY = 100002, - STI_VALIDATION = 100003, + STI_TRANSACTION = 10001, + STI_LEDGERENTRY = 10002, + STI_VALIDATION = 10003, }; enum SOE_Flags @@ -73,7 +73,7 @@ public: static int compare(SField::ref f1, SField::ref f2); }; -extern SField sfInvalid, sfGeneric; +extern SField sfInvalid, sfGeneric, sfLedgerEntry, sfTransaction; #define FIELD(name, type, index) extern SField sf##name; #define TYPE(name, type, index) From d76f61a648081fdd8205f68e069380ddd2cb42da Mon Sep 17 00:00:00 2001 From: JoelKatz Date: Wed, 26 Sep 2012 15:09:11 -0700 Subject: [PATCH 14/53] Cleanups. --- src/SerializeProto.h | 21 ++++++++++++--------- 1 file changed, 12 insertions(+), 9 deletions(-) diff --git a/src/SerializeProto.h b/src/SerializeProto.h index bf60039fb8..7aca88d086 100644 --- a/src/SerializeProto.h +++ b/src/SerializeProto.h @@ -2,11 +2,11 @@ // appropriate #define statements. // types (common) - TYPE("Int32", UINT32, 1) - TYPE("Int64", UINT64, 2) - TYPE("Hash128", HASH128, 3) - TYPE("Hash256", HASH256, 4) - // 5 is reserved + TYPE("Int16", UINT16, 1) + TYPE("Int32", UINT32, 2) + TYPE("Int64", UINT64, 3) + TYPE("Hash128", HASH128, 4) + TYPE("Hash256", HASH256, 5) TYPE("Amount", AMOUNT, 6) TYPE("VariableLength", VL, 7) TYPE("Account", ACCOUNT, 8) @@ -16,16 +16,19 @@ // types (uncommon) TYPE("Int8", UINT8, 16) - TYPE("Int16", UINT16, 17) - TYPE("Hash160", HASH160, 18) - TYPE("PathSet", PATHSET, 19) - TYPE("Vector256", VECTOR256, 20) + TYPE("Hash160", HASH160, 17) + TYPE("PathSet", PATHSET, 18) + TYPE("Vector256", VECTOR256, 19) // 8-bit integers FIELD(CloseResolution, UINT8, 1) + // 16-bit integers + FIELD(LedgerEntryType, UINT16, 1) + FIELD(TransactionType, UINT16, 1) + // 32-bit integers (common) FIELD(ObjectType, UINT32, 1) FIELD(Flags, UINT32, 2) From ad4952b9587d5559892dfffdb9abb054b211991a Mon Sep 17 00:00:00 2001 From: JoelKatz Date: Wed, 26 Sep 2012 15:09:27 -0700 Subject: [PATCH 15/53] Cleanups. --- src/SerializedObject.cpp | 4 +--- src/SerializedObject.h | 6 +++--- 2 files changed, 4 insertions(+), 6 deletions(-) diff --git a/src/SerializedObject.cpp b/src/SerializedObject.cpp index d7f360b962..ef700db52e 100644 --- a/src/SerializedObject.cpp +++ b/src/SerializedObject.cpp @@ -169,10 +169,8 @@ bool STObject::isFieldAllowed(SField::ref field) return false; } -bool STObject::set(SOElement::ptrList elem, SerializerIterator& sit, int depth) +bool STObject::set(SerializerIterator& sit, int depth) { // return true = terminated with end-of-object - setType(elem); - mData.empty(); while (!sit.empty()) { diff --git a/src/SerializedObject.h b/src/SerializedObject.h index 58914bfb78..fdc9030e92 100644 --- a/src/SerializedObject.h +++ b/src/SerializedObject.h @@ -39,19 +39,19 @@ public: { set(type); } STObject(SOElement::ptrList type, SerializerIterator& sit, SField::ref name) : SerializedType(name) - { set(type, sit); } + { set(sit); setType(type); } virtual ~STObject() { ; } static std::auto_ptr deserialize(SerializerIterator& sit, SField::ref name) { return std::auto_ptr(construct(sit, name)); } - void setType(SOElement const * t); + void setType(SOElement::ptrList); bool isValidForType(); bool isFieldAllowed(SField::ref); void set(SOElement::ptrList); - bool set(SOElement::ptrList, SerializerIterator& u, int depth = 0); + bool set(SerializerIterator& u, int depth = 0); virtual SerializedTypeID getSType() const { return STI_OBJECT; } virtual bool isEquivalent(const SerializedType& t) const; From 9c08dc00ae379bf3c0b721a40df0f003ef3f4565 Mon Sep 17 00:00:00 2001 From: JoelKatz Date: Wed, 26 Sep 2012 15:09:38 -0700 Subject: [PATCH 16/53] Mark a huge number of ugly functions deprecated. You no longer need to use the special 'IField' functions. You can treat a ledger entry like any STObject. --- src/SerializedLedger.h | 88 ++++++++++++++++++++---------------------- 1 file changed, 41 insertions(+), 47 deletions(-) diff --git a/src/SerializedLedger.h b/src/SerializedLedger.h index 813e4dccb9..0b9cb1c17b 100644 --- a/src/SerializedLedger.h +++ b/src/SerializedLedger.h @@ -5,7 +5,7 @@ #include "LedgerFormats.h" #include "NewcoinAddress.h" -class SerializedLedgerEntry : public SerializedType +class SerializedLedgerEntry : public STObject { public: typedef boost::shared_ptr pointer; @@ -14,8 +14,6 @@ public: protected: uint256 mIndex; LedgerEntryType mType; - STUInt16 mVersion; - STObject mObject; const LedgerEntryFormat* mFormat; SerializedLedgerEntry* duplicate() const { return new SerializedLedgerEntry(*this); } @@ -29,40 +27,15 @@ public: std::string getFullText() const; std::string getText() const; Json::Value getJson(int options) const; - void add(Serializer& s) const { mVersion.add(s); mObject.add(s); } virtual bool isEquivalent(const SerializedType& t) const; - bool setFlag(uint32 uSet) { return mObject.setFlag(uSet); } - bool clearFlag(uint32 uClear) { return mObject.clearFlag(uClear); } - uint32 getFlags() const { return mObject.getFlags(); } - - const uint256& getIndex() const { return mIndex; } - void setIndex(const uint256& i) { mIndex = i; } + const uint256& getIndex() const; + void setIndex(const uint256& i); LedgerEntryType getType() const { return mType; } - uint16 getVersion() const { return mVersion.getValue(); } + uint16 getVersion() const { return getValueFieldU16(sfLedgerEntryType); } const LedgerEntryFormat* getFormat() { return mFormat; } - int getIFieldIndex(SField::ref field) const { return mObject.getFieldIndex(field); } - int getIFieldCount() const { return mObject.getCount(); } - const SerializedType& peekIField(SField::ref field) const { return mObject.peekAtField(field); } - SerializedType& getIField(SField::ref field) { return mObject.getField(field); } - SField::ref getIFieldSType(int index) { return mObject.getFieldSType(index); } - - std::string getIFieldString(SField::ref field) const { return mObject.getFieldString(field); } - unsigned char getIFieldU8(SField::ref field) const { return mObject.getValueFieldU8(field); } - uint16 getIFieldU16(SField::ref field) const { return mObject.getValueFieldU16(field); } - uint32 getIFieldU32(SField::ref field) const { return mObject.getValueFieldU32(field); } - uint64 getIFieldU64(SField::ref field) const { return mObject.getValueFieldU64(field); } - uint128 getIFieldH128(SField::ref field) const { return mObject.getValueFieldH128(field); } - uint160 getIFieldH160(SField::ref field) const { return mObject.getValueFieldH160(field); } - uint256 getIFieldH256(SField::ref field) const { return mObject.getValueFieldH256(field); } - std::vector getIFieldVL(SField::ref field) const { return mObject.getValueFieldVL(field); } - std::vector getIFieldTL(SField::ref field) const { return mObject.getValueFieldTL(field); } - NewcoinAddress getIValueFieldAccount(SField::ref field) const { return mObject.getValueFieldAccount(field); } - STAmount getIValueFieldAmount(SField::ref field) const { return mObject.getValueFieldAmount(field); } - STVector256 getIFieldV256(SField::ref field) { return mObject.getValueFieldV256(field); } - bool isThreadedType(); // is this a ledger entry that can be threaded bool isThreaded(); // is this ledger entry actually threaded bool hasOneOwner(); // This node has one other node that owns it (like nickname) @@ -75,28 +48,49 @@ public: bool thread(const uint256& txID, uint32 ledgerSeq, uint256& prevTxID, uint32& prevLedgerID); std::vector getOwners(); // nodes notified if this node is deleted - void setIFieldU8(SField::ref field, unsigned char v) { return mObject.setValueFieldU8(field, v); } - void setIFieldU16(SField::ref field, uint16 v) { return mObject.setValueFieldU16(field, v); } - void setIFieldU32(SField::ref field, uint32 v) { return mObject.setValueFieldU32(field, v); } - void setIFieldU64(SField::ref field, uint64 v) { return mObject.setValueFieldU64(field, v); } - void setIFieldH128(SField::ref field, const uint128& v) { return mObject.setValueFieldH128(field, v); } - void setIFieldH160(SField::ref field, const uint160& v) { return mObject.setValueFieldH160(field, v); } - void setIFieldH256(SField::ref field, const uint256& v) { return mObject.setValueFieldH256(field, v); } + // CAUTION: All these functions are now obsolete and will be removed after + // the new serialization code is merged. + int getIFieldIndex(SField::ref field) const { return getFieldIndex(field); } + int getIFieldCount() const { return getCount(); } + const SerializedType& peekIField(SField::ref field) const { return peekAtField(field); } + SerializedType& getIField(SField::ref field) { return getField(field); } + SField::ref getIFieldSType(int index) { return getFieldSType(index); } + std::string getIFieldString(SField::ref field) const { return getFieldString(field); } + unsigned char getIFieldU8(SField::ref field) const { return getValueFieldU8(field); } + uint16 getIFieldU16(SField::ref field) const { return getValueFieldU16(field); } + uint32 getIFieldU32(SField::ref field) const { return getValueFieldU32(field); } + uint64 getIFieldU64(SField::ref field) const { return getValueFieldU64(field); } + uint128 getIFieldH128(SField::ref field) const { return getValueFieldH128(field); } + uint160 getIFieldH160(SField::ref field) const { return getValueFieldH160(field); } + uint256 getIFieldH256(SField::ref field) const { return getValueFieldH256(field); } + std::vector getIFieldVL(SField::ref field) const { return getValueFieldVL(field); } + std::vector getIFieldTL(SField::ref field) const { return getValueFieldTL(field); } + NewcoinAddress getIValueFieldAccount(SField::ref field) const { return getValueFieldAccount(field); } + STAmount getIValueFieldAmount(SField::ref field) const { return getValueFieldAmount(field); } + STVector256 getIFieldV256(SField::ref field) { return getValueFieldV256(field); } + void setIFieldU8(SField::ref field, unsigned char v) { return setValueFieldU8(field, v); } + void setIFieldU16(SField::ref field, uint16 v) { return setValueFieldU16(field, v); } + void setIFieldU32(SField::ref field, uint32 v) { return setValueFieldU32(field, v); } + void setIFieldU64(SField::ref field, uint64 v) { return setValueFieldU64(field, v); } + void setIFieldH128(SField::ref field, const uint128& v) { return setValueFieldH128(field, v); } + void setIFieldH160(SField::ref field, const uint160& v) { return setValueFieldH160(field, v); } + void setIFieldH256(SField::ref field, const uint256& v) { return setValueFieldH256(field, v); } void setIFieldVL(SField::ref field, const std::vector& v) - { return mObject.setValueFieldVL(field, v); } + { return setValueFieldVL(field, v); } void setIFieldTL(SField::ref field, const std::vector& v) - { return mObject.setValueFieldTL(field, v); } + { return setValueFieldTL(field, v); } void setIFieldAccount(SField::ref field, const uint160& account) - { return mObject.setValueFieldAccount(field, account); } + { return setValueFieldAccount(field, account); } void setIFieldAccount(SField::ref field, const NewcoinAddress& account) - { return mObject.setValueFieldAccount(field, account); } + { return setValueFieldAccount(field, account); } void setIFieldAmount(SField::ref field, const STAmount& amount) - { return mObject.setValueFieldAmount(field, amount); } - void setIFieldV256(SField::ref field, const STVector256& v) { return mObject.setValueFieldV256(field, v); } + { return setValueFieldAmount(field, amount); } + void setIFieldV256(SField::ref field, const STVector256& v) { return setValueFieldV256(field, v); } + bool getIFieldPresent(SField::ref field) const { return isFieldPresent(field); } + void makeIFieldPresent(SField::ref field) { makeFieldPresent(field); } + void makeIFieldAbsent(SField::ref field) { return makeFieldAbsent(field); } + // CAUTION: All the above functions are obsolete - bool getIFieldPresent(SField::ref field) const { return mObject.isFieldPresent(field); } - void makeIFieldPresent(SField::ref field) { mObject.makeFieldPresent(field); } - void makeIFieldAbsent(SField::ref field) { return mObject.makeFieldAbsent(field); } }; typedef SerializedLedgerEntry SLE; From 3f469c914d42db61dbf89131ad7d72b40dc77c97 Mon Sep 17 00:00:00 2001 From: JoelKatz Date: Wed, 26 Sep 2012 16:26:39 -0700 Subject: [PATCH 17/53] More serialization work. --- src/FieldNames.h | 2 +- src/SerializeProto.h | 5 ++- src/SerializedLedger.cpp | 70 +++++++++++++++-------------------- src/SerializedLedger.h | 1 - src/SerializedTransaction.cpp | 10 ++--- src/SerializedValidation.cpp | 18 +++++---- 6 files changed, 50 insertions(+), 56 deletions(-) diff --git a/src/FieldNames.h b/src/FieldNames.h index 8dbbb0bcd4..c738e6cefa 100644 --- a/src/FieldNames.h +++ b/src/FieldNames.h @@ -73,7 +73,7 @@ public: static int compare(SField::ref f1, SField::ref f2); }; -extern SField sfInvalid, sfGeneric, sfLedgerEntry, sfTransaction; +extern SField sfInvalid, sfGeneric, sfLedgerEntry, sfTransaction, sfValidation; #define FIELD(name, type, index) extern SField sf##name; #define TYPE(name, type, index) diff --git a/src/SerializeProto.h b/src/SerializeProto.h index 7aca88d086..eeef22f132 100644 --- a/src/SerializeProto.h +++ b/src/SerializeProto.h @@ -71,8 +71,9 @@ FIELD(TransactionHash, HASH256, 3) FIELD(AccountHash, HASH256, 4) FIELD(LastTxnID, HASH256, 5) - FIELD(WalletLocator, HASH256, 6) - FIELD(PublishHash, HASH256, 7) + FIELD(LedgerIndex, HASH256, 6) + FIELD(WalletLocator, HASH256, 7) + FIELD(PublishHash, HASH256, 8) // 256-bit (uncommon) FIELD(BookDirectory, HASH256, 16) diff --git a/src/SerializedLedger.cpp b/src/SerializedLedger.cpp index 0353df8b69..1d26049883 100644 --- a/src/SerializedLedger.cpp +++ b/src/SerializedLedger.cpp @@ -6,27 +6,29 @@ #include "Log.h" SerializedLedgerEntry::SerializedLedgerEntry(SerializerIterator& sit, const uint256& index) - : SerializedType("LedgerEntry"), mIndex(index) + : STObject(sfLedgerEntry), mIndex(index) { - uint16 type = sit.get16(); + set(sit); + uint16 type = getValueFieldU16(sfLedgerEntryType); mFormat = getLgrFormat(static_cast(type)); - if (mFormat == NULL) throw std::runtime_error("invalid ledger entry type"); + if (mFormat == NULL) + throw std::runtime_error("invalid ledger entry type"); mType = mFormat->t_type; - mVersion.setValue(type); - mObject = STObject(mFormat->elements, sit); + setType(mType); } SerializedLedgerEntry::SerializedLedgerEntry(const Serializer& s, const uint256& index) - : SerializedType("LedgerEntry"), mIndex(index) + : STObject(sfLedgerEntry), mIndex(index) { SerializerIterator sit(s); + set(sit); - uint16 type = sit.get16(); + uint16 type = getValueFieldU16(sfLedgerEntryType); mFormat = getLgrFormat(static_cast(type)); - if (mFormat == NULL) throw std::runtime_error("invalid ledger entry type"); + if (mFormat == NULL) + throw std::runtime_error("invalid ledger entry type"); mType = mFormat->t_type; - mVersion.setValue(type); - mObject.set(mFormat->elements, sit); + setType(mTyhpe); } SerializedLedgerEntry::SerializedLedgerEntry(LedgerEntryType type) : SerializedType("LedgerEntry"), mType(type) @@ -34,7 +36,7 @@ SerializedLedgerEntry::SerializedLedgerEntry(LedgerEntryType type) : SerializedT mFormat = getLgrFormat(type); if (mFormat == NULL) throw std::runtime_error("invalid ledger entry type"); mVersion.setValue(static_cast(mFormat->t_type)); - mObject.set(mFormat->elements); + set(mFormat->elements); } std::string SerializedLedgerEntry::getFullText() const @@ -44,7 +46,7 @@ std::string SerializedLedgerEntry::getFullText() const ret += "\" = { "; ret += mFormat->t_name; ret += ", "; - ret += mObject.getFullText(); + ret += getFullText(); ret += "}"; return ret; } @@ -53,67 +55,55 @@ std::string SerializedLedgerEntry::getText() const { return str(boost::format("{ %s, %s, %s }") % mIndex.GetHex() - % mVersion.getText() - % mObject.getText()); + % STObject::getText()); } Json::Value SerializedLedgerEntry::getJson(int options) const { - Json::Value ret(mObject.getJson(options)); + Json::Value ret(SerializedObject::getJson(options)); - ret["type"] = mFormat->t_name; ret["index"] = mIndex.GetHex(); - ret["version"] = std::string(1, mVersion); return ret; } -bool SerializedLedgerEntry::isEquivalent(const SerializedType& t) const -{ // locators are not compared - const SerializedLedgerEntry* v = dynamic_cast(&t); - if (!v) return false; - if (mType != v->mType) return false; - if (mObject != v->mObject) return false; - return true; -} - bool SerializedLedgerEntry::isThreadedType() { - return getIFieldIndex(sfLastTxnID) != -1; + return getFieldIndex(sfLastTxnID) != -1; } bool SerializedLedgerEntry::isThreaded() { - return getIFieldPresent(sfLastTxnID); + return isFieldPresent(sfLastTxnID); } uint256 SerializedLedgerEntry::getThreadedTransaction() { - return getIFieldH256(sfLastTxnID); + return getValueFieldH256(sfLastTxnID); } uint32 SerializedLedgerEntry::getThreadedLedger() { - return getIFieldU32(sfLastTxnSeq); + return getValueFieldU32(sfLastTxnSeq); } bool SerializedLedgerEntry::thread(const uint256& txID, uint32 ledgerSeq, uint256& prevTxID, uint32& prevLedgerID) { - uint256 oldPrevTxID = getIFieldH256(sfLastTxnID); + uint256 oldPrevTxID = getValueFieldH256(sfLastTxnID); Log(lsTRACE) << "Thread Tx:" << txID << " prev:" << oldPrevTxID; if (oldPrevTxID == txID) return false; prevTxID = oldPrevTxID; - prevLedgerID = getIFieldU32(sfLastTxnSeq); + prevLedgerID = getValueFieldU32(sfLastTxnSeq); assert(prevTxID != txID); - setIFieldH256(sfLastTxnID, txID); - setIFieldU32(sfLastTxnSeq, ledgerSeq); + setFieldH256(sfLastTxnID, txID); + setFieldU32(sfLastTxnSeq, ledgerSeq); return true; } bool SerializedLedgerEntry::hasOneOwner() { - return (mType != ltACCOUNT_ROOT) && (getIFieldIndex(sfAccount) != -1); + return (mType != ltACCOUNT_ROOT) && (getFieldIndex(sfAccount) != -1); } bool SerializedLedgerEntry::hasTwoOwners() @@ -123,17 +113,17 @@ bool SerializedLedgerEntry::hasTwoOwners() NewcoinAddress SerializedLedgerEntry::getOwner() { - return getIValueFieldAccount(sfAccount); + return getValueFieldAccount(sfAccount); } NewcoinAddress SerializedLedgerEntry::getFirstOwner() { - return getIValueFieldAccount(sfLowID); + return getValueFieldAccount(sfLowID); } NewcoinAddress SerializedLedgerEntry::getSecondOwner() { - return getIValueFieldAccount(sfHighID); + return getValueFieldAccount(sfHighID); } std::vector SerializedLedgerEntry::getOwners() @@ -141,9 +131,9 @@ std::vector SerializedLedgerEntry::getOwners() std::vector owners; uint160 account; - for (int i = 0, fields = getIFieldCount(); i < fields; ++i) + for (int i = 0, fields = getCount(); i < fields; ++i) { - switch (getIFieldSType(i)) + switch (getFieldSType(i)) { case sfAccount: case sfLowID: diff --git a/src/SerializedLedger.h b/src/SerializedLedger.h index 0b9cb1c17b..7468da4d02 100644 --- a/src/SerializedLedger.h +++ b/src/SerializedLedger.h @@ -27,7 +27,6 @@ public: std::string getFullText() const; std::string getText() const; Json::Value getJson(int options) const; - virtual bool isEquivalent(const SerializedType& t) const; const uint256& getIndex() const; void setIndex(const uint256& i); diff --git a/src/SerializedTransaction.cpp b/src/SerializedTransaction.cpp index 0ee218028c..87db2afc0b 100644 --- a/src/SerializedTransaction.cpp +++ b/src/SerializedTransaction.cpp @@ -12,11 +12,11 @@ SerializedTransaction::SerializedTransaction(TransactionType type) : mType(type) mFormat = getTxnFormat(type); if (mFormat == NULL) throw std::runtime_error("invalid transaction type"); - mMiddleTxn.giveObject(new STVariableLength("SigningPubKey")); - mMiddleTxn.giveObject(new STAccount("SourceAccount")); - mMiddleTxn.giveObject(new STUInt32("Sequence")); - mMiddleTxn.giveObject(new STUInt16("Type", static_cast(type))); - mMiddleTxn.giveObject(new STAmount("Fee")); + mMiddleTxn.giveObject(new STVariableLength(sfSigningPubKey)); + mMiddleTxn.giveObject(new STAccount(sfSourceAccount)); + mMiddleTxn.giveObject(new STUInt32(sfSequence)); + mMiddleTxn.giveObject(new STUInt16(sfTransactionType, static_cast(type))); + mMiddleTxn.giveObject(new STAmount(sfFee)); mInnerTxn = STObject(mFormat->elements, "InnerTransaction"); } diff --git a/src/SerializedValidation.cpp b/src/SerializedValidation.cpp index 9ae32c31bb..6eedadb94b 100644 --- a/src/SerializedValidation.cpp +++ b/src/SerializedValidation.cpp @@ -4,24 +4,28 @@ #include "HashPrefixes.h" SOElement SerializedValidation::sValidationFormat[] = { - { sfFlags, "Flags", STI_UINT32, SOE_FLAGS, 0 }, - { sfLedgerHash, "LedgerHash", STI_HASH256, SOE_REQUIRED, 0 }, - { sfSigningTime, "SignTime", STI_UINT32, SOE_REQUIRED, 0 }, - { sfSigningKey, "SigningKey", STI_VL, SOE_REQUIRED, 0 }, - { sfInvalid, NULL, STI_DONE, SOE_NEVER, -1 }, + { sfFlags, SOE_REQUIRED }, + { sfLedgerHash, SOE_REQUIRED }, + { sfLedgerSequence, SOE_OPTIONAL }, + { sfCloseTime, SOE_OPTIONAL }, + { sfLoadFee, SOE_OPTIONAL }, + { sfBaseFee, SOE_OPTIONAL }, + { sfSigningTime, SOE_REQUIRED }, + { sfSigningKey, SOE_REQUIRED }, + { sfInvalid, SOE_END } }; const uint32 SerializedValidation::sFullFlag = 0x00010000; SerializedValidation::SerializedValidation(SerializerIterator& sit, bool checkSignature) - : STObject(sValidationFormat, sit), mSignature(sit, "Signature"), mTrusted(false) + : STObject(sValidationFormat, sit, sfValidation), mSignature(sit, sfSignature), mTrusted(false) { if (checkSignature && !isValid()) throw std::runtime_error("Invalid validation"); } SerializedValidation::SerializedValidation(const uint256& ledgerHash, uint32 signTime, const NewcoinAddress& naSeed, bool isFull) - : STObject(sValidationFormat), mSignature("Signature"), mTrusted(false) + : STObject(sValidationFormat, sfValidation), mSignature(sfSignature), mTrusted(false) { setValueFieldH256(sfLedgerHash, ledgerHash); setValueFieldU32(sfSigningTime, signTime); From c9b8408d0867a7f60edf9cb7c28013aab5af8eaf Mon Sep 17 00:00:00 2001 From: JoelKatz Date: Wed, 26 Sep 2012 20:40:23 -0700 Subject: [PATCH 18/53] Cleanups and fixes. --- src/SerializeProto.h | 11 ++++++----- src/SerializedLedger.cpp | 27 ++++++++++----------------- src/SerializedTransaction.cpp | 25 ++++++++++--------------- 3 files changed, 26 insertions(+), 37 deletions(-) diff --git a/src/SerializeProto.h b/src/SerializeProto.h index eeef22f132..225cb85dac 100644 --- a/src/SerializeProto.h +++ b/src/SerializeProto.h @@ -56,11 +56,12 @@ FIELD(OfferSequence, UINT32, 25) // 64-bit integers - FIELD(IndexNext, UINT64, 1) - FIELD(IndexPrevious, UINT64, 2) - FIELD(BookNode, UINT64, 3) - FIELD(OwnerNode, UINT64, 4) - FIELD(BaseFee, UINT64, 5) + FIELD(Fee, UINT64, 1) + FIELD(IndexNext, UINT64, 2) + FIELD(IndexPrevious, UINT64, 3) + FIELD(BookNode, UINT64, 4) + FIELD(OwnerNode, UINT64, 5) + FIELD(BaseFee, UINT64, 6) // 128-bit FIELD(EmailHash, HASH128, 2) diff --git a/src/SerializedLedger.cpp b/src/SerializedLedger.cpp index 1d26049883..824f77145b 100644 --- a/src/SerializedLedger.cpp +++ b/src/SerializedLedger.cpp @@ -14,7 +14,7 @@ SerializedLedgerEntry::SerializedLedgerEntry(SerializerIterator& sit, const uint if (mFormat == NULL) throw std::runtime_error("invalid ledger entry type"); mType = mFormat->t_type; - setType(mType); + setType(mFormat->elements); } SerializedLedgerEntry::SerializedLedgerEntry(const Serializer& s, const uint256& index) @@ -28,15 +28,15 @@ SerializedLedgerEntry::SerializedLedgerEntry(const Serializer& s, const uint256& if (mFormat == NULL) throw std::runtime_error("invalid ledger entry type"); mType = mFormat->t_type; - setType(mTyhpe); + setType(mFormat->elements); } -SerializedLedgerEntry::SerializedLedgerEntry(LedgerEntryType type) : SerializedType("LedgerEntry"), mType(type) +SerializedLedgerEntry::SerializedLedgerEntry(LedgerEntryType type) : STObject(sfLedgerEntry), mType(type) { mFormat = getLgrFormat(type); if (mFormat == NULL) throw std::runtime_error("invalid ledger entry type"); - mVersion.setValue(static_cast(mFormat->t_type)); set(mFormat->elements); + setValueFieldU16(sfLedgerEntryType, static_cast(mFormat->t_type)); } std::string SerializedLedgerEntry::getFullText() const @@ -60,7 +60,7 @@ std::string SerializedLedgerEntry::getText() const Json::Value SerializedLedgerEntry::getJson(int options) const { - Json::Value ret(SerializedObject::getJson(options)); + Json::Value ret(STObject::getJson(options)); ret["index"] = mIndex.GetHex(); @@ -96,8 +96,8 @@ bool SerializedLedgerEntry::thread(const uint256& txID, uint32 ledgerSeq, uint25 prevTxID = oldPrevTxID; prevLedgerID = getValueFieldU32(sfLastTxnSeq); assert(prevTxID != txID); - setFieldH256(sfLastTxnID, txID); - setFieldU32(sfLastTxnSeq, ledgerSeq); + setValueFieldH256(sfLastTxnID, txID); + setValueFieldU32(sfLastTxnSeq, ledgerSeq); return true; } @@ -133,19 +133,12 @@ std::vector SerializedLedgerEntry::getOwners() for (int i = 0, fields = getCount(); i < fields; ++i) { - switch (getFieldSType(i)) + int fc = getFieldSType(i).fieldCode; + if ((fc == sfAccount.fieldCode) || (fc == sfLowID.fieldCode) || (fc == sfHighID.fieldCode)) { - case sfAccount: - case sfLowID: - case sfHighID: - { - const STAccount* entry = dynamic_cast(mObject.peekAtPIndex(i)); + const STAccount* entry = dynamic_cast(peekAtPIndex(i)); if ((entry != NULL) && entry->getValueH160(account)) owners.push_back(Ledger::getAccountRootIndex(account)); - } - - default: - nothing(); } } diff --git a/src/SerializedTransaction.cpp b/src/SerializedTransaction.cpp index 87db2afc0b..f77937cce4 100644 --- a/src/SerializedTransaction.cpp +++ b/src/SerializedTransaction.cpp @@ -12,13 +12,13 @@ SerializedTransaction::SerializedTransaction(TransactionType type) : mType(type) mFormat = getTxnFormat(type); if (mFormat == NULL) throw std::runtime_error("invalid transaction type"); - mMiddleTxn.giveObject(new STVariableLength(sfSigningPubKey)); - mMiddleTxn.giveObject(new STAccount(sfSourceAccount)); + mMiddleTxn.giveObject(new STVariableLength(sfSigningKey)); + mMiddleTxn.giveObject(new STAccount(sfAccount)); mMiddleTxn.giveObject(new STUInt32(sfSequence)); mMiddleTxn.giveObject(new STUInt16(sfTransactionType, static_cast(type))); mMiddleTxn.giveObject(new STAmount(sfFee)); - mInnerTxn = STObject(mFormat->elements, "InnerTransaction"); + mInnerTxn = STObject(mFormat->elements, sfInnerTransaction); } SerializedTransaction::SerializedTransaction(SerializerIterator& sit) @@ -53,11 +53,6 @@ SerializedTransaction::SerializedTransaction(SerializerIterator& sit) mInnerTxn = STObject(mFormat->elements, sit, "InnerTransaction"); } -int SerializedTransaction::getLength() const -{ - return mSignature.getLength() + mMiddleTxn.getLength() + mInnerTxn.getLength(); -} - std::string SerializedTransaction::getFullText() const { std::string ret = "\""; @@ -241,7 +236,7 @@ const NewcoinAddress& SerializedTransaction::setSourceAccount(const NewcoinAddre return mSourceAccount; } -uint160 SerializedTransaction::getITFieldAccount(SOE_Field field) const +uint160 SerializedTransaction::getITFieldAccount(SField::ref field) const { uint160 r; const SerializedType* st = mInnerTxn.peekAtPField(field); @@ -253,7 +248,7 @@ uint160 SerializedTransaction::getITFieldAccount(SOE_Field field) const return r; } -int SerializedTransaction::getITFieldIndex(SOE_Field field) const +int SerializedTransaction::getITFieldIndex(SField::ref field) const { return mInnerTxn.getFieldIndex(field); } @@ -263,27 +258,27 @@ int SerializedTransaction::getITFieldCount() const return mInnerTxn.getCount(); } -bool SerializedTransaction::getITFieldPresent(SOE_Field field) const +bool SerializedTransaction::getITFieldPresent(SField::ref field) const { return mInnerTxn.isFieldPresent(field); } -const SerializedType& SerializedTransaction::peekITField(SOE_Field field) const +const SerializedType& SerializedTransaction::peekITField(SField::ref field) const { return mInnerTxn.peekAtField(field); } -SerializedType& SerializedTransaction::getITField(SOE_Field field) +SerializedType& SerializedTransaction::getITField(SField::ref field) { return mInnerTxn.getField(field); } -void SerializedTransaction::makeITFieldPresent(SOE_Field field) +void SerializedTransaction::makeITFieldPresent(SField::ref field) { mInnerTxn.makeFieldPresent(field); } -void SerializedTransaction::makeITFieldAbsent(SOE_Field field) +void SerializedTransaction::makeITFieldAbsent(SField::ref field) { return mInnerTxn.makeFieldAbsent(field); } From a40120b6c9109baf1f96304d4d432b0bbc059df6 Mon Sep 17 00:00:00 2001 From: JoelKatz Date: Thu, 27 Sep 2012 14:11:10 -0700 Subject: [PATCH 19/53] Cleanups and fixes. --- src/Amount.cpp | 2 +- src/SerializeProto.h | 7 +++---- src/SerializedLedger.h | 4 ++-- src/SerializedObject.cpp | 4 ++-- src/SerializedObject.h | 2 +- src/SerializedTransaction.cpp | 14 +++++++------- src/SerializedTypes.cpp | 4 ++-- src/SerializedTypes.h | 25 +++++++++++++------------ src/SerializedValidation.cpp | 8 ++++---- 9 files changed, 35 insertions(+), 35 deletions(-) diff --git a/src/Amount.cpp b/src/Amount.cpp index 793e71c250..11711917ea 100644 --- a/src/Amount.cpp +++ b/src/Amount.cpp @@ -274,7 +274,7 @@ void STAmount::canonicalize() assert((mValue != 0) || (mOffset != -100) ); } -void STAmount::add(Serializer& s) const +void STAmount::addData(Serializer& s) const { if (mIsNative) { diff --git a/src/SerializeProto.h b/src/SerializeProto.h index 225cb85dac..2c9115fd85 100644 --- a/src/SerializeProto.h +++ b/src/SerializeProto.h @@ -64,7 +64,7 @@ FIELD(BaseFee, UINT64, 6) // 128-bit - FIELD(EmailHash, HASH128, 2) + FIELD(EmailHash, HASH128, 1) // 256-bit (common) FIELD(LedgerHash, HASH256, 1) @@ -98,7 +98,7 @@ // variable length FIELD(PublicKey, VL, 1) FIELD(MessageKey, VL, 2) - FIELD(SigningKey, VL, 3) + FIELD(SigningPubKey, VL, 3) FIELD(Signature, VL, 4) FIELD(Generator, VL, 5) FIELD(Domain, VL, 6) @@ -125,8 +125,7 @@ // inner object // OBJECT/1 is reserved for end of object - FIELD(MiddleTransaction, OBJECT, 2) - FIELD(InnerTransaction, OBJECT, 3) + FIELD(InnerTransaction, OBJECT, 1) // array of objects // ARRAY/1 is reserved for end of array diff --git a/src/SerializedLedger.h b/src/SerializedLedger.h index 7468da4d02..b7f35a34f4 100644 --- a/src/SerializedLedger.h +++ b/src/SerializedLedger.h @@ -28,8 +28,8 @@ public: std::string getText() const; Json::Value getJson(int options) const; - const uint256& getIndex() const; - void setIndex(const uint256& i); + const uint256& getIndex() const { return mIndex; } + void setIndex(const uint256& i) { mIndex = i; } LedgerEntryType getType() const { return mType; } uint16 getVersion() const { return getValueFieldU16(sfLedgerEntryType); } diff --git a/src/SerializedObject.cpp b/src/SerializedObject.cpp index ef700db52e..18f20388b7 100644 --- a/src/SerializedObject.cpp +++ b/src/SerializedObject.cpp @@ -212,11 +212,11 @@ std::string STObject::getFullText() const void STObject::add(Serializer& s) const { addFieldID(s); - addRaw(s); + addData(s); s.addFieldID(STI_OBJECT, 1); } -void STObject::addRaw(Serializer& s) const +void STObject::addData(Serializer& s) const { // FIXME: need to add in sorted order BOOST_FOREACH(const SerializedType& it, mData) it.add(s); diff --git a/src/SerializedObject.h b/src/SerializedObject.h index fdc9030e92..f037f0446d 100644 --- a/src/SerializedObject.h +++ b/src/SerializedObject.h @@ -57,7 +57,7 @@ public: virtual bool isEquivalent(const SerializedType& t) const; void add(Serializer& s) const; // with start/end of object - virtual void addRaw(Serializer& s) const; // just inner elements + virtual void addData(Serializer& s) const; // just inner elements Serializer getSerializer() const { Serializer s; add(s); return s; } std::string getFullText() const; std::string getText() const; diff --git a/src/SerializedTransaction.cpp b/src/SerializedTransaction.cpp index f77937cce4..b8a5f96c9a 100644 --- a/src/SerializedTransaction.cpp +++ b/src/SerializedTransaction.cpp @@ -12,7 +12,7 @@ SerializedTransaction::SerializedTransaction(TransactionType type) : mType(type) mFormat = getTxnFormat(type); if (mFormat == NULL) throw std::runtime_error("invalid transaction type"); - mMiddleTxn.giveObject(new STVariableLength(sfSigningKey)); + mMiddleTxn.giveObject(new STVariableLength(sfSigningPubKey)); mMiddleTxn.giveObject(new STAccount(sfAccount)); mMiddleTxn.giveObject(new STUInt32(sfSequence)); mMiddleTxn.giveObject(new STUInt16(sfTransactionType, static_cast(type))); @@ -32,25 +32,25 @@ SerializedTransaction::SerializedTransaction(SerializerIterator& sit) mSignature.setValue(sit.getVL()); - mMiddleTxn.giveObject(new STVariableLength("SigningPubKey", sit.getVL())); + mMiddleTxn.giveObject(new STVariableLength(sfSigningPubKey, sit.getVL())); - STAccount sa("SourceAccount", sit.getVL()); + STAccount sa(sfAccount, sit.getVL()); mSourceAccount = sa.getValueNCA(); mMiddleTxn.giveObject(new STAccount(sa)); - mMiddleTxn.giveObject(new STUInt32("Sequence", sit.get32())); + mMiddleTxn.giveObject(new STUInt32(sfSequence, sit.get32())); mType = static_cast(sit.get16()); - mMiddleTxn.giveObject(new STUInt16("Type", static_cast(mType))); + mMiddleTxn.giveObject(new STUInt16(sfTransactionType, static_cast(mType))); mFormat = getTxnFormat(mType); if (!mFormat) { Log(lsERROR) << "Transaction has invalid type"; throw std::runtime_error("Transaction has invalid type"); } - mMiddleTxn.giveObject(STAmount::deserialize(sit, "Fee")); + mMiddleTxn.giveObject(STAmount::deserialize(sit, sfFee)); - mInnerTxn = STObject(mFormat->elements, sit, "InnerTransaction"); + mInnerTxn = STObject(mFormat->elements, sit, sfInnerTransaction); } std::string SerializedTransaction::getFullText() const diff --git a/src/SerializedTypes.cpp b/src/SerializedTypes.cpp index 6eeb0c9120..4e7ed6ec56 100644 --- a/src/SerializedTypes.cpp +++ b/src/SerializedTypes.cpp @@ -202,7 +202,7 @@ STVector256* STVector256::construct(SerializerIterator& u, SField::ref name) return new STVector256(name, value); } -void STVector256::add(Serializer& s) const +void STVector256::addData(Serializer& s) const { s.addVL(mValue.empty() ? NULL : mValue[0].begin(), mValue.size() * (256 / 8)); } @@ -427,7 +427,7 @@ std::string STPathSet::getText() const } #endif -void STPathSet::add(Serializer& s) const +void STPathSet::addData(Serializer& s) const { bool bFirst = true; diff --git a/src/SerializedTypes.h b/src/SerializedTypes.h index 5df8b6fada..e30a2f783c 100644 --- a/src/SerializedTypes.h +++ b/src/SerializedTypes.h @@ -61,7 +61,8 @@ public: virtual Json::Value getJson(int) const { return getText(); } - virtual void add(Serializer& s) const { return; } + virtual void add(Serializer& s) const { addFieldID(s); addData(s); } + virtual void addData(Serializer& s) const { ; } virtual bool isEquivalent(const SerializedType& t) const { assert(getSType() == STI_NOTPRESENT); return t.getSType() == STI_NOTPRESENT; } @@ -97,7 +98,7 @@ public: SerializedTypeID getSType() const { return STI_UINT8; } std::string getText() const; - void add(Serializer& s) const { s.add8(value); } + void addData(Serializer& s) const { s.add8(value); } unsigned char getValue() const { return value; } void setValue(unsigned char v) { value = v; } @@ -123,7 +124,7 @@ public: SerializedTypeID getSType() const { return STI_UINT16; } std::string getText() const; - void add(Serializer& s) const { s.add16(value); } + void addData(Serializer& s) const { s.add16(value); } uint16 getValue() const { return value; } void setValue(uint16 v) { value=v; } @@ -149,7 +150,7 @@ public: SerializedTypeID getSType() const { return STI_UINT32; } std::string getText() const; - void add(Serializer& s) const { s.add32(value); } + void addData(Serializer& s) const { s.add32(value); } uint32 getValue() const { return value; } void setValue(uint32 v) { value=v; } @@ -175,7 +176,7 @@ public: SerializedTypeID getSType() const { return STI_UINT64; } std::string getText() const; - void add(Serializer& s) const { s.add64(value); } + void addData(Serializer& s) const { s.add64(value); } uint64 getValue() const { return value; } void setValue(uint64 v) { value=v; } @@ -267,7 +268,7 @@ public: std::string getText() const; std::string getRaw() const; std::string getFullText() const; - void add(Serializer& s) const; + void addData(Serializer& s) const; int getExponent() const { return mOffset; } uint64 getMantissa() const { return mValue; } @@ -391,7 +392,7 @@ public: SerializedTypeID getSType() const { return STI_HASH128; } virtual std::string getText() const; - void add(Serializer& s) const { s.add128(value); } + void addData(Serializer& s) const { s.add128(value); } const uint128& getValue() const { return value; } void setValue(const uint128& v) { value=v; } @@ -419,7 +420,7 @@ public: SerializedTypeID getSType() const { return STI_HASH160; } virtual std::string getText() const; - void add(Serializer& s) const { s.add160(value); } + void addData(Serializer& s) const { s.add160(value); } const uint160& getValue() const { return value; } void setValue(const uint160& v) { value=v; } @@ -447,7 +448,7 @@ public: SerializedTypeID getSType() const { return STI_HASH256; } std::string getText() const; - void add(Serializer& s) const { s.add256(value); } + void addData(Serializer& s) const { s.add256(value); } const uint256& getValue() const { return value; } void setValue(const uint256& v) { value=v; } @@ -476,7 +477,7 @@ public: virtual SerializedTypeID getSType() const { return STI_VL; } virtual std::string getText() const; - void add(Serializer& s) const { s.addVL(value); } + void addData(Serializer& s) const { s.addVL(value); } const std::vector& peekValue() const { return value; } std::vector& peekValue() { return value; } @@ -641,7 +642,7 @@ public: { return std::auto_ptr(construct(sit, name)); } // std::string getText() const; - void add(Serializer& s) const; + void addData(Serializer& s) const; virtual Json::Value getJson(int) const; SerializedTypeID getSType() const { return STI_PATHSET; } @@ -710,7 +711,7 @@ public: STVector256(const std::vector& vector) : mValue(vector) { ; } SerializedTypeID getSType() const { return STI_VECTOR256; } - void add(Serializer& s) const; + void addData(Serializer& s) const; static std::auto_ptr deserialize(SerializerIterator& sit, SField::ref name) { return std::auto_ptr(construct(sit, name)); } diff --git a/src/SerializedValidation.cpp b/src/SerializedValidation.cpp index 6eedadb94b..edd4fe721b 100644 --- a/src/SerializedValidation.cpp +++ b/src/SerializedValidation.cpp @@ -11,7 +11,7 @@ SOElement SerializedValidation::sValidationFormat[] = { { sfLoadFee, SOE_OPTIONAL }, { sfBaseFee, SOE_OPTIONAL }, { sfSigningTime, SOE_REQUIRED }, - { sfSigningKey, SOE_REQUIRED }, + { sfSigningPubKey, SOE_REQUIRED }, { sfInvalid, SOE_END } }; @@ -30,7 +30,7 @@ SerializedValidation::SerializedValidation(const uint256& ledgerHash, uint32 sig setValueFieldH256(sfLedgerHash, ledgerHash); setValueFieldU32(sfSigningTime, signTime); if (naSeed.isValid()) - setValueFieldVL(sfSigningKey, NewcoinAddress::createNodePublic(naSeed).getNodePublic()); + setValueFieldVL(sfSigningPubKey, NewcoinAddress::createNodePublic(naSeed).getNodePublic()); if (!isFull) setFlag(sFullFlag); NewcoinAddress::createNodePrivate(naSeed).signNodePrivate(getSigningHash(), mSignature.peekValue()); @@ -73,7 +73,7 @@ bool SerializedValidation::isValid(const uint256& signingHash) const { try { - NewcoinAddress naPublicKey = NewcoinAddress::createNodePublic(getValueFieldVL(sfSigningKey)); + NewcoinAddress naPublicKey = NewcoinAddress::createNodePublic(getValueFieldVL(sfSigningPubKey)); return naPublicKey.isValid() && naPublicKey.verifyNodePublic(signingHash, mSignature.peekValue()); } catch (...) @@ -85,7 +85,7 @@ bool SerializedValidation::isValid(const uint256& signingHash) const NewcoinAddress SerializedValidation::getSignerPublic() const { NewcoinAddress a; - a.setNodePublic(getValueFieldVL(sfSigningKey)); + a.setNodePublic(getValueFieldVL(sfSigningPubKey)); return a; } From b6653732b0f84c120a45fff01932d5c4460a6de1 Mon Sep 17 00:00:00 2001 From: JoelKatz Date: Thu, 27 Sep 2012 15:43:29 -0700 Subject: [PATCH 20/53] New serializer work. Rework add/addRaw/addData per discussion with Arthur. New STObject add/deserialize code. STArray add/deserialize code. Allow arrays of normal fields. Other small fixes. --- src/Amount.cpp | 2 +- src/SerializedObject.cpp | 94 +++++++++++++++++++++++++++++++++++++--- src/SerializedObject.h | 61 +++++++++++++------------- src/SerializedTypes.cpp | 4 +- src/SerializedTypes.h | 25 +++++------ src/Serializer.h | 2 +- 6 files changed, 132 insertions(+), 56 deletions(-) diff --git a/src/Amount.cpp b/src/Amount.cpp index 8bd2d96a02..bfcad54d37 100644 --- a/src/Amount.cpp +++ b/src/Amount.cpp @@ -275,7 +275,7 @@ void STAmount::canonicalize() assert((mValue != 0) || (mOffset != -100) ); } -void STAmount::addData(Serializer& s) const +void STAmount::add(Serializer& s) const { if (mIsNative) { diff --git a/src/SerializedObject.cpp b/src/SerializedObject.cpp index 18f20388b7..25219648d3 100644 --- a/src/SerializedObject.cpp +++ b/src/SerializedObject.cpp @@ -186,6 +186,14 @@ bool STObject::set(SerializerIterator& sit, int depth) return false; } +std::auto_ptr STObject::deserialize(SerializerIterator& sit, SField::ref name) +{ + STObject *o; + std::auto_ptr object(o = new STObject(name)); + o->set(sit, 1); + return object; +} + std::string STObject::getFullText() const { std::string ret; @@ -211,15 +219,28 @@ std::string STObject::getFullText() const void STObject::add(Serializer& s) const { - addFieldID(s); - addData(s); - s.addFieldID(STI_OBJECT, 1); -} + std::map fields; -void STObject::addData(Serializer& s) const -{ // FIXME: need to add in sorted order BOOST_FOREACH(const SerializedType& it, mData) - it.add(s); + { // pick out the fields and sort them + if (it.getSType() != STI_NOTPRESENT) + fields.insert(std::make_pair(it.getFName().fieldCode, &it)); + } + + + typedef std::pair field_iterator; + BOOST_FOREACH(field_iterator& it, fields) + { // insert them in sorted order + const SerializedType* field = it.second; + + field->addFieldID(s); + field->add(s); + + if (dynamic_cast(field)) + s.addFieldID(STI_OBJECT, 1); + else if (dynamic_cast(field)) + s.addFieldID(STI_ARRAY, 1); + } } std::string STObject::getText() const @@ -653,6 +674,65 @@ Json::Value STVector256::getJson(int options) const return ret; } +std::string STArray::getFullText() const +{ + return "WRITEME"; +} + +std::string STArray::getText() const +{ + return "WRITEME"; +} + +Json::Value STArray::getJson(int) const +{ + return Json::Value("WRITEME"); +} + +void STArray::add(Serializer& s) const +{ + BOOST_FOREACH(const SerializedType& object, value) + { + object.addFieldID(s); + object.add(s); + + if (dynamic_cast(&object)) + s.addFieldID(STI_OBJECT, 1); + else if (dynamic_cast(&object)) + s.addFieldID(STI_ARRAY, 1); + } +} + +bool STArray::isEquivalent(const SerializedType& t) const +{ + const STArray* v = dynamic_cast(&t); + if (!v) + return false; + return value == v->value; +} + +STArray* STArray::construct(SerializerIterator& sit, SField::ref field) +{ + vector value; + + while (!sit.empty()) + { + int type, field; + sit.getFieldID(type, field); + if ((type == STI_ARRAY) && (field == 1)) + break; + + SField::ref fn = SField::getField(type, field); + if (fn.isInvalid()) + throw std::runtime_error("Unknown field"); + + value.push_back(*STObject::makeDeserializedObject(fn.fieldType, fn, sit, 1)); + } + + return new STArray(field, value); +} + + #if 0 static SOElement testSOElements[2][16] = diff --git a/src/SerializedObject.h b/src/SerializedObject.h index f037f0446d..8c696b6b7f 100644 --- a/src/SerializedObject.h +++ b/src/SerializedObject.h @@ -28,7 +28,6 @@ protected: std::vector mType; STObject* duplicate() const { return new STObject(*this); } - static STObject* construct(SerializerIterator&, SField::ref); public: STObject() { ; } @@ -43,8 +42,7 @@ public: virtual ~STObject() { ; } - static std::auto_ptr deserialize(SerializerIterator& sit, SField::ref name) - { return std::auto_ptr(construct(sit, name)); } + static std::auto_ptr deserialize(SerializerIterator& sit, SField::ref name); void setType(SOElement::ptrList); bool isValidForType(); @@ -56,8 +54,7 @@ public: virtual SerializedTypeID getSType() const { return STI_OBJECT; } virtual bool isEquivalent(const SerializedType& t) const; - void add(Serializer& s) const; // with start/end of object - virtual void addData(Serializer& s) const; // just inner elements + virtual void add(Serializer& s) const; // just inner elements Serializer getSerializer() const { Serializer s; add(s); return s; } std::string getFullText() const; std::string getText() const; @@ -140,12 +137,12 @@ public: class STArray : public SerializedType { public: - typedef std::vector vector; - typedef std::vector::iterator iterator; - typedef std::vector::const_iterator const_iterator; - typedef std::vector::reverse_iterator reverse_iterator; - typedef std::vector::const_reverse_iterator const_reverse_iterator; - typedef std::vector::size_type size_type; + typedef std::vector vector; + typedef std::vector::iterator iterator; + typedef std::vector::const_iterator const_iterator; + typedef std::vector::reverse_iterator reverse_iterator; + typedef std::vector::const_reverse_iterator const_reverse_iterator; + typedef std::vector::size_type size_type; protected: @@ -164,36 +161,36 @@ public: static std::auto_ptr deserialize(SerializerIterator& sit, SField::ref name) { return std::auto_ptr(construct(sit, name)); } - const vector& getValue() const { return value; } - vector& getValue() { return value; } + const vector& getValue() const { return value; } + vector& getValue() { return value; } // vector-like functions - void push_back(const STObject& object) { value.push_back(object); } - STObject& operator[](int j) { return value[j]; } - const STObject& operator[](int j) const { return value[j]; } - iterator begin() { return value.begin(); } - const_iterator begin() const { return value.begin(); } - iterator end() { return value.end(); } - const_iterator end() const { return value.end(); } - size_type size() const { return value.size(); } - reverse_iterator rbegin() { return value.rbegin(); } - const_reverse_iterator rbegin() const { return value.rbegin(); } - reverse_iterator rend() { return value.rend(); } - const_reverse_iterator rend() const { return value.rend(); } - iterator erase(iterator pos) { return value.erase(pos); } - void pop_back() { value.pop_back(); } - bool empty() const { return value.empty(); } - void clear() { value.clear(); } + void push_back(const SerializedType& object) { value.push_back(object); } + SerializedType& operator[](int j) { return value[j]; } + const SerializedType& operator[](int j) const { return value[j]; } + iterator begin() { return value.begin(); } + const_iterator begin() const { return value.begin(); } + iterator end() { return value.end(); } + const_iterator end() const { return value.end(); } + size_type size() const { return value.size(); } + reverse_iterator rbegin() { return value.rbegin(); } + const_reverse_iterator rbegin() const { return value.rbegin(); } + reverse_iterator rend() { return value.rend(); } + const_reverse_iterator rend() const { return value.rend(); } + iterator erase(iterator pos) { return value.erase(pos); } + void pop_back() { value.pop_back(); } + bool empty() const { return value.empty(); } + void clear() { value.clear(); } virtual std::string getFullText() const; virtual std::string getText() const; virtual Json::Value getJson(int) const; virtual void add(Serializer& s) const; - bool operator==(const STArray &s) { return value == s.value; } - bool operator!=(const STArray &s) { return value != s.value; } + bool operator==(const STArray &s) { return value == s.value; } + bool operator!=(const STArray &s) { return value != s.value; } - virtual SerializedTypeID getSType() const { return STI_ARRAY; } + virtual SerializedTypeID getSType() const { return STI_ARRAY; } virtual bool isEquivalent(const SerializedType& t) const; }; diff --git a/src/SerializedTypes.cpp b/src/SerializedTypes.cpp index 4e7ed6ec56..6eeb0c9120 100644 --- a/src/SerializedTypes.cpp +++ b/src/SerializedTypes.cpp @@ -202,7 +202,7 @@ STVector256* STVector256::construct(SerializerIterator& u, SField::ref name) return new STVector256(name, value); } -void STVector256::addData(Serializer& s) const +void STVector256::add(Serializer& s) const { s.addVL(mValue.empty() ? NULL : mValue[0].begin(), mValue.size() * (256 / 8)); } @@ -427,7 +427,7 @@ std::string STPathSet::getText() const } #endif -void STPathSet::addData(Serializer& s) const +void STPathSet::add(Serializer& s) const { bool bFirst = true; diff --git a/src/SerializedTypes.h b/src/SerializedTypes.h index e30a2f783c..5748f960ec 100644 --- a/src/SerializedTypes.h +++ b/src/SerializedTypes.h @@ -61,8 +61,7 @@ public: virtual Json::Value getJson(int) const { return getText(); } - virtual void add(Serializer& s) const { addFieldID(s); addData(s); } - virtual void addData(Serializer& s) const { ; } + virtual void add(Serializer& s) const { ; } virtual bool isEquivalent(const SerializedType& t) const { assert(getSType() == STI_NOTPRESENT); return t.getSType() == STI_NOTPRESENT; } @@ -98,7 +97,7 @@ public: SerializedTypeID getSType() const { return STI_UINT8; } std::string getText() const; - void addData(Serializer& s) const { s.add8(value); } + void add(Serializer& s) const { s.add8(value); } unsigned char getValue() const { return value; } void setValue(unsigned char v) { value = v; } @@ -124,7 +123,7 @@ public: SerializedTypeID getSType() const { return STI_UINT16; } std::string getText() const; - void addData(Serializer& s) const { s.add16(value); } + void add(Serializer& s) const { s.add16(value); } uint16 getValue() const { return value; } void setValue(uint16 v) { value=v; } @@ -150,7 +149,7 @@ public: SerializedTypeID getSType() const { return STI_UINT32; } std::string getText() const; - void addData(Serializer& s) const { s.add32(value); } + void add(Serializer& s) const { s.add32(value); } uint32 getValue() const { return value; } void setValue(uint32 v) { value=v; } @@ -176,7 +175,7 @@ public: SerializedTypeID getSType() const { return STI_UINT64; } std::string getText() const; - void addData(Serializer& s) const { s.add64(value); } + void add(Serializer& s) const { s.add64(value); } uint64 getValue() const { return value; } void setValue(uint64 v) { value=v; } @@ -268,7 +267,7 @@ public: std::string getText() const; std::string getRaw() const; std::string getFullText() const; - void addData(Serializer& s) const; + void add(Serializer& s) const; int getExponent() const { return mOffset; } uint64 getMantissa() const { return mValue; } @@ -392,7 +391,7 @@ public: SerializedTypeID getSType() const { return STI_HASH128; } virtual std::string getText() const; - void addData(Serializer& s) const { s.add128(value); } + void add(Serializer& s) const { s.add128(value); } const uint128& getValue() const { return value; } void setValue(const uint128& v) { value=v; } @@ -420,7 +419,7 @@ public: SerializedTypeID getSType() const { return STI_HASH160; } virtual std::string getText() const; - void addData(Serializer& s) const { s.add160(value); } + void add(Serializer& s) const { s.add160(value); } const uint160& getValue() const { return value; } void setValue(const uint160& v) { value=v; } @@ -448,7 +447,7 @@ public: SerializedTypeID getSType() const { return STI_HASH256; } std::string getText() const; - void addData(Serializer& s) const { s.add256(value); } + void add(Serializer& s) const { s.add256(value); } const uint256& getValue() const { return value; } void setValue(const uint256& v) { value=v; } @@ -477,7 +476,7 @@ public: virtual SerializedTypeID getSType() const { return STI_VL; } virtual std::string getText() const; - void addData(Serializer& s) const { s.addVL(value); } + void add(Serializer& s) const { s.addVL(value); } const std::vector& peekValue() const { return value; } std::vector& peekValue() { return value; } @@ -642,7 +641,7 @@ public: { return std::auto_ptr(construct(sit, name)); } // std::string getText() const; - void addData(Serializer& s) const; + void add(Serializer& s) const; virtual Json::Value getJson(int) const; SerializedTypeID getSType() const { return STI_PATHSET; } @@ -711,7 +710,7 @@ public: STVector256(const std::vector& vector) : mValue(vector) { ; } SerializedTypeID getSType() const { return STI_VECTOR256; } - void addData(Serializer& s) const; + void add(Serializer& s) const; static std::auto_ptr deserialize(SerializerIterator& sit, SField::ref name) { return std::auto_ptr(construct(sit, name)); } diff --git a/src/Serializer.h b/src/Serializer.h index ec762e52c7..8666efe4c3 100644 --- a/src/Serializer.h +++ b/src/Serializer.h @@ -70,7 +70,7 @@ public: bool getFieldID(int& type, int& name, int offset) const; int addFieldID(int type, int name); - int addFieldID(SerializedTypeID type, int name); + int addFieldID(SerializedTypeID type, int name) { return addFieldID(static_cast(type), name); } // normal hash functions uint160 getRIPEMD160(int size=-1) const; From 5ab9871fe6ed3abbc56d6bb78c824daab4849def Mon Sep 17 00:00:00 2001 From: JoelKatz Date: Thu, 27 Sep 2012 20:40:15 -0700 Subject: [PATCH 21/53] Bump versions to prevent incomatible server-server connections. --- src/Version.h | 10 +++++----- 1 file changed, 5 insertions(+), 5 deletions(-) diff --git a/src/Version.h b/src/Version.h index d7cd3a02aa..382977f4ab 100644 --- a/src/Version.h +++ b/src/Version.h @@ -5,7 +5,7 @@ // #define SERVER_VERSION_MAJOR 0 -#define SERVER_VERSION_MINOR 5 +#define SERVER_VERSION_MINOR 6 #define SERVER_VERSION_SUB "-a" #define SERVER_NAME "NewCoin" @@ -15,12 +15,12 @@ (SERVER_NAME "-" SV_STRINGIZE(SERVER_VERSION_MAJOR) "." SV_STRINGIZE(SERVER_VERSION_MINOR) SERVER_VERSION_SUB) // Version we prefer to speak: -#define PROTO_VERSION_MAJOR 0 -#define PROTO_VERSION_MINOR 7 +#define PROTO_VERSION_MAJOR 1 +#define PROTO_VERSION_MINOR 0 // Version we will speak to: -#define MIN_PROTO_MAJOR 0 -#define MIN_PROTO_MINOR 7 +#define MIN_PROTO_MAJOR 1 +#define MIN_PROTO_MINOR 0 #define MAKE_VERSION_INT(maj,min) ((maj << 16) | min) #define GET_VERSION_MAJOR(ver) (ver >> 16) From b8a84ec83eae88243e2ad3e34b5450dae73b47ff Mon Sep 17 00:00:00 2001 From: JoelKatz Date: Thu, 27 Sep 2012 20:40:34 -0700 Subject: [PATCH 22/53] Bug fixes. --- src/FieldNames.cpp | 6 ++++-- src/LedgerFormats.cpp | 26 ++++++++++++++++++-------- src/TransactionFormats.cpp | 31 ++++++++++++++++++------------- 3 files changed, 40 insertions(+), 23 deletions(-) diff --git a/src/FieldNames.cpp b/src/FieldNames.cpp index 98ba23616e..d631fb7f01 100644 --- a/src/FieldNames.cpp +++ b/src/FieldNames.cpp @@ -7,6 +7,10 @@ #include +// These must stay at the top of this file +std::map SField::codeToField; +boost::mutex SField::mapMutex; + SField sfInvalid(-1), sfGeneric(0); SField sfLedgerEntry(FIELD_CODE(STI_LEDGERENTRY, 1), STI_LEDGERENTRY, 1, "LedgerEntry"); SField sfTransaction(FIELD_CODE(STI_TRANSACTION, 1), STI_TRANSACTION, 1, "Transaction"); @@ -18,8 +22,6 @@ SField sfValidation(FIELD_CODE(STI_VALIDATION, 1), STI_VALIDATION, 1, "Validatio #undef FIELD #undef TYPE -std::map SField::codeToField; -boost::mutex SField::mapMutex; SField::ref SField::getField(int code) { diff --git a/src/LedgerFormats.cpp b/src/LedgerFormats.cpp index 37cc7906e4..59aa5fd668 100644 --- a/src/LedgerFormats.cpp +++ b/src/LedgerFormats.cpp @@ -1,10 +1,14 @@ #include "LedgerFormats.h" +#define LEF_BASE \ + { sfLedgerEntryType, SOE_REQUIRED }, \ + { sfFlags, SOE_REQUIRED }, \ + { sfLedgerIndex, SOE_OPTIONAL }, + LedgerEntryFormat LedgerFormats[]= { - { "AccountRoot", ltACCOUNT_ROOT, { - { sfFlags, SOE_REQUIRED }, + { "AccountRoot", ltACCOUNT_ROOT, { LEF_BASE { sfAccount, SOE_REQUIRED }, { sfSequence, SOE_REQUIRED }, { sfBalance, SOE_REQUIRED }, @@ -20,7 +24,8 @@ LedgerEntryFormat LedgerFormats[]= { sfPublishSize, SOE_OPTIONAL }, { sfInvalid, SOE_END } } }, - { "Contract", ltCONTRACT, { + { "Contract", ltCONTRACT, { LEF_BASE + { sfLedgerEntryType,SOE_REQUIRED }, { sfFlags, SOE_REQUIRED }, { sfAccount, SOE_REQUIRED }, { sfBalance, SOE_REQUIRED }, @@ -36,25 +41,29 @@ LedgerEntryFormat LedgerFormats[]= { sfExpireCode, SOE_REQUIRED }, { sfInvalid, SOE_END } } }, - { "DirectoryNode", ltDIR_NODE, { + { "DirectoryNode", ltDIR_NODE, { LEF_BASE + { sfLedgerEntryType,SOE_REQUIRED }, { sfFlags, SOE_REQUIRED }, { sfIndexes, SOE_REQUIRED }, { sfIndexNext, SOE_OPTIONAL }, { sfIndexPrevious, SOE_OPTIONAL }, { sfInvalid, SOE_END } } }, - { "GeneratorMap", ltGENERATOR_MAP, { + { "GeneratorMap", ltGENERATOR_MAP, { LEF_BASE + { sfLedgerEntryType,SOE_REQUIRED }, { sfFlags, SOE_REQUIRED }, { sfGenerator, SOE_REQUIRED }, { sfInvalid, SOE_END } } }, - { "Nickname", ltNICKNAME, { + { "Nickname", ltNICKNAME, { LEF_BASE + { sfLedgerEntryType,SOE_REQUIRED }, { sfFlags, SOE_REQUIRED }, { sfAccount, SOE_REQUIRED }, { sfMinimumOffer, SOE_OPTIONAL }, { sfInvalid, SOE_END } } }, - { "Offer", ltOFFER, { + { "Offer", ltOFFER, { LEF_BASE + { sfLedgerEntryType,SOE_REQUIRED }, { sfFlags, SOE_REQUIRED }, { sfAccount, SOE_REQUIRED }, { sfSequence, SOE_REQUIRED }, @@ -68,7 +77,8 @@ LedgerEntryFormat LedgerFormats[]= { sfExpiration, SOE_OPTIONAL }, { sfInvalid, SOE_END } } }, - { "RippleState", ltRIPPLE_STATE, { + { "RippleState", ltRIPPLE_STATE, { LEF_BASE + { sfLedgerEntryType,SOE_REQUIRED }, { sfFlags, SOE_REQUIRED }, { sfBalance, SOE_REQUIRED }, { sfLowID, SOE_REQUIRED }, diff --git a/src/TransactionFormats.cpp b/src/TransactionFormats.cpp index a23d82320c..2216180dd6 100644 --- a/src/TransactionFormats.cpp +++ b/src/TransactionFormats.cpp @@ -1,9 +1,14 @@ #include "TransactionFormats.h" +#define TF_BASE \ + { sfTransactionType, SOE_REQUIRED }, \ + { sfFlags, SOE_REQUIRED }, \ + { sfSignature, SOE_OPTIONAL }, + TransactionFormat InnerTxnFormats[]= { - { "AccountSet", ttACCOUNT_SET, { + { "AccountSet", ttACCOUNT_SET, { TF_BASE { sfFlags, SOE_REQUIRED }, { sfSourceTag, SOE_OPTIONAL }, { sfEmailHash, SOE_OPTIONAL }, @@ -15,7 +20,7 @@ TransactionFormat InnerTxnFormats[]= { sfPublishSize, SOE_OPTIONAL }, { sfInvalid, SOE_END } } }, - { "Claim", ttCLAIM, { + { "Claim", ttCLAIM, { TF_BASE { sfFlags, SOE_REQUIRED }, { sfGenerator, SOE_REQUIRED }, { sfPublicKey, SOE_REQUIRED }, @@ -23,7 +28,7 @@ TransactionFormat InnerTxnFormats[]= { sfSourceTag, SOE_OPTIONAL }, { sfInvalid, SOE_END } } }, - { "CreditSet", ttCREDIT_SET, { + { "CreditSet", ttCREDIT_SET, { TF_BASE { sfFlags, SOE_REQUIRED }, { sfDestination, SOE_REQUIRED }, { sfSourceTag, SOE_OPTIONAL }, @@ -33,7 +38,7 @@ TransactionFormat InnerTxnFormats[]= { sfInvalid, SOE_END } } }, /* - { "Invoice", ttINVOICE, { + { "Invoice", ttINVOICE, { TF_BASE { sfFlags, SOE_REQUIRED }, { sfTarget, SOE_REQUIRED }, { sfAmount, SOE_REQUIRED }, @@ -43,7 +48,7 @@ TransactionFormat InnerTxnFormats[]= { sfInvalid, SOE_END } } }, */ - { "NicknameSet", ttNICKNAME_SET, { + { "NicknameSet", ttNICKNAME_SET, { TF_BASE { sfFlags, SOE_REQUIRED }, { sfNickname, SOE_REQUIRED }, { sfMinimumOffer, SOE_OPTIONAL }, @@ -51,7 +56,7 @@ TransactionFormat InnerTxnFormats[]= { sfSourceTag, SOE_OPTIONAL }, { sfInvalid, SOE_END } } }, - { "OfferCreate", ttOFFER_CREATE, { + { "OfferCreate", ttOFFER_CREATE, { TF_BASE { sfFlags, SOE_REQUIRED}, { sfTakerPays, SOE_REQUIRED }, { sfTakerGets, SOE_REQUIRED }, @@ -59,19 +64,19 @@ TransactionFormat InnerTxnFormats[]= { sfExpiration, SOE_OPTIONAL }, { sfInvalid, SOE_END } } }, - { "OfferCancel", ttOFFER_CANCEL, { + { "OfferCancel", ttOFFER_CANCEL, { TF_BASE { sfFlags, SOE_REQUIRED }, { sfOfferSequence, SOE_REQUIRED }, { sfSourceTag, SOE_OPTIONAL }, { sfInvalid, SOE_END } } }, - { "PasswordFund", ttPASSWORD_FUND, { + { "PasswordFund", ttPASSWORD_FUND, { TF_BASE { sfFlags, SOE_REQUIRED }, { sfDestination, SOE_REQUIRED }, { sfSourceTag, SOE_OPTIONAL }, { sfInvalid, SOE_END } } }, - { "PasswordSet", ttPASSWORD_SET, { + { "PasswordSet", ttPASSWORD_SET, { TF_BASE { sfFlags, SOE_REQUIRED }, { sfAuthorizedKey, SOE_REQUIRED }, { sfGenerator, SOE_REQUIRED }, @@ -80,7 +85,7 @@ TransactionFormat InnerTxnFormats[]= { sfSourceTag, SOE_OPTIONAL }, { sfInvalid, SOE_END } } }, - { "Payment", ttPAYMENT, { + { "Payment", ttPAYMENT, { TF_BASE { sfFlags, SOE_REQUIRED }, { sfDestination, SOE_REQUIRED }, { sfAmount, SOE_REQUIRED }, @@ -90,7 +95,7 @@ TransactionFormat InnerTxnFormats[]= { sfInvoiceID, SOE_OPTIONAL }, { sfInvalid, SOE_END } } }, - { "WalletAdd", ttWALLET_ADD, { + { "WalletAdd", ttWALLET_ADD, { TF_BASE { sfFlags, SOE_REQUIRED }, { sfAmount, SOE_REQUIRED }, { sfAuthorizedKey, SOE_REQUIRED }, @@ -99,7 +104,7 @@ TransactionFormat InnerTxnFormats[]= { sfSourceTag, SOE_OPTIONAL }, { sfInvalid, SOE_END } } }, - { "Contract", ttCONTRACT, { + { "Contract", ttCONTRACT, { TF_BASE { sfFlags, SOE_REQUIRED }, { sfExpiration, SOE_REQUIRED }, { sfBondAmount, SOE_REQUIRED }, @@ -111,7 +116,7 @@ TransactionFormat InnerTxnFormats[]= { sfExpireCode, SOE_OPTIONAL }, { sfInvalid, SOE_END } } }, - { "RemoveContract", ttCONTRACT_REMOVE, { + { "RemoveContract", ttCONTRACT_REMOVE, { TF_BASE { sfFlags, SOE_REQUIRED }, { sfTarget, SOE_REQUIRED }, { sfInvalid, SOE_END } } From 2c2bfab52fcca1a8f0bca7613b1e0057af86fd16 Mon Sep 17 00:00:00 2001 From: JoelKatz Date: Thu, 27 Sep 2012 20:47:11 -0700 Subject: [PATCH 23/53] STArrays should only hold STObject's --- src/SerializedObject.cpp | 14 +++----------- src/SerializedObject.h | 20 ++++++++++---------- 2 files changed, 13 insertions(+), 21 deletions(-) diff --git a/src/SerializedObject.cpp b/src/SerializedObject.cpp index 25219648d3..e2f3cbeab3 100644 --- a/src/SerializedObject.cpp +++ b/src/SerializedObject.cpp @@ -235,11 +235,7 @@ void STObject::add(Serializer& s) const field->addFieldID(s); field->add(s); - - if (dynamic_cast(field)) - s.addFieldID(STI_OBJECT, 1); - else if (dynamic_cast(field)) - s.addFieldID(STI_ARRAY, 1); + s.addFieldID(STI_OBJECT, 1); } } @@ -691,15 +687,11 @@ Json::Value STArray::getJson(int) const void STArray::add(Serializer& s) const { - BOOST_FOREACH(const SerializedType& object, value) + BOOST_FOREACH(const STObject& object, value) { object.addFieldID(s); object.add(s); - - if (dynamic_cast(&object)) - s.addFieldID(STI_OBJECT, 1); - else if (dynamic_cast(&object)) - s.addFieldID(STI_ARRAY, 1); + s.addFieldID(STI_OBJECT, 1); } } diff --git a/src/SerializedObject.h b/src/SerializedObject.h index 8c696b6b7f..bed99e969b 100644 --- a/src/SerializedObject.h +++ b/src/SerializedObject.h @@ -137,12 +137,12 @@ public: class STArray : public SerializedType { public: - typedef std::vector vector; - typedef std::vector::iterator iterator; - typedef std::vector::const_iterator const_iterator; - typedef std::vector::reverse_iterator reverse_iterator; - typedef std::vector::const_reverse_iterator const_reverse_iterator; - typedef std::vector::size_type size_type; + typedef std::vector vector; + typedef std::vector::iterator iterator; + typedef std::vector::const_iterator const_iterator; + typedef std::vector::reverse_iterator reverse_iterator; + typedef std::vector::const_reverse_iterator const_reverse_iterator; + typedef std::vector::size_type size_type; protected: @@ -165,9 +165,9 @@ public: vector& getValue() { return value; } // vector-like functions - void push_back(const SerializedType& object) { value.push_back(object); } - SerializedType& operator[](int j) { return value[j]; } - const SerializedType& operator[](int j) const { return value[j]; } + void push_back(const STObject& object) { value.push_back(object); } + STObject& operator[](int j) { return value[j]; } + const STObject& operator[](int j) const { return value[j]; } iterator begin() { return value.begin(); } const_iterator begin() const { return value.begin(); } iterator end() { return value.end(); } @@ -191,7 +191,7 @@ public: bool operator!=(const STArray &s) { return value != s.value; } virtual SerializedTypeID getSType() const { return STI_ARRAY; } - virtual bool isEquivalent(const SerializedType& t) const; + virtual bool isEquivalent(const STObject& t) const; }; #endif From febe7a1224933073af03e2e09d8f69df791966cc Mon Sep 17 00:00:00 2001 From: JoelKatz Date: Thu, 27 Sep 2012 20:47:50 -0700 Subject: [PATCH 24/53] Search/replace went slightly awry. --- src/SerializedObject.h | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/src/SerializedObject.h b/src/SerializedObject.h index bed99e969b..c74402f15c 100644 --- a/src/SerializedObject.h +++ b/src/SerializedObject.h @@ -191,7 +191,7 @@ public: bool operator!=(const STArray &s) { return value != s.value; } virtual SerializedTypeID getSType() const { return STI_ARRAY; } - virtual bool isEquivalent(const STObject& t) const; + virtual bool isEquivalent(const SerializedType& t) const; }; #endif From b88d6486a6bc22605c4b4537997fb6290ea33e08 Mon Sep 17 00:00:00 2001 From: JoelKatz Date: Thu, 27 Sep 2012 20:55:10 -0700 Subject: [PATCH 25/53] Rather than a polymorphic downcast, just fill in the object in place. --- src/SerializedObject.cpp | 3 ++- 1 file changed, 2 insertions(+), 1 deletion(-) diff --git a/src/SerializedObject.cpp b/src/SerializedObject.cpp index e2f3cbeab3..4834a1f3f5 100644 --- a/src/SerializedObject.cpp +++ b/src/SerializedObject.cpp @@ -718,7 +718,8 @@ STArray* STArray::construct(SerializerIterator& sit, SField::ref field) if (fn.isInvalid()) throw std::runtime_error("Unknown field"); - value.push_back(*STObject::makeDeserializedObject(fn.fieldType, fn, sit, 1)); + value.push_back(STObject(fn)); + value.rbegin()->set(sit, 1); } return new STArray(field, value); From 8c2eda1f93536138c881bb0c15e07ea445e9b1d4 Mon Sep 17 00:00:00 2001 From: JoelKatz Date: Fri, 28 Sep 2012 14:26:19 -0700 Subject: [PATCH 26/53] Fix signature/hash generation. --- src/SerializedObject.cpp | 29 ++++++++++++++++++++++++++--- src/SerializedObject.h | 6 +++++- 2 files changed, 31 insertions(+), 4 deletions(-) diff --git a/src/SerializedObject.cpp b/src/SerializedObject.cpp index 4834a1f3f5..cc6f6f9136 100644 --- a/src/SerializedObject.cpp +++ b/src/SerializedObject.cpp @@ -217,14 +217,18 @@ std::string STObject::getFullText() const return ret; } -void STObject::add(Serializer& s) const +void STObject::add(Serializer& s, bool withSigningFields) const { std::map fields; BOOST_FOREACH(const SerializedType& it, mData) { // pick out the fields and sort them if (it.getSType() != STI_NOTPRESENT) - fields.insert(std::make_pair(it.getFName().fieldCode, &it)); + { + SField::ref fName = it.getFName(); + if (withSigningFields || (fName == sfSignature) || (fName == sfSignatures)) + fields.insert(std::make_pair(it.getFName().fieldCode, &it)); + } } @@ -235,7 +239,10 @@ void STObject::add(Serializer& s) const field->addFieldID(s); field->add(s); - s.addFieldID(STI_OBJECT, 1); + if (dynamic_cast(field) != NULL) + s.addFieldID(STI_ARRAY, 1); + else if (dynamic_cast(field) != NULL) + s.addFieldID(STI_OBJECT, 1); } } @@ -272,6 +279,22 @@ bool STObject::isEquivalent(const SerializedType& t) const return (it1 == end1) && (it2 == end2); } +uint256 getHash(uint32 prefix) cosnt +{ + Serializer s; + s.add32(prefix); + add(s, true); + return s.getSHA512Half(); +} + +uint256 getSigningHash(uint32 prefix) cosnt +{ + Serializer s; + s.add32(prefix); + add(s, false); + return s.getSHA512Half(); +} + int STObject::getFieldIndex(SField::ref field) const { int i = 0; diff --git a/src/SerializedObject.h b/src/SerializedObject.h index c74402f15c..adb054586b 100644 --- a/src/SerializedObject.h +++ b/src/SerializedObject.h @@ -54,7 +54,8 @@ public: virtual SerializedTypeID getSType() const { return STI_OBJECT; } virtual bool isEquivalent(const SerializedType& t) const; - virtual void add(Serializer& s) const; // just inner elements + virtual void add(Serializer& s) const { add(s, true); } // just inner elements + void add(Serializer& s, int withSignature) const; Serializer getSerializer() const { Serializer s; add(s); return s; } std::string getFullText() const; std::string getText() const; @@ -72,6 +73,9 @@ public: bool clearFlag(uint32); uint32 getFlags() const; + uint256 getHash(uint32 prefix) const; + uint256 getSigningHash(uint32 prefix) const; + const SerializedType& peekAtIndex(int offset) const { return mData[offset]; } SerializedType& getIndex(int offset) { return mData[offset]; } const SerializedType* peekAtPIndex(int offset) const { return &(mData[offset]); } From 64231daadbff7002adc4f4b104636510c0164e6d Mon Sep 17 00:00:00 2001 From: JoelKatz Date: Fri, 28 Sep 2012 19:11:24 -0700 Subject: [PATCH 27/53] Protocol updates. --- src/SerializeProto.h | 14 +++++++------- 1 file changed, 7 insertions(+), 7 deletions(-) diff --git a/src/SerializeProto.h b/src/SerializeProto.h index 2c9115fd85..fe8778c04a 100644 --- a/src/SerializeProto.h +++ b/src/SerializeProto.h @@ -56,12 +56,11 @@ FIELD(OfferSequence, UINT32, 25) // 64-bit integers - FIELD(Fee, UINT64, 1) - FIELD(IndexNext, UINT64, 2) - FIELD(IndexPrevious, UINT64, 3) - FIELD(BookNode, UINT64, 4) - FIELD(OwnerNode, UINT64, 5) - FIELD(BaseFee, UINT64, 6) + FIELD(IndexNext, UINT64, 1) + FIELD(IndexPrevious, UINT64, 2) + FIELD(BookNode, UINT64, 3) + FIELD(OwnerNode, UINT64, 4) + FIELD(BaseFee, UINT64, 5) // 128-bit FIELD(EmailHash, HASH128, 1) @@ -89,6 +88,7 @@ FIELD(TakerGets, AMOUNT, 5) FIELD(LowLimit, AMOUNT, 6) FIELD(HighLimit, AMOUNT, 7) + FIELD(Fee, AMOUNT, 8) FIELD(SendMax, AMOUNT, 9) // current amount (uncommon) @@ -125,8 +125,8 @@ // inner object // OBJECT/1 is reserved for end of object - FIELD(InnerTransaction, OBJECT, 1) // array of objects // ARRAY/1 is reserved for end of array FIELD(SigningAccounts, ARRAY, 2) + FIELD(Signatures, ARRAY, 3) From 3f0c87588eef3c767a3ef2c66742a7cd09a35af1 Mon Sep 17 00:00:00 2001 From: JoelKatz Date: Fri, 28 Sep 2012 19:12:07 -0700 Subject: [PATCH 28/53] Small changes to support new transaction serialization code. --- src/Transaction.cpp | 9 ++------- src/TransactionEngine.cpp | 2 +- 2 files changed, 3 insertions(+), 8 deletions(-) diff --git a/src/Transaction.cpp b/src/Transaction.cpp index 526f433bf1..863e8e834c 100644 --- a/src/Transaction.cpp +++ b/src/Transaction.cpp @@ -18,7 +18,7 @@ Transaction::Transaction(const SerializedTransaction::pointer& sit, bool bValida { try { - mFromPubKey.setAccountPublic(mTransaction->peekSigningPubKey()); + mFromPubKey.setAccountPublic(mTransaction->getSigningPubKey()); mTransactionID = mTransaction->getTransactionID(); mAccountFrom = mTransaction->getSourceAccount(); } @@ -92,12 +92,7 @@ bool Transaction::sign(const NewcoinAddress& naAccountPrivate) Log(lsWARNING) << "No private key for signing"; bResult = false; } - else if (!getSTransaction()->sign(naAccountPrivate)) - { - Log(lsWARNING) << "Failed to make signature"; - assert(false); - bResult = false; - } + getSTransaction()->sign(naAccountPrivate); if (bResult) { diff --git a/src/TransactionEngine.cpp b/src/TransactionEngine.cpp index 3dc45c7c15..55f252dda6 100644 --- a/src/TransactionEngine.cpp +++ b/src/TransactionEngine.cpp @@ -105,7 +105,7 @@ TER TransactionEngine::applyTransaction(const SerializedTransaction& txn, Transa NewcoinAddress naSigningPubKey; if (tesSUCCESS == terResult) - naSigningPubKey = NewcoinAddress::createAccountPublic(txn.peekSigningPubKey()); + naSigningPubKey = NewcoinAddress::createAccountPublic(txn.setSigningPubKey()); // Consistency: really signed. if ((tesSUCCESS == terResult) && !isSetBit(params, tapNO_CHECK_SIGN) && !txn.checkSign(naSigningPubKey)) From dc2e47b67c175687401fa0e7242ed80199888b74 Mon Sep 17 00:00:00 2001 From: JoelKatz Date: Fri, 28 Sep 2012 19:12:38 -0700 Subject: [PATCH 29/53] Hash functions. --- src/SerializedObject.cpp | 10 +++++----- src/SerializedObject.h | 2 +- 2 files changed, 6 insertions(+), 6 deletions(-) diff --git a/src/SerializedObject.cpp b/src/SerializedObject.cpp index cc6f6f9136..20f0835e24 100644 --- a/src/SerializedObject.cpp +++ b/src/SerializedObject.cpp @@ -131,7 +131,7 @@ void STObject::set(SOElement::ptr elem) void STObject::setType(SOElement::ptrList t) { - mData.empty(); + mType.empty(); while (t->flags != SOE_END) mType.push_back(t++); } @@ -239,9 +239,9 @@ void STObject::add(Serializer& s, bool withSigningFields) const field->addFieldID(s); field->add(s); - if (dynamic_cast(field) != NULL) + if (dynamic_cast(field) != NULL) s.addFieldID(STI_ARRAY, 1); - else if (dynamic_cast(field) != NULL) + else if (dynamic_cast(field) != NULL) s.addFieldID(STI_OBJECT, 1); } } @@ -279,7 +279,7 @@ bool STObject::isEquivalent(const SerializedType& t) const return (it1 == end1) && (it2 == end2); } -uint256 getHash(uint32 prefix) cosnt +uint256 STObject::getHash(uint32 prefix) const { Serializer s; s.add32(prefix); @@ -287,7 +287,7 @@ uint256 getHash(uint32 prefix) cosnt return s.getSHA512Half(); } -uint256 getSigningHash(uint32 prefix) cosnt +uint256 STObject::getSigningHash(uint32 prefix) const { Serializer s; s.add32(prefix); diff --git a/src/SerializedObject.h b/src/SerializedObject.h index adb054586b..c69f18d3a9 100644 --- a/src/SerializedObject.h +++ b/src/SerializedObject.h @@ -55,7 +55,7 @@ public: virtual bool isEquivalent(const SerializedType& t) const; virtual void add(Serializer& s) const { add(s, true); } // just inner elements - void add(Serializer& s, int withSignature) const; + void add(Serializer& s, bool withSignature) const; Serializer getSerializer() const { Serializer s; add(s); return s; } std::string getFullText() const; std::string getText() const; From 01c164c6fbdb796ff241c8fcdd19305006756b5b Mon Sep 17 00:00:00 2001 From: JoelKatz Date: Fri, 28 Sep 2012 19:12:56 -0700 Subject: [PATCH 30/53] Rewrite a lot of the SerializedTransaction code. Mostly just removing obsolete code. --- src/SerializedTransaction.cpp | 241 +++++++--------------------------- src/SerializedTransaction.h | 105 +++++++-------- src/TransactionFormats.h | 6 - 3 files changed, 91 insertions(+), 261 deletions(-) diff --git a/src/SerializedTransaction.cpp b/src/SerializedTransaction.cpp index b8a5f96c9a..5d1bdc6fe2 100644 --- a/src/SerializedTransaction.cpp +++ b/src/SerializedTransaction.cpp @@ -7,21 +7,16 @@ #include "Log.h" #include "HashPrefixes.h" -SerializedTransaction::SerializedTransaction(TransactionType type) : mType(type) +SerializedTransaction::SerializedTransaction(TransactionType type) : STObject(sfTransaction), mType(type) { mFormat = getTxnFormat(type); - if (mFormat == NULL) throw std::runtime_error("invalid transaction type"); - - mMiddleTxn.giveObject(new STVariableLength(sfSigningPubKey)); - mMiddleTxn.giveObject(new STAccount(sfAccount)); - mMiddleTxn.giveObject(new STUInt32(sfSequence)); - mMiddleTxn.giveObject(new STUInt16(sfTransactionType, static_cast(type))); - mMiddleTxn.giveObject(new STAmount(sfFee)); - - mInnerTxn = STObject(mFormat->elements, sfInnerTransaction); + if (mFormat == NULL) + throw std::runtime_error("invalid transaction type"); + set(mFormat->elements); + setValueFieldU16(sfTransactionType, mFormat->t_type); } -SerializedTransaction::SerializedTransaction(SerializerIterator& sit) +SerializedTransaction::SerializedTransaction(SerializerIterator& sit) : STObject(sfTransaction) { int length = sit.getBytesLeft(); if ((length < TransactionMinLen) || (length > TransactionMaxLen)) @@ -30,27 +25,18 @@ SerializedTransaction::SerializedTransaction(SerializerIterator& sit) throw std::runtime_error("Transaction length invalid"); } - mSignature.setValue(sit.getVL()); + set(sit); + mType = static_cast(getValueFieldU16(sfTransactionType)); - mMiddleTxn.giveObject(new STVariableLength(sfSigningPubKey, sit.getVL())); - - STAccount sa(sfAccount, sit.getVL()); - mSourceAccount = sa.getValueNCA(); - mMiddleTxn.giveObject(new STAccount(sa)); - - mMiddleTxn.giveObject(new STUInt32(sfSequence, sit.get32())); - - mType = static_cast(sit.get16()); - mMiddleTxn.giveObject(new STUInt16(sfTransactionType, static_cast(mType))); mFormat = getTxnFormat(mType); if (!mFormat) + throw std::runtime_error("invalid transction type"); + setType(mFormat->elements); + if (!isValidForType()) { - Log(lsERROR) << "Transaction has invalid type"; - throw std::runtime_error("Transaction has invalid type"); + Log(lsDEBUG) << "Transaction not valid for type " << getJson(0); + throw std::runtime_error("transaction not valid"); } - mMiddleTxn.giveObject(STAmount::deserialize(sit, sfFee)); - - mInnerTxn = STObject(mFormat->elements, sit, sfInnerTransaction); } std::string SerializedTransaction::getFullText() const @@ -58,29 +44,21 @@ std::string SerializedTransaction::getFullText() const std::string ret = "\""; ret += getTransactionID().GetHex(); ret += "\" = {"; - ret += mSignature.getFullText(); - ret += mMiddleTxn.getFullText(); - ret += mInnerTxn.getFullText(); + ret += STObject::getFullText(); ret += "}"; return ret; } std::string SerializedTransaction::getText() const { - std::string ret = "{"; - ret += mSignature.getText(); - ret += mMiddleTxn.getText(); - ret += mInnerTxn.getText(); - ret += "}"; - return ret; + return STObject::getText(); } std::vector SerializedTransaction::getAffectedAccounts() const { std::vector accounts; - accounts.push_back(mSourceAccount); - BOOST_FOREACH(const SerializedType& it, mInnerTxn.peekData()) + BOOST_FOREACH(const SerializedType& it, peekData()) { const STAccount* sa = dynamic_cast(&it); if (sa != NULL) @@ -103,197 +81,70 @@ std::vector SerializedTransaction::getAffectedAccounts() const return accounts; } -void SerializedTransaction::add(Serializer& s) const -{ - mSignature.add(s); - mMiddleTxn.add(s); - mInnerTxn.add(s); -} - -bool SerializedTransaction::isEquivalent(const SerializedType& t) const -{ // Signatures are not compared - const SerializedTransaction* v = dynamic_cast(&t); - if (!v) return false; - if (mType != v->mType) return false; - if (mMiddleTxn != v->mMiddleTxn) return false; - if (mInnerTxn != v->mInnerTxn) return false; - return true; -} - uint256 SerializedTransaction::getSigningHash() const { - Serializer s; - s.add32(sHP_TransactionSign); - mMiddleTxn.add(s); - mInnerTxn.add(s); - return s.getSHA512Half(); + return STObject::getSigningHash(sHP_TransactionSign); } uint256 SerializedTransaction::getTransactionID() const { // perhaps we should cache this - Serializer s; - s.add32(sHP_TransactionID); - mSignature.add(s); - mMiddleTxn.add(s); - mInnerTxn.add(s); - return s.getSHA512Half(); + return getHash(sHP_TransactionID); } std::vector SerializedTransaction::getSignature() const { - return mSignature.getValue(); + try + { + return getValueFieldVL(sfSignature); + } + catch (...) + { + return std::vector(); + } } -const std::vector& SerializedTransaction::peekSignature() const +void SerializedTransaction::sign(const NewcoinAddress& naAccountPrivate) { - return mSignature.peekValue(); -} - -bool SerializedTransaction::sign(const NewcoinAddress& naAccountPrivate) -{ - return naAccountPrivate.accountPrivateSign(getSigningHash(), mSignature.peekValue()); + std::vector signature; + naAccountPrivate.accountPrivateSign(getSigningHash(), signature); + setValueFieldVL(sfSignature, signature); } bool SerializedTransaction::checkSign(const NewcoinAddress& naAccountPublic) const { - return naAccountPublic.accountPublicVerify(getSigningHash(), mSignature.getValue()); + try + { + return naAccountPublic.accountPublicVerify(getSigningHash(), getValueFieldVL(sfSignature)); + } + catch (...) + { + return false; + } } -void SerializedTransaction::setSignature(const std::vector& sig) +void SerializedTransaction::setSigningPubKey(const NewcoinAddress& naSignPubKey) { - mSignature.setValue(sig); + setValueFieldVL(sfSigningPubKey, naSignPubKey.getAccountPublic()); } -STAmount SerializedTransaction::getTransactionFee() const +void SerializedTransaction::setSourceAccount(const NewcoinAddress& naSource) { - const STAmount* v = dynamic_cast(mMiddleTxn.peekAtPIndex(TransactionIFee)); - if (!v) throw std::runtime_error("corrupt transaction"); - return *v; -} - -void SerializedTransaction::setTransactionFee(const STAmount& fee) -{ - STAmount* v = dynamic_cast(mMiddleTxn.getPIndex(TransactionIFee)); - if (!v) throw std::runtime_error("corrupt transaction"); - v->setValue(fee); -} - -uint32 SerializedTransaction::getSequence() const -{ - const STUInt32* v = dynamic_cast(mMiddleTxn.peekAtPIndex(TransactionISequence)); - if (!v) throw std::runtime_error("corrupt transaction"); - return v->getValue(); -} - -void SerializedTransaction::setSequence(uint32 seq) -{ - STUInt32* v = dynamic_cast(mMiddleTxn.getPIndex(TransactionISequence)); - if (!v) throw std::runtime_error("corrupt transaction"); - v->setValue(seq); -} - -std::vector SerializedTransaction::getSigningPubKey() const -{ - const STVariableLength* v = - dynamic_cast(mMiddleTxn.peekAtPIndex(TransactionISigningPubKey)); - if (!v) throw std::runtime_error("corrupt transaction"); - return v->getValue(); -} - -const std::vector& SerializedTransaction::peekSigningPubKey() const -{ - const STVariableLength* v= - dynamic_cast(mMiddleTxn.peekAtPIndex(TransactionISigningPubKey)); - if (!v) throw std::runtime_error("corrupt transaction"); - return v->peekValue(); -} - -std::vector& SerializedTransaction::peekSigningPubKey() -{ - STVariableLength* v = dynamic_cast(mMiddleTxn.getPIndex(TransactionISigningPubKey)); - if (!v) throw std::runtime_error("corrupt transaction"); - return v->peekValue(); -} - -const NewcoinAddress& SerializedTransaction::setSigningPubKey(const NewcoinAddress& naSignPubKey) -{ - mSignPubKey = naSignPubKey; - - STVariableLength* v = dynamic_cast(mMiddleTxn.getPIndex(TransactionISigningPubKey)); - if (!v) throw std::runtime_error("corrupt transaction"); - v->setValue(mSignPubKey.getAccountPublic()); - - return mSignPubKey; -} - -const NewcoinAddress& SerializedTransaction::setSourceAccount(const NewcoinAddress& naSource) -{ - mSourceAccount = naSource; - - STAccount* v = dynamic_cast(mMiddleTxn.getPIndex(TransactionISourceID)); - if (!v) throw std::runtime_error("corrupt transaction"); - v->setValueNCA(mSourceAccount); - return mSourceAccount; + setValueFieldAccount(sfAccount, naSource); } uint160 SerializedTransaction::getITFieldAccount(SField::ref field) const { uint160 r; - const SerializedType* st = mInnerTxn.peekAtPField(field); - if (!st) return r; - - const STAccount* ac = dynamic_cast(st); - if (!ac) return r; - ac->getValueH160(r); + const STAccount* ac = dynamic_cast(peekAtPField(field)); + if (ac) + ac->getValueH160(r); return r; } -int SerializedTransaction::getITFieldIndex(SField::ref field) const -{ - return mInnerTxn.getFieldIndex(field); -} - -int SerializedTransaction::getITFieldCount() const -{ - return mInnerTxn.getCount(); -} - -bool SerializedTransaction::getITFieldPresent(SField::ref field) const -{ - return mInnerTxn.isFieldPresent(field); -} - -const SerializedType& SerializedTransaction::peekITField(SField::ref field) const -{ - return mInnerTxn.peekAtField(field); -} - -SerializedType& SerializedTransaction::getITField(SField::ref field) -{ - return mInnerTxn.getField(field); -} - -void SerializedTransaction::makeITFieldPresent(SField::ref field) -{ - mInnerTxn.makeFieldPresent(field); -} - -void SerializedTransaction::makeITFieldAbsent(SField::ref field) -{ - return mInnerTxn.makeFieldAbsent(field); -} - Json::Value SerializedTransaction::getJson(int options) const { - Json::Value ret = Json::objectValue; + Json::Value ret = STObject::getJson(0); ret["id"] = getTransactionID().GetHex(); - ret["signature"] = mSignature.getText(); - - Json::Value middle = mMiddleTxn.getJson(options); - middle["type"] = mFormat->t_name; - ret["middle"] = middle; - - ret["inner"] = mInnerTxn.getJson(options); return ret; } diff --git a/src/SerializedTransaction.h b/src/SerializedTransaction.h index ce997b5b8c..953cf20947 100644 --- a/src/SerializedTransaction.h +++ b/src/SerializedTransaction.h @@ -17,17 +17,13 @@ #define TXN_SQL_INCLUDED 'I' #define TXN_SQL_UNKNOWN 'U' -class SerializedTransaction : public SerializedType +class SerializedTransaction : public STObject { public: typedef boost::shared_ptr pointer; protected: - NewcoinAddress mSignPubKey; - NewcoinAddress mSourceAccount; TransactionType mType; - STVariableLength mSignature; - STObject mMiddleTxn, mInnerTxn; const TransactionFormat* mFormat; SerializedTransaction* duplicate() const { return new SerializedTransaction(*this); } @@ -40,80 +36,69 @@ public: SerializedTypeID getSType() const { return STI_TRANSACTION; } std::string getFullText() const; std::string getText() const; - void add(Serializer& s) const; - virtual bool isEquivalent(const SerializedType& t) const; // outer transaction functions / signature functions std::vector getSignature() const; - const std::vector& peekSignature() const; - void setSignature(const std::vector& s); + void setSignature(const std::vector& s) { setValueFieldVL(sfSignature, s); } uint256 getSigningHash() const; - TransactionType getTxnType() const { return mType; } - STAmount getTransactionFee() const; - void setTransactionFee(const STAmount& fee); + TransactionType getTxnType() const { return mType; } + STAmount getTransactionFee() const { return getValueFieldAmount(sfFee); } + void setTransactionFee(const STAmount& fee) { setValueFieldAmount(sfFee, fee); } - const NewcoinAddress& getSourceAccount() const { return mSourceAccount; } + NewcoinAddress getSourceAccount() const { return getValueFieldAccount(sfAccount); } std::vector getSigningPubKey() const; - const std::vector& peekSigningPubKey() const; - std::vector& peekSigningPubKey(); - const NewcoinAddress& setSigningPubKey(const NewcoinAddress& naSignPubKey); - const NewcoinAddress& setSourceAccount(const NewcoinAddress& naSource); + void setSigningPubKey(const NewcoinAddress& naSignPubKey); + void setSourceAccount(const NewcoinAddress& naSource); std::string getTransactionType() const { return mFormat->t_name; } - // inner transaction functions - uint32 getFlags() const { return mInnerTxn.getFlags(); } - void setFlag(uint32 v) { mInnerTxn.setFlag(v); } - void clearFlag(uint32 v) { mInnerTxn.clearFlag(v); } + uint32 getSequence() const { return getValueFieldU32(sfSequence); } + void setSequence(uint32 seq) { return setValueFieldU32(sfSequence, seq); } - uint32 getSequence() const; - void setSequence(uint32); + // inner transaction field functions (OBSOLETE - use STObject functions) + int getITFieldIndex(SField::ref field) const { return getFieldIndex(field); } + const SerializedType& peekITField(SField::ref field) const { return peekAtField(field); } + SerializedType& getITField(SField::ref field) { return getField(field); } - // inner transaction field functions - int getITFieldIndex(SField::ref field) const; - int getITFieldCount() const; - const SerializedType& peekITField(SField::ref field) const; - SerializedType& getITField(SField::ref field); - - // inner transaction field value functions - std::string getITFieldString(SField::ref field) const { return mInnerTxn.getFieldString(field); } - unsigned char getITFieldU8(SField::ref field) const { return mInnerTxn.getValueFieldU8(field); } - uint16 getITFieldU16(SField::ref field) const { return mInnerTxn.getValueFieldU16(field); } - uint32 getITFieldU32(SField::ref field) const { return mInnerTxn.getValueFieldU32(field); } - uint64 getITFieldU64(SField::ref field) const { return mInnerTxn.getValueFieldU64(field); } - uint128 getITFieldH128(SField::ref field) const { return mInnerTxn.getValueFieldH128(field); } - uint160 getITFieldH160(SField::ref field) const { return mInnerTxn.getValueFieldH160(field); } + // inner transaction field value functions (OBSOLETE - use STObject functions) + std::string getITFieldString(SField::ref field) const { return getFieldString(field); } + unsigned char getITFieldU8(SField::ref field) const { return getValueFieldU8(field); } + uint16 getITFieldU16(SField::ref field) const { return getValueFieldU16(field); } + uint32 getITFieldU32(SField::ref field) const { return getValueFieldU32(field); } + uint64 getITFieldU64(SField::ref field) const { return getValueFieldU64(field); } + uint128 getITFieldH128(SField::ref field) const { return getValueFieldH128(field); } + uint160 getITFieldH160(SField::ref field) const { return getValueFieldH160(field); } uint160 getITFieldAccount(SField::ref field) const; - uint256 getITFieldH256(SField::ref field) const { return mInnerTxn.getValueFieldH256(field); } - std::vector getITFieldVL(SField::ref field) const { return mInnerTxn.getValueFieldVL(field); } - std::vector getITFieldTL(SField::ref field) const { return mInnerTxn.getValueFieldTL(field); } - STAmount getITFieldAmount(SField::ref field) const { return mInnerTxn.getValueFieldAmount(field); } - STPathSet getITFieldPathSet(SField::ref field) const { return mInnerTxn.getValueFieldPathSet(field); } + uint256 getITFieldH256(SField::ref field) const { return getValueFieldH256(field); } + std::vector getITFieldVL(SField::ref field) const { return getValueFieldVL(field); } + std::vector getITFieldTL(SField::ref field) const { return getValueFieldTL(field); } + STAmount getITFieldAmount(SField::ref field) const { return getValueFieldAmount(field); } + STPathSet getITFieldPathSet(SField::ref field) const { return getValueFieldPathSet(field); } - void setITFieldU8(SField::ref field, unsigned char v) { return mInnerTxn.setValueFieldU8(field, v); } - void setITFieldU16(SField::ref field, uint16 v) { return mInnerTxn.setValueFieldU16(field, v); } - void setITFieldU32(SField::ref field, uint32 v) { return mInnerTxn.setValueFieldU32(field, v); } - void setITFieldU64(SField::ref field, uint32 v) { return mInnerTxn.setValueFieldU64(field, v); } - void setITFieldH128(SField::ref field, const uint128& v) { return mInnerTxn.setValueFieldH128(field, v); } - void setITFieldH160(SField::ref field, const uint160& v) { return mInnerTxn.setValueFieldH160(field, v); } - void setITFieldH256(SField::ref field, const uint256& v) { return mInnerTxn.setValueFieldH256(field, v); } + void setITFieldU8(SField::ref field, unsigned char v) { return setValueFieldU8(field, v); } + void setITFieldU16(SField::ref field, uint16 v) { return setValueFieldU16(field, v); } + void setITFieldU32(SField::ref field, uint32 v) { return setValueFieldU32(field, v); } + void setITFieldU64(SField::ref field, uint32 v) { return setValueFieldU64(field, v); } + void setITFieldH128(SField::ref field, const uint128& v) { return setValueFieldH128(field, v); } + void setITFieldH160(SField::ref field, const uint160& v) { return setValueFieldH160(field, v); } + void setITFieldH256(SField::ref field, const uint256& v) { return setValueFieldH256(field, v); } void setITFieldVL(SField::ref field, const std::vector& v) - { return mInnerTxn.setValueFieldVL(field, v); } + { return setValueFieldVL(field, v); } void setITFieldTL(SField::ref field, const std::vector& v) - { return mInnerTxn.setValueFieldTL(field, v); } + { return setValueFieldTL(field, v); } void setITFieldAccount(SField::ref field, const uint160& v) - { return mInnerTxn.setValueFieldAccount(field, v); } + { return setValueFieldAccount(field, v); } void setITFieldAccount(SField::ref field, const NewcoinAddress& v) - { return mInnerTxn.setValueFieldAccount(field, v); } + { return setValueFieldAccount(field, v); } void setITFieldAmount(SField::ref field, const STAmount& v) - { return mInnerTxn.setValueFieldAmount(field, v); } + { return setValueFieldAmount(field, v); } void setITFieldPathSet(SField::ref field, const STPathSet& v) - { return mInnerTxn.setValueFieldPathSet(field, v); } + { return setValueFieldPathSet(field, v); } - // optional field functions - bool getITFieldPresent(SField::ref field) const; - void makeITFieldPresent(SField::ref field); - void makeITFieldAbsent(SField::ref field); + // optional field functions (OBSOLETE - use STObject functions) + bool getITFieldPresent(SField::ref field) const { return isFieldPresent(field); } + void makeITFieldPresent(SField::ref field) { makeFieldPresent(field); } + void makeITFieldAbsent(SField::ref field) { makeFieldAbsent(field); } std::vector getAffectedAccounts() const; @@ -121,7 +106,7 @@ public: virtual Json::Value getJson(int options) const; - bool sign(const NewcoinAddress& naAccountPrivate); + void sign(const NewcoinAddress& naAccountPrivate); bool checkSign(const NewcoinAddress& naAccountPublic) const; // SQL Functions diff --git a/src/TransactionFormats.h b/src/TransactionFormats.h index 0efaf03397..edbccf3a69 100644 --- a/src/TransactionFormats.h +++ b/src/TransactionFormats.h @@ -28,12 +28,6 @@ struct TransactionFormat SOElement elements[24]; }; -const int TransactionISigningPubKey = 0; -const int TransactionISourceID = 1; -const int TransactionISequence = 2; -const int TransactionIType = 3; -const int TransactionIFee = 4; - const int TransactionMinLen = 32; const int TransactionMaxLen = 1048576; From 2b0c95a83811661ce6b8742986b4c748863b8c78 Mon Sep 17 00:00:00 2001 From: JoelKatz Date: Fri, 28 Sep 2012 19:13:34 -0700 Subject: [PATCH 31/53] Typo. --- src/TransactionEngine.cpp | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/src/TransactionEngine.cpp b/src/TransactionEngine.cpp index 55f252dda6..8847ca87e1 100644 --- a/src/TransactionEngine.cpp +++ b/src/TransactionEngine.cpp @@ -105,7 +105,7 @@ TER TransactionEngine::applyTransaction(const SerializedTransaction& txn, Transa NewcoinAddress naSigningPubKey; if (tesSUCCESS == terResult) - naSigningPubKey = NewcoinAddress::createAccountPublic(txn.setSigningPubKey()); + naSigningPubKey = NewcoinAddress::createAccountPublic(txn.getSigningPubKey()); // Consistency: really signed. if ((tesSUCCESS == terResult) && !isSetBit(params, tapNO_CHECK_SIGN) && !txn.checkSign(naSigningPubKey)) From ebf3aeee64e23ce61c7e16563b4c25a401266504 Mon Sep 17 00:00:00 2001 From: JoelKatz Date: Fri, 28 Sep 2012 19:14:21 -0700 Subject: [PATCH 32/53] Remove infinite loop. --- src/SerializedLedger.cpp | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/src/SerializedLedger.cpp b/src/SerializedLedger.cpp index 824f77145b..db21fe47dd 100644 --- a/src/SerializedLedger.cpp +++ b/src/SerializedLedger.cpp @@ -46,7 +46,7 @@ std::string SerializedLedgerEntry::getFullText() const ret += "\" = { "; ret += mFormat->t_name; ret += ", "; - ret += getFullText(); + ret += STObject::getFullText(); ret += "}"; return ret; } From 16ea43d60cd6323d4ce93de7f76b3a910593095b Mon Sep 17 00:00:00 2001 From: JoelKatz Date: Fri, 28 Sep 2012 19:26:36 -0700 Subject: [PATCH 33/53] Fixups. --- src/SerializedLedger.cpp | 7 ++++--- 1 file changed, 4 insertions(+), 3 deletions(-) diff --git a/src/SerializedLedger.cpp b/src/SerializedLedger.cpp index 38781b503b..b2cd4f95ce 100644 --- a/src/SerializedLedger.cpp +++ b/src/SerializedLedger.cpp @@ -133,14 +133,14 @@ std::vector SerializedLedgerEntry::getOwners() for (int i = 0, fields = getCount(); i < fields; ++i) { - int fc = getFieldSType(i).fieldCode; - if ((fc == sfAccount.fieldCode) || (fc == sfOwner.fieldCode)) + SField::ref fc = getFieldSType(i); + if ((fc == sfAccount) || (fc == sfOwner)) { const STAccount* entry = dynamic_cast(peekAtPIndex(i)); if ((entry != NULL) && entry->getValueH160(account)) owners.push_back(Ledger::getAccountRootIndex(account)); } - if ((fc == sfLowLimit.fieldCode) || (fs == sfHighLimit.fieldCode)) + if ((fc == sfLowLimit) || (fc == sfHighLimit)) { const STAmount* entry = dynamic_cast(peekAtPIndex(i)); if ((entry != NULL)) @@ -148,6 +148,7 @@ std::vector SerializedLedgerEntry::getOwners() uint160 issuer = entry->getIssuer(); if (issuer.isNonZero()) owners.push_back(Ledger::getAccountRootIndex(issuer)); + } } } From 431ba3033520bf9405c65df1dd15ba76d0aebc67 Mon Sep 17 00:00:00 2001 From: JoelKatz Date: Fri, 28 Sep 2012 19:34:21 -0700 Subject: [PATCH 34/53] Missing function. --- src/SerializedTransaction.h | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/src/SerializedTransaction.h b/src/SerializedTransaction.h index 953cf20947..8153a76487 100644 --- a/src/SerializedTransaction.h +++ b/src/SerializedTransaction.h @@ -47,7 +47,7 @@ public: void setTransactionFee(const STAmount& fee) { setValueFieldAmount(sfFee, fee); } NewcoinAddress getSourceAccount() const { return getValueFieldAccount(sfAccount); } - std::vector getSigningPubKey() const; + std::vector getSigningPubKey() const { return getValueFieldVL(sfSigningPubKey); } void setSigningPubKey(const NewcoinAddress& naSignPubKey); void setSourceAccount(const NewcoinAddress& naSource); std::string getTransactionType() const { return mFormat->t_name; } From cc8d470e2134817f3dacb88a26e84977bdd07919 Mon Sep 17 00:00:00 2001 From: JoelKatz Date: Fri, 28 Sep 2012 22:39:43 -0700 Subject: [PATCH 35/53] Bugfix., --- src/SerializedTypes.h | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/src/SerializedTypes.h b/src/SerializedTypes.h index 5748f960ec..9852735e35 100644 --- a/src/SerializedTypes.h +++ b/src/SerializedTypes.h @@ -219,7 +219,7 @@ protected: STAmount(bool isNeg, uint64 value) : mValue(value), mOffset(0), mIsNative(true), mIsNegative(isNeg) { ; } STAmount(SField::ref name, uint64 value, bool isNegative) - : SerializedType(fName), mValue(value), mOffset(0), mIsNative(true), mIsNegative(isNegative) + : SerializedType(name), mValue(value), mOffset(0), mIsNative(true), mIsNegative(isNegative) { ; } STAmount(SField::ref name, const uint160& cur, const uint160& iss, uint64 val, int off, bool isNat, bool isNeg) : SerializedType(name), mCurrency(cur), mIssuer(iss), mValue(val), mOffset(off), From 079d376390070dafc4b78f166d2b0da1f30bec10 Mon Sep 17 00:00:00 2001 From: JoelKatz Date: Fri, 28 Sep 2012 22:40:00 -0700 Subject: [PATCH 36/53] Bugfix. --- src/SerializeProto.h | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/src/SerializeProto.h b/src/SerializeProto.h index fe8778c04a..2b1050bb41 100644 --- a/src/SerializeProto.h +++ b/src/SerializeProto.h @@ -27,7 +27,7 @@ // 16-bit integers FIELD(LedgerEntryType, UINT16, 1) - FIELD(TransactionType, UINT16, 1) + FIELD(TransactionType, UINT16, 2) // 32-bit integers (common) FIELD(ObjectType, UINT32, 1) From 609edfddbd672504e9d949c5e149bc51503d7b77 Mon Sep 17 00:00:00 2001 From: JoelKatz Date: Fri, 28 Sep 2012 22:40:14 -0700 Subject: [PATCH 37/53] Cleanups. --- src/Amount.cpp | 23 +++++++---------------- src/SerializedObject.cpp | 3 ++- 2 files changed, 9 insertions(+), 17 deletions(-) diff --git a/src/Amount.cpp b/src/Amount.cpp index bfcad54d37..c398e49f3f 100644 --- a/src/Amount.cpp +++ b/src/Amount.cpp @@ -325,7 +325,8 @@ void STAmount::setValue(const STAmount &a) uint64 STAmount::toUInt64() const { // makes them sort easily - if (mValue == 0) return 0x4000000000000000ull; + if (mValue == 0) + return 0x4000000000000000ull; if (mIsNegative) return mValue | (static_cast(mOffset + 97) << (64 - 10)); return mValue | (static_cast(mOffset + 256 + 97) << (64 - 10)); @@ -351,8 +352,6 @@ STAmount* STAmount::construct(SerializerIterator& sit, SField::ref name) int offset = static_cast(value >> (64 - 10)); // 10 bits for the offset, sign and "not native" flag value &= ~(1023ull << (64-10)); - STAmount* sapResult; - if (value) { bool isNegative = (offset & 256) == 0; @@ -360,17 +359,12 @@ STAmount* STAmount::construct(SerializerIterator& sit, SField::ref name) if ((value < cMinValue) || (value > cMaxValue) || (offset < cMinOffset) || (offset > cMaxOffset)) throw std::runtime_error("invalid currency value"); - sapResult = new STAmount(name, uCurrencyID, uIssuerID, value, offset, isNegative); - } - else - { - if (offset != 512) - throw std::runtime_error("invalid currency value"); - - sapResult = new STAmount(name, uCurrencyID, uIssuerID); + return new STAmount(name, uCurrencyID, uIssuerID, value, offset, isNegative); } - return sapResult; + if (offset != 512) + throw std::runtime_error("invalid currency value"); + return new STAmount(name, uCurrencyID, uIssuerID); } int64 STAmount::getSNValue() const @@ -890,11 +884,8 @@ STAmount STAmount::convertToInternalAmount(uint64 displayAmount, uint64 totalNow STAmount STAmount::deserialize(SerializerIterator& it) { - STAmount *s = construct(it, sfGeneric); + auto_ptr s = construct(it, sfGeneric); STAmount ret(*s); - - delete s; - return ret; } diff --git a/src/SerializedObject.cpp b/src/SerializedObject.cpp index 20f0835e24..8d5fc3ec18 100644 --- a/src/SerializedObject.cpp +++ b/src/SerializedObject.cpp @@ -677,7 +677,8 @@ Json::Value STObject::getJson(int options) const { if (it.getName() == NULL) ret[boost::lexical_cast(index)] = it.getJson(options); - else ret[it.getName()] = it.getJson(options); + else + ret[it.getName()] = it.getJson(options); } } return ret; From b6c73c87d41e97ffd8f9daa3652394d7cd30adb7 Mon Sep 17 00:00:00 2001 From: JoelKatz Date: Fri, 28 Sep 2012 23:35:40 -0700 Subject: [PATCH 38/53] auto_ptr semantics are a bit odd --- src/Amount.cpp | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/src/Amount.cpp b/src/Amount.cpp index c398e49f3f..28f3516cf3 100644 --- a/src/Amount.cpp +++ b/src/Amount.cpp @@ -884,7 +884,7 @@ STAmount STAmount::convertToInternalAmount(uint64 displayAmount, uint64 totalNow STAmount STAmount::deserialize(SerializerIterator& it) { - auto_ptr s = construct(it, sfGeneric); + std::auto_ptr s(dynamic_cast(construct(it, sfGeneric))); STAmount ret(*s); return ret; } From aa8401066efb53d3184d579c1c98c96322a7f758 Mon Sep 17 00:00:00 2001 From: JoelKatz Date: Fri, 28 Sep 2012 23:48:19 -0700 Subject: [PATCH 39/53] Bugfixes. --- src/SerializedObject.cpp | 19 +++++++++++-------- 1 file changed, 11 insertions(+), 8 deletions(-) diff --git a/src/SerializedObject.cpp b/src/SerializedObject.cpp index 8d5fc3ec18..e77c756e1a 100644 --- a/src/SerializedObject.cpp +++ b/src/SerializedObject.cpp @@ -298,8 +298,12 @@ uint256 STObject::getSigningHash(uint32 prefix) const int STObject::getFieldIndex(SField::ref field) const { int i = 0; - for (std::vector::const_iterator it = mType.begin(), end = mType.end(); it != end; ++it, ++i) - if ((*it)->e_field == field) return i; + BOOST_FOREACH(const SerializedType& elem, mData) + { + if (elem.getFName() == field) + return i; + ++i; + } return -1; } @@ -321,7 +325,7 @@ SerializedType& STObject::getField(SField::ref field) SField::ref STObject::getFieldSType(int index) const { - return mType[index]->e_field; + return mData[index].getFName(); } const SerializedType* STObject::peekAtPField(SField::ref field) const @@ -383,7 +387,7 @@ SerializedType* STObject::makeFieldPresent(SField::ref field) SerializedType* f = getPIndex(index); if (f->getSType() != STI_NOTPRESENT) return f; - mData.replace(index, makeDefaultObject(mType[index]->e_field)); + mData.replace(index, makeDefaultObject(f->getFName())); return getPIndex(index); } @@ -392,13 +396,12 @@ void STObject::makeFieldAbsent(SField::ref field) int index = getFieldIndex(field); if (index == -1) throw std::runtime_error("Field not found"); - if (mType[index]->flags != SOE_OPTIONAL) - throw std::runtime_error("field is not optional"); - if (peekAtIndex(index).getSType() == STI_NOTPRESENT) + const SerializedType& f = peekAtIndex(index); + if (f.getSType() == STI_NOTPRESENT) return; - mData.replace(index, makeDefaultObject(mType[index]->e_field)); + mData.replace(index, makeDefaultObject(f.getFName())); } std::string STObject::getFieldString(SField::ref field) const From 29a5b60154188c5abfc2218230f3ce0e18cab6c7 Mon Sep 17 00:00:00 2001 From: JoelKatz Date: Sat, 29 Sep 2012 00:05:54 -0700 Subject: [PATCH 40/53] Fix txn signature breakage. --- src/SerializedObject.cpp | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/src/SerializedObject.cpp b/src/SerializedObject.cpp index e77c756e1a..4178ef0087 100644 --- a/src/SerializedObject.cpp +++ b/src/SerializedObject.cpp @@ -226,7 +226,7 @@ void STObject::add(Serializer& s, bool withSigningFields) const if (it.getSType() != STI_NOTPRESENT) { SField::ref fName = it.getFName(); - if (withSigningFields || (fName == sfSignature) || (fName == sfSignatures)) + if (withSigningFields || ((fName != sfSignature) && (fName != sfSignatures))) fields.insert(std::make_pair(it.getFName().fieldCode, &it)); } } From 135b4054e0b34f0c072d51130985bd9ae51511bf Mon Sep 17 00:00:00 2001 From: JoelKatz Date: Sat, 29 Sep 2012 00:06:08 -0700 Subject: [PATCH 41/53] Cleanup, remove dead code. --- src/NetworkOPs.cpp | 15 ++++++++------- 1 file changed, 8 insertions(+), 7 deletions(-) diff --git a/src/NetworkOPs.cpp b/src/NetworkOPs.cpp index 9988a03925..7985e2dbe6 100644 --- a/src/NetworkOPs.cpp +++ b/src/NetworkOPs.cpp @@ -83,17 +83,18 @@ uint32 NetworkOPs::getCurrentLedgerID() Transaction::pointer NetworkOPs::submitTransaction(const Transaction::pointer& tpTrans) { Serializer s; - tpTrans->getSTransaction()->add(s); - std::vector vucTransaction = s.getData(); - - SerializerIterator sit(s); - Transaction::pointer tpTransNew = Transaction::sharedTransaction(s.getData(), true); - assert(tpTransNew); - assert(tpTransNew->getSTransaction()->isEquivalent(*tpTrans->getSTransaction())); + + if(!tpTransNew->getSTransaction()->isEquivalent(*tpTrans->getSTransaction())) + { + Log(lsFATAL) << "Transaction reconstruction failure"; + Log(lsFATAL) << tpTransNew->getSTransaction()->getJson(0); + Log(lsFATAL) << tpTrans->getSTransaction()->getJson(0); + assert(false); + } (void) NetworkOPs::processTransaction(tpTransNew); From 4800899c478bbc5aee2b4e4fd3baab7277f224eb Mon Sep 17 00:00:00 2001 From: JoelKatz Date: Sat, 29 Sep 2012 00:06:17 -0700 Subject: [PATCH 42/53] Cleanup. bugfixes. --- src/TransactionFormats.cpp | 33 +++++---------------------------- 1 file changed, 5 insertions(+), 28 deletions(-) diff --git a/src/TransactionFormats.cpp b/src/TransactionFormats.cpp index 2216180dd6..3665af7d59 100644 --- a/src/TransactionFormats.cpp +++ b/src/TransactionFormats.cpp @@ -4,13 +4,16 @@ #define TF_BASE \ { sfTransactionType, SOE_REQUIRED }, \ { sfFlags, SOE_REQUIRED }, \ + { sfSourceTag, SOE_OPTIONAL }, \ + { sfAccount, SOE_REQUIRED }, \ + { sfSequence, SOE_REQUIRED }, \ + { sfFee, SOE_REQUIRED }, \ + { sfSigningPubKey, SOE_REQUIRED }, \ { sfSignature, SOE_OPTIONAL }, TransactionFormat InnerTxnFormats[]= { { "AccountSet", ttACCOUNT_SET, { TF_BASE - { sfFlags, SOE_REQUIRED }, - { sfSourceTag, SOE_OPTIONAL }, { sfEmailHash, SOE_OPTIONAL }, { sfWalletLocator, SOE_OPTIONAL }, { sfMessageKey, SOE_OPTIONAL }, @@ -21,17 +24,12 @@ TransactionFormat InnerTxnFormats[]= { sfInvalid, SOE_END } } }, { "Claim", ttCLAIM, { TF_BASE - { sfFlags, SOE_REQUIRED }, { sfGenerator, SOE_REQUIRED }, { sfPublicKey, SOE_REQUIRED }, - { sfSignature, SOE_REQUIRED }, - { sfSourceTag, SOE_OPTIONAL }, { sfInvalid, SOE_END } } }, { "CreditSet", ttCREDIT_SET, { TF_BASE - { sfFlags, SOE_REQUIRED }, { sfDestination, SOE_REQUIRED }, - { sfSourceTag, SOE_OPTIONAL }, { sfLimitAmount, SOE_OPTIONAL }, { sfQualityIn, SOE_OPTIONAL }, { sfQualityOut, SOE_OPTIONAL }, @@ -39,73 +37,53 @@ TransactionFormat InnerTxnFormats[]= }, /* { "Invoice", ttINVOICE, { TF_BASE - { sfFlags, SOE_REQUIRED }, { sfTarget, SOE_REQUIRED }, { sfAmount, SOE_REQUIRED }, - { sfSourceTag, SOE_OPTIONAL }, { sfDestination, SOE_OPTIONAL }, { sfIdentifier, SOE_OPTIONAL }, { sfInvalid, SOE_END } } }, */ { "NicknameSet", ttNICKNAME_SET, { TF_BASE - { sfFlags, SOE_REQUIRED }, { sfNickname, SOE_REQUIRED }, { sfMinimumOffer, SOE_OPTIONAL }, - { sfSignature, SOE_OPTIONAL }, - { sfSourceTag, SOE_OPTIONAL }, { sfInvalid, SOE_END } } }, { "OfferCreate", ttOFFER_CREATE, { TF_BASE - { sfFlags, SOE_REQUIRED}, { sfTakerPays, SOE_REQUIRED }, { sfTakerGets, SOE_REQUIRED }, - { sfSourceTag, SOE_OPTIONAL }, { sfExpiration, SOE_OPTIONAL }, { sfInvalid, SOE_END } } }, { "OfferCancel", ttOFFER_CANCEL, { TF_BASE - { sfFlags, SOE_REQUIRED }, { sfOfferSequence, SOE_REQUIRED }, - { sfSourceTag, SOE_OPTIONAL }, { sfInvalid, SOE_END } } }, { "PasswordFund", ttPASSWORD_FUND, { TF_BASE - { sfFlags, SOE_REQUIRED }, { sfDestination, SOE_REQUIRED }, - { sfSourceTag, SOE_OPTIONAL }, { sfInvalid, SOE_END } } }, { "PasswordSet", ttPASSWORD_SET, { TF_BASE - { sfFlags, SOE_REQUIRED }, { sfAuthorizedKey, SOE_REQUIRED }, { sfGenerator, SOE_REQUIRED }, { sfPublicKey, SOE_REQUIRED }, - { sfSignature, SOE_REQUIRED }, - { sfSourceTag, SOE_OPTIONAL }, { sfInvalid, SOE_END } } }, { "Payment", ttPAYMENT, { TF_BASE - { sfFlags, SOE_REQUIRED }, { sfDestination, SOE_REQUIRED }, { sfAmount, SOE_REQUIRED }, { sfSendMax, SOE_OPTIONAL }, { sfPaths, SOE_OPTIONAL }, - { sfSourceTag, SOE_OPTIONAL }, { sfInvoiceID, SOE_OPTIONAL }, { sfInvalid, SOE_END } } }, { "WalletAdd", ttWALLET_ADD, { TF_BASE - { sfFlags, SOE_REQUIRED }, { sfAmount, SOE_REQUIRED }, { sfAuthorizedKey, SOE_REQUIRED }, { sfPublicKey, SOE_REQUIRED }, - { sfSignature, SOE_REQUIRED }, - { sfSourceTag, SOE_OPTIONAL }, { sfInvalid, SOE_END } } }, { "Contract", ttCONTRACT, { TF_BASE - { sfFlags, SOE_REQUIRED }, { sfExpiration, SOE_REQUIRED }, { sfBondAmount, SOE_REQUIRED }, { sfStampEscrow, SOE_REQUIRED }, @@ -117,7 +95,6 @@ TransactionFormat InnerTxnFormats[]= { sfInvalid, SOE_END } } }, { "RemoveContract", ttCONTRACT_REMOVE, { TF_BASE - { sfFlags, SOE_REQUIRED }, { sfTarget, SOE_REQUIRED }, { sfInvalid, SOE_END } } }, From 3e305871c376ebb2c8391adb535664414c689dd8 Mon Sep 17 00:00:00 2001 From: JoelKatz Date: Sat, 29 Sep 2012 00:30:21 -0700 Subject: [PATCH 43/53] Missing sort. --- src/SerializedObject.cpp | 16 ++++++++++++++++ src/SerializedObject.h | 1 + 2 files changed, 17 insertions(+) diff --git a/src/SerializedObject.cpp b/src/SerializedObject.cpp index 4178ef0087..9cd320e06f 100644 --- a/src/SerializedObject.cpp +++ b/src/SerializedObject.cpp @@ -3,6 +3,7 @@ #include #include +#include #include "../json/writer.h" @@ -129,11 +130,26 @@ void STObject::set(SOElement::ptr elem) } } +bool STObject::compare(const SerializedType& f1, const SerializedType& f2) +{ + BOOST_FOREACH(SOElement::ptr elem, mType) + { + if (elem->e_field == f1.getFName()) // element one comes first + return true; + if (elem->e_field == f2.getFName()) // element two comes first + return false; + } + assert(false); + return false; +} + void STObject::setType(SOElement::ptrList t) { mType.empty(); while (t->flags != SOE_END) mType.push_back(t++); + + std::sort(mData.begin(), mData.end(), boost::bind(&STObject::compare, this, _1, _2)); } bool STObject::isValidForType() diff --git a/src/SerializedObject.h b/src/SerializedObject.h index c69f18d3a9..ee66681ee4 100644 --- a/src/SerializedObject.h +++ b/src/SerializedObject.h @@ -28,6 +28,7 @@ protected: std::vector mType; STObject* duplicate() const { return new STObject(*this); } + bool compare(const SerializedType& f1, const SerializedType& f2); public: STObject() { ; } From 98655aed4dd822f58024644a3d96582b7e8f3131 Mon Sep 17 00:00:00 2001 From: JoelKatz Date: Sat, 29 Sep 2012 01:30:17 -0700 Subject: [PATCH 44/53] Correctly check validity for type during setType. --- src/SerializedLedger.cpp | 6 ++-- src/SerializedObject.cpp | 67 ++++++++++++++++++++--------------- src/SerializedObject.h | 3 +- src/SerializedTransaction.cpp | 7 ++-- 4 files changed, 46 insertions(+), 37 deletions(-) diff --git a/src/SerializedLedger.cpp b/src/SerializedLedger.cpp index b2cd4f95ce..f96e96e2f9 100644 --- a/src/SerializedLedger.cpp +++ b/src/SerializedLedger.cpp @@ -14,7 +14,8 @@ SerializedLedgerEntry::SerializedLedgerEntry(SerializerIterator& sit, const uint if (mFormat == NULL) throw std::runtime_error("invalid ledger entry type"); mType = mFormat->t_type; - setType(mFormat->elements); + if (!setType(mFormat->elements)) + throw std::runtime_error("ledger entry not valid for type"); } SerializedLedgerEntry::SerializedLedgerEntry(const Serializer& s, const uint256& index) @@ -28,7 +29,8 @@ SerializedLedgerEntry::SerializedLedgerEntry(const Serializer& s, const uint256& if (mFormat == NULL) throw std::runtime_error("invalid ledger entry type"); mType = mFormat->t_type; - setType(mFormat->elements); + if (!setType(mFormat->elements)) + throw std::runtime_error("ledger entry not valid for type"); } SerializedLedgerEntry::SerializedLedgerEntry(LedgerEntryType type) : STObject(sfLedgerEntry), mType(type) diff --git a/src/SerializedObject.cpp b/src/SerializedObject.cpp index 9cd320e06f..c810c0de4d 100644 --- a/src/SerializedObject.cpp +++ b/src/SerializedObject.cpp @@ -130,46 +130,54 @@ void STObject::set(SOElement::ptr elem) } } -bool STObject::compare(const SerializedType& f1, const SerializedType& f2) +bool STObject::setType(SOElement::ptrList t) { - BOOST_FOREACH(SOElement::ptr elem, mType) - { - if (elem->e_field == f1.getFName()) // element one comes first - return true; - if (elem->e_field == f2.getFName()) // element two comes first - return false; - } - assert(false); - return false; -} + boost::ptr_vector newData; + bool valid = true; -void STObject::setType(SOElement::ptrList t) -{ mType.empty(); while (t->flags != SOE_END) - mType.push_back(t++); + { + bool match = false; + for (boost::ptr_vector::iterator it = mData.begin(); it != mData.end(); ++it) + if (it->getFName() == t->e_field) + { + match = true; + newData.push_back(mData.release(it).release()); + break; + } - std::sort(mData.begin(), mData.end(), boost::bind(&STObject::compare, this, _1, _2)); + if (!match) + { + if (t->flags != SOE_OPTIONAL) + { + Log(lsTRACE) << "setType !valid missing"; + valid = false; + } + newData.push_back(makeNonPresentObject(t->e_field)); + } + + mType.push_back(t++); + } + if (mData.size() != 0) + { + Log(lsTRACE) << "setType !valid leftover"; + valid = false; + } + mData.swap(newData); + return valid; } bool STObject::isValidForType() { + boost::ptr_vector::iterator it = mData.begin(); BOOST_FOREACH(SOElement::ptr elem, mType) - { // are any required elemnents missing - if ((elem->flags == SOE_REQUIRED) && (getPField(elem->e_field) == NULL)) - { - Log(lsWARNING) << getName() << " missing required element " << elem->e_field.fieldName; + { + if (it == mData.end()) return false; - } - } - - BOOST_FOREACH(const SerializedType& elem, mData) - { // are any non-permitted elements present - if (!isFieldAllowed(elem.getFName())) - { - Log(lsWARNING) << getName() << " has non-permitted element " << elem.getName(); + if (elem->e_field != it->getFName()) return false; - } + ++it; } return true; @@ -282,7 +290,8 @@ std::string STObject::getText() const bool STObject::isEquivalent(const SerializedType& t) const { const STObject* v = dynamic_cast(&t); - if (!v) return false; + if (!v) + return false; boost::ptr_vector::const_iterator it1 = mData.begin(), end1 = mData.end(); boost::ptr_vector::const_iterator it2 = v->mData.begin(), end2 = v->mData.end(); while ((it1 != end1) && (it2 != end2)) diff --git a/src/SerializedObject.h b/src/SerializedObject.h index ee66681ee4..98ffc8407e 100644 --- a/src/SerializedObject.h +++ b/src/SerializedObject.h @@ -28,7 +28,6 @@ protected: std::vector mType; STObject* duplicate() const { return new STObject(*this); } - bool compare(const SerializedType& f1, const SerializedType& f2); public: STObject() { ; } @@ -45,7 +44,7 @@ public: static std::auto_ptr deserialize(SerializerIterator& sit, SField::ref name); - void setType(SOElement::ptrList); + bool setType(SOElement::ptrList); bool isValidForType(); bool isFieldAllowed(SField::ref); diff --git a/src/SerializedTransaction.cpp b/src/SerializedTransaction.cpp index 5d1bdc6fe2..1fe5109ce6 100644 --- a/src/SerializedTransaction.cpp +++ b/src/SerializedTransaction.cpp @@ -30,11 +30,10 @@ SerializedTransaction::SerializedTransaction(SerializerIterator& sit) : STObject mFormat = getTxnFormat(mType); if (!mFormat) - throw std::runtime_error("invalid transction type"); - setType(mFormat->elements); - if (!isValidForType()) + throw std::runtime_error("invalid transaction type"); + if (!setType(mFormat->elements)) { - Log(lsDEBUG) << "Transaction not valid for type " << getJson(0); + assert(false); throw std::runtime_error("transaction not valid"); } } From 9496050bdf55d69369d3c8238f14e0a370f61ce5 Mon Sep 17 00:00:00 2001 From: MJK Date: Sat, 29 Sep 2012 18:29:02 -0700 Subject: [PATCH 45/53] Towards pathfinder() changes --- src/RPCServer.cpp | 18 +++++++++--------- 1 file changed, 9 insertions(+), 9 deletions(-) diff --git a/src/RPCServer.cpp b/src/RPCServer.cpp index ba6415daf3..17c2b4b6b1 100644 --- a/src/RPCServer.cpp +++ b/src/RPCServer.cpp @@ -1779,17 +1779,17 @@ Json::Value RPCServer::doSend(const Json::Value& params) // Destination exists, ordinary send. STPathSet spsPaths; - /* uint160 srcCurrencyID; - bool ret_b; - ret_b = false; - STAmount::currencyFromString(srcCurrencyID, sSrcCurrency); + bool ret_b; + ret_b = false; - Pathfinder pf(naSrcAccountID, naDstAccountID, srcCurrencyID, saDstAmount); - - ret_b = pf.findPaths(5, 1, spsPaths); - // TODO: Nope; the above can't be right - */ + if (!saSrcAmountMax.isNative() || !saDstAmount.isNative()) + { + STAmount::currencyFromString(srcCurrencyID, sSrcCurrency); + Pathfinder pf(naSrcAccountID, naDstAccountID, srcCurrencyID, saDstAmount); + ret_b = pf.findPaths(5, 1, spsPaths); + } + trans = Transaction::sharedPayment( naAccountPublic, naAccountPrivate, naSrcAccountID, From 11d092b98e11c4e197191c6338b0176fab5c9f25 Mon Sep 17 00:00:00 2001 From: JoelKatz Date: Sun, 30 Sep 2012 22:41:08 -0700 Subject: [PATCH 46/53] Oops, accidental reversion .# ntest --- src/LedgerFormats.cpp | 8 -------- 1 file changed, 8 deletions(-) diff --git a/src/LedgerFormats.cpp b/src/LedgerFormats.cpp index c3c9bc9bc9..f8fc80d4d2 100644 --- a/src/LedgerFormats.cpp +++ b/src/LedgerFormats.cpp @@ -50,21 +50,15 @@ LedgerEntryFormat LedgerFormats[]= { sfInvalid, SOE_END } } }, { "GeneratorMap", ltGENERATOR_MAP, { LEF_BASE - { sfLedgerEntryType,SOE_REQUIRED }, - { sfFlags, SOE_REQUIRED }, { sfGenerator, SOE_REQUIRED }, { sfInvalid, SOE_END } } }, { "Nickname", ltNICKNAME, { LEF_BASE - { sfLedgerEntryType,SOE_REQUIRED }, - { sfFlags, SOE_REQUIRED }, { sfAccount, SOE_REQUIRED }, { sfMinimumOffer, SOE_OPTIONAL }, { sfInvalid, SOE_END } } }, { "Offer", ltOFFER, { LEF_BASE - { sfLedgerEntryType,SOE_REQUIRED }, - { sfFlags, SOE_REQUIRED }, { sfAccount, SOE_REQUIRED }, { sfSequence, SOE_REQUIRED }, { sfTakerPays, SOE_REQUIRED }, @@ -78,8 +72,6 @@ LedgerEntryFormat LedgerFormats[]= { sfInvalid, SOE_END } } }, { "RippleState", ltRIPPLE_STATE, { LEF_BASE - { sfLedgerEntryType,SOE_REQUIRED }, - { sfFlags, SOE_REQUIRED }, { sfBalance, SOE_REQUIRED }, { sfLowLimit, SOE_REQUIRED }, { sfHighLimit, SOE_REQUIRED }, From 5cc421bc767f5d3b086e866e1cca896be7d5c16e Mon Sep 17 00:00:00 2001 From: JoelKatz Date: Sun, 30 Sep 2012 22:42:06 -0700 Subject: [PATCH 47/53] Temporary fix to some issues caused by transaction flattening. Will work out details with Arthur. --- src/SerializeProto.h | 16 +++++++++------- src/SerializedLedger.cpp | 4 ++++ src/SerializedObject.cpp | 2 +- src/SerializedTransaction.cpp | 6 +++--- src/SerializedTransaction.h | 2 +- 5 files changed, 18 insertions(+), 12 deletions(-) diff --git a/src/SerializeProto.h b/src/SerializeProto.h index 2b1050bb41..23a2260bb7 100644 --- a/src/SerializeProto.h +++ b/src/SerializeProto.h @@ -99,13 +99,14 @@ FIELD(PublicKey, VL, 1) FIELD(MessageKey, VL, 2) FIELD(SigningPubKey, VL, 3) - FIELD(Signature, VL, 4) + FIELD(TxnSignature, VL, 4) FIELD(Generator, VL, 5) - FIELD(Domain, VL, 6) - FIELD(FundCode, VL, 7) - FIELD(RemoveCode, VL, 8) - FIELD(ExpireCode, VL, 9) - FIELD(CreateCode, VL, 10) + FIELD(Signature, VL, 6) + FIELD(Domain, VL, 7) + FIELD(FundCode, VL, 8) + FIELD(RemoveCode, VL, 9) + FIELD(ExpireCode, VL, 10) + FIELD(CreateCode, VL, 11) // account FIELD(Account, ACCOUNT, 1) @@ -129,4 +130,5 @@ // array of objects // ARRAY/1 is reserved for end of array FIELD(SigningAccounts, ARRAY, 2) - FIELD(Signatures, ARRAY, 3) + FIELD(TxnSignatures, ARRAY, 3) + FIELD(Signatures, ARRAY, 4) diff --git a/src/SerializedLedger.cpp b/src/SerializedLedger.cpp index 5b153d11f3..4ba43bd1e3 100644 --- a/src/SerializedLedger.cpp +++ b/src/SerializedLedger.cpp @@ -30,7 +30,11 @@ SerializedLedgerEntry::SerializedLedgerEntry(const Serializer& s, const uint256& throw std::runtime_error("invalid ledger entry type"); mType = mFormat->t_type; if (!setType(mFormat->elements)) + { + Log(lsWARNING) << "Ledger entry not valid for type " << mFormat->t_name; + Log(lsWARNING) << getJson(0); throw std::runtime_error("ledger entry not valid for type"); + } } SerializedLedgerEntry::SerializedLedgerEntry(LedgerEntryType type) : STObject(sfLedgerEntry), mType(type) diff --git a/src/SerializedObject.cpp b/src/SerializedObject.cpp index c810c0de4d..a2980efa21 100644 --- a/src/SerializedObject.cpp +++ b/src/SerializedObject.cpp @@ -250,7 +250,7 @@ void STObject::add(Serializer& s, bool withSigningFields) const if (it.getSType() != STI_NOTPRESENT) { SField::ref fName = it.getFName(); - if (withSigningFields || ((fName != sfSignature) && (fName != sfSignatures))) + if (withSigningFields || ((fName != sfTxnSignature) && (fName != sfTxnSignatures))) fields.insert(std::make_pair(it.getFName().fieldCode, &it)); } } diff --git a/src/SerializedTransaction.cpp b/src/SerializedTransaction.cpp index 1fe5109ce6..aca26946ca 100644 --- a/src/SerializedTransaction.cpp +++ b/src/SerializedTransaction.cpp @@ -94,7 +94,7 @@ std::vector SerializedTransaction::getSignature() const { try { - return getValueFieldVL(sfSignature); + return getValueFieldVL(sfTxnSignature); } catch (...) { @@ -106,14 +106,14 @@ void SerializedTransaction::sign(const NewcoinAddress& naAccountPrivate) { std::vector signature; naAccountPrivate.accountPrivateSign(getSigningHash(), signature); - setValueFieldVL(sfSignature, signature); + setValueFieldVL(sfTxnSignature, signature); } bool SerializedTransaction::checkSign(const NewcoinAddress& naAccountPublic) const { try { - return naAccountPublic.accountPublicVerify(getSigningHash(), getValueFieldVL(sfSignature)); + return naAccountPublic.accountPublicVerify(getSigningHash(), getValueFieldVL(sfTxnSignature)); } catch (...) { diff --git a/src/SerializedTransaction.h b/src/SerializedTransaction.h index 8153a76487..295d0eb3cb 100644 --- a/src/SerializedTransaction.h +++ b/src/SerializedTransaction.h @@ -39,7 +39,7 @@ public: // outer transaction functions / signature functions std::vector getSignature() const; - void setSignature(const std::vector& s) { setValueFieldVL(sfSignature, s); } + void setSignature(const std::vector& s) { setValueFieldVL(sfTxnSignature, s); } uint256 getSigningHash() const; TransactionType getTxnType() const { return mType; } From de3b89d5c167a9563e63e6a5d9db7589697933f7 Mon Sep 17 00:00:00 2001 From: JoelKatz Date: Sun, 30 Sep 2012 23:38:29 -0700 Subject: [PATCH 48/53] Fix the bug Jed reported. Need isTeRetry. --- src/LedgerConsensus.cpp | 8 +++++--- src/TransactionErr.h | 2 ++ 2 files changed, 7 insertions(+), 3 deletions(-) diff --git a/src/LedgerConsensus.cpp b/src/LedgerConsensus.cpp index 2b2af08a78..f42acb9f0a 100644 --- a/src/LedgerConsensus.cpp +++ b/src/LedgerConsensus.cpp @@ -977,21 +977,23 @@ void LedgerConsensus::applyTransaction(TransactionEngine& engine, const Serializ { #endif TER result = engine.applyTransaction(*txn, parms); - if (result > 0) + if (isTerRetry(result { Log(lsINFO) << " retry"; assert(!ledger->hasTransaction(txn->getTransactionID())); failedTransactions.push_back(txn); } - else if (result == 0) + else if (isTepSuccess(result)) // FIXME: Need to do partial success { Log(lsTRACE) << " success"; assert(ledger->hasTransaction(txn->getTransactionID())); } - else + else if (isTemMalformed(result) || isTefFailure(result)) { Log(lsINFO) << " hard fail"; } + else + assert(false); #ifndef TRUST_NETWORK } catch (...) diff --git a/src/TransactionErr.h b/src/TransactionErr.h index 7ce5cd6109..59f42b46be 100644 --- a/src/TransactionErr.h +++ b/src/TransactionErr.h @@ -111,6 +111,8 @@ enum TER // aka TransactionEngineResult #define isTemMalformed(x) ((x) >= temMALFORMED && (x) < tefFAILURE) #define isTefFailure(x) ((x) >= tefFAILURE && (x) < terRETRY) #define isTepPartial(x) ((x) >= tepPATH_PARTIAL) +#define isTepSucess(x) ((x) >= tesSUCCESS) +#define isTerRetry(x) ((x) >= terRETRY && (x) < tesSUCCESS) bool transResultInfo(TER terCode, std::string& strToken, std::string& strHuman); std::string transToken(TER terCode); From b973f3509c03bc7332695e2a404f929beccb4a97 Mon Sep 17 00:00:00 2001 From: JoelKatz Date: Sun, 30 Sep 2012 23:40:21 -0700 Subject: [PATCH 49/53] Typo fixes. --- src/LedgerConsensus.cpp | 2 +- src/TransactionErr.h | 2 +- 2 files changed, 2 insertions(+), 2 deletions(-) diff --git a/src/LedgerConsensus.cpp b/src/LedgerConsensus.cpp index f42acb9f0a..2dc6672f6f 100644 --- a/src/LedgerConsensus.cpp +++ b/src/LedgerConsensus.cpp @@ -977,7 +977,7 @@ void LedgerConsensus::applyTransaction(TransactionEngine& engine, const Serializ { #endif TER result = engine.applyTransaction(*txn, parms); - if (isTerRetry(result + if (isTerRetry(result)) { Log(lsINFO) << " retry"; assert(!ledger->hasTransaction(txn->getTransactionID())); diff --git a/src/TransactionErr.h b/src/TransactionErr.h index 59f42b46be..576f3dbf80 100644 --- a/src/TransactionErr.h +++ b/src/TransactionErr.h @@ -111,7 +111,7 @@ enum TER // aka TransactionEngineResult #define isTemMalformed(x) ((x) >= temMALFORMED && (x) < tefFAILURE) #define isTefFailure(x) ((x) >= tefFAILURE && (x) < terRETRY) #define isTepPartial(x) ((x) >= tepPATH_PARTIAL) -#define isTepSucess(x) ((x) >= tesSUCCESS) +#define isTepSuccess(x) ((x) >= tesSUCCESS) #define isTerRetry(x) ((x) >= terRETRY && (x) < tesSUCCESS) bool transResultInfo(TER terCode, std::string& strToken, std::string& strHuman); From c6aa3b26788c3b13a138204fd87534d1cb68f56e Mon Sep 17 00:00:00 2001 From: JoelKatz Date: Mon, 1 Oct 2012 00:55:16 -0700 Subject: [PATCH 50/53] Type json improvements --- src/LedgerFormats.cpp | 9 +++++++-- src/LedgerFormats.h | 1 + src/SerializedTypes.cpp | 14 ++++++++++++++ src/TransactionFormats.cpp | 16 +++++++++++----- src/TransactionFormats.h | 1 + 5 files changed, 34 insertions(+), 7 deletions(-) diff --git a/src/LedgerFormats.cpp b/src/LedgerFormats.cpp index f8fc80d4d2..89cc24d078 100644 --- a/src/LedgerFormats.cpp +++ b/src/LedgerFormats.cpp @@ -86,13 +86,18 @@ LedgerEntryFormat LedgerFormats[]= { NULL, ltINVALID } }; - LedgerEntryFormat* getLgrFormat(LedgerEntryType t) +{ + return getLgrFormat(t); +} + +LedgerEntryFormat* getLgrFormat(int t) { LedgerEntryFormat* f = LedgerFormats; while (f->t_name != NULL) { - if (f->t_type == t) return f; + if (f->t_type == t) + return f; ++f; } return NULL; diff --git a/src/LedgerFormats.h b/src/LedgerFormats.h index 82221ca31d..7b4a95683e 100644 --- a/src/LedgerFormats.h +++ b/src/LedgerFormats.h @@ -48,5 +48,6 @@ struct LedgerEntryFormat extern LedgerEntryFormat LedgerFormats[]; extern LedgerEntryFormat* getLgrFormat(LedgerEntryType t); +extern LedgerEntryFormat* getLgrFormat(int t); #endif // vim:ts=4 diff --git a/src/SerializedTypes.cpp b/src/SerializedTypes.cpp index 6eeb0c9120..570a2e80ce 100644 --- a/src/SerializedTypes.cpp +++ b/src/SerializedTypes.cpp @@ -5,6 +5,8 @@ #include "SerializedTypes.h" #include "SerializedObject.h" #include "TransactionFormats.h" +#include "LedgerFormats.h" +#include "FieldNames.h" #include "Log.h" #include "NewcoinAddress.h" #include "utils.h" @@ -50,6 +52,18 @@ STUInt16* STUInt16::construct(SerializerIterator& u, SField::ref name) std::string STUInt16::getText() const { + if (getFName() == sfLedgerEntryType) + { + LedgerEntryFormat *f = getLgrFormat(value); + if (f != NULL) + return f->t_name; + } + if (getFName() == sfTransactionType) + { + TransactionFormat *f = getTxnFormat(value); + if (f != NULL) + return f->t_name; + } return boost::lexical_cast(value); } diff --git a/src/TransactionFormats.cpp b/src/TransactionFormats.cpp index eec5b363de..9e84d32004 100644 --- a/src/TransactionFormats.cpp +++ b/src/TransactionFormats.cpp @@ -100,14 +100,20 @@ TransactionFormat InnerTxnFormats[]= { NULL, ttINVALID } }; -TransactionFormat* getTxnFormat(TransactionType t) +TransactionFormat* getTxnFormat(TransactionType t) { - TransactionFormat* f = InnerTxnFormats; - while (f->t_name != NULL) + return getTxnFormat(t); +} + +TransactionFormat* getTxnFormat(int t) +{ + TransactionFormat* f = InnerTxnFormats; + while (f->t_name != NULL) { - if (f->t_type == t) return f; + if (f->t_type == t) + return f; ++f; } - return NULL; + return NULL; } // vim:ts=4 diff --git a/src/TransactionFormats.h b/src/TransactionFormats.h index edbccf3a69..57b155285f 100644 --- a/src/TransactionFormats.h +++ b/src/TransactionFormats.h @@ -46,5 +46,6 @@ const uint32 tfNoRippleDirect = 0x00080000; extern TransactionFormat InnerTxnFormats[]; extern TransactionFormat* getTxnFormat(TransactionType t); +extern TransactionFormat* getTxnFormat(int t); #endif // vim:ts=4 From d37db0219d82d62f897dfb628b53d61fdffd0dc7 Mon Sep 17 00:00:00 2001 From: JoelKatz Date: Mon, 1 Oct 2012 00:57:01 -0700 Subject: [PATCH 51/53] Fix endless recursion. --- src/LedgerFormats.cpp | 2 +- src/TransactionFormats.cpp | 2 +- 2 files changed, 2 insertions(+), 2 deletions(-) diff --git a/src/LedgerFormats.cpp b/src/LedgerFormats.cpp index 89cc24d078..84aaf73d14 100644 --- a/src/LedgerFormats.cpp +++ b/src/LedgerFormats.cpp @@ -88,7 +88,7 @@ LedgerEntryFormat LedgerFormats[]= LedgerEntryFormat* getLgrFormat(LedgerEntryType t) { - return getLgrFormat(t); + return getLgrFormat(static_cast(t)); } LedgerEntryFormat* getLgrFormat(int t) diff --git a/src/TransactionFormats.cpp b/src/TransactionFormats.cpp index 9e84d32004..cebc37a49c 100644 --- a/src/TransactionFormats.cpp +++ b/src/TransactionFormats.cpp @@ -102,7 +102,7 @@ TransactionFormat InnerTxnFormats[]= TransactionFormat* getTxnFormat(TransactionType t) { - return getTxnFormat(t); + return getTxnFormat(static_cast(t)); } TransactionFormat* getTxnFormat(int t) From 98d8823be0ab59a68659b4ffcb294b262608480f Mon Sep 17 00:00:00 2001 From: JoelKatz Date: Mon, 1 Oct 2012 02:19:17 -0700 Subject: [PATCH 52/53] Get ready for Json decode. --- src/FieldNames.cpp | 2 +- src/FieldNames.h | 6 +++--- src/SerializedObject.cpp | 15 ++++++++++++++- src/SerializedObject.h | 2 ++ src/SerializedTypes.cpp | 2 +- src/SerializedTypes.h | 2 +- 6 files changed, 22 insertions(+), 7 deletions(-) diff --git a/src/FieldNames.cpp b/src/FieldNames.cpp index d631fb7f01..e6af94ad26 100644 --- a/src/FieldNames.cpp +++ b/src/FieldNames.cpp @@ -75,7 +75,7 @@ SField::ref SField::getField(int type, int value) std::string SField::getName() const { - if (fieldName != NULL) + if (!fieldName.empty()) return fieldName; if (fieldValue == 0) return ""; diff --git a/src/FieldNames.h b/src/FieldNames.h index c738e6cefa..4d966c547c 100644 --- a/src/FieldNames.h +++ b/src/FieldNames.h @@ -48,20 +48,20 @@ public: const int fieldCode; // (type<<16)|index const SerializedTypeID fieldType; // STI_* const int fieldValue; // Code number for protocol - const char* fieldName; + std::string fieldName; SField(int fc, SerializedTypeID tid, int fv, const char* fn) : fieldCode(fc), fieldType(tid), fieldValue(fv), fieldName(fn) { codeToField[fc] = this; } - SField(int fc) : fieldCode(fc), fieldType(STI_UNKNOWN), fieldValue(0), fieldName(NULL) { ; } + SField(int fc) : fieldCode(fc), fieldType(STI_UNKNOWN), fieldValue(0) { ; } static SField::ref getField(int fieldCode); static SField::ref getField(int fieldType, int fieldValue); static SField::ref getField(SerializedTypeID type, int value) { return getField(FIELD_CODE(type, value)); } std::string getName() const; - bool hasName() const { return (fieldName != NULL) || (fieldValue != 0); } + bool hasName() const { return !fieldName.empty(); } bool isGeneric() const { return fieldCode == 0; } bool isInvalid() const { return fieldCode == -1; } diff --git a/src/SerializedObject.cpp b/src/SerializedObject.cpp index a2980efa21..af7ac0c47b 100644 --- a/src/SerializedObject.cpp +++ b/src/SerializedObject.cpp @@ -703,7 +703,7 @@ Json::Value STObject::getJson(int options) const { if (it.getSType() != STI_NOTPRESENT) { - if (it.getName() == NULL) + if (!it.getFName().hasName()) ret[boost::lexical_cast(index)] = it.getJson(options); else ret[it.getName()] = it.getJson(options); @@ -777,6 +777,19 @@ STArray* STArray::construct(SerializerIterator& sit, SField::ref field) return new STArray(field, value); } +STObject::STObject(const Json::Value& object, SField::ref name) : SerializedType(name) +{ + if (!object.isObject()) + throw std::runtime_error("Value is not an object"); + + Json::Value::Members members(object.getMemberNames()); + for (Json::Value::Members::iterator it = members.begin(), end = members.end(); it != end; ++it) + { + const std::string& name = *it; + const Json::Value& value = object[name]; + // WRITEME + } +} #if 0 diff --git a/src/SerializedObject.h b/src/SerializedObject.h index 98ffc8407e..bfcc7c090c 100644 --- a/src/SerializedObject.h +++ b/src/SerializedObject.h @@ -40,6 +40,8 @@ public: STObject(SOElement::ptrList type, SerializerIterator& sit, SField::ref name) : SerializedType(name) { set(sit); setType(type); } + STObject(const Json::Value& value, SField::ref name); + virtual ~STObject() { ; } static std::auto_ptr deserialize(SerializerIterator& sit, SField::ref name); diff --git a/src/SerializedTypes.cpp b/src/SerializedTypes.cpp index 570a2e80ce..4cee5f5c9b 100644 --- a/src/SerializedTypes.cpp +++ b/src/SerializedTypes.cpp @@ -19,7 +19,7 @@ std::string SerializedType::getFullText() const std::string ret; if (getSType() != STI_NOTPRESENT) { - if(fName != NULL) + if(fName->hasName()) { ret = fName->fieldName; ret += " = "; diff --git a/src/SerializedTypes.h b/src/SerializedTypes.h index 9852735e35..33706ae456 100644 --- a/src/SerializedTypes.h +++ b/src/SerializedTypes.h @@ -50,7 +50,7 @@ public: void setFName(SField::ref n) { fName = &n; assert(fName); } SField::ref getFName() const { return *fName; } - const char *getName() const { return fName->fieldName; } + std::string getName() const { return fName->fieldName; } virtual SerializedTypeID getSType() const { return STI_NOTPRESENT; } std::auto_ptr clone() const { return std::auto_ptr(duplicate()); } From c4275c6d806e4e3e5148c247e3ffe4215908e8ff Mon Sep 17 00:00:00 2001 From: JoelKatz Date: Mon, 1 Oct 2012 08:32:23 -0700 Subject: [PATCH 53/53] More work on the JSON conversion code. --- src/FieldNames.cpp | 13 ++++ src/FieldNames.h | 1 + src/LedgerFormats.cpp | 4 +- src/SerializedObject.cpp | 126 ++++++++++++++++++++++++++++++++++++++- src/SerializedObject.h | 5 +- src/SerializedTypes.h | 28 ++++----- 6 files changed, 157 insertions(+), 20 deletions(-) diff --git a/src/FieldNames.cpp b/src/FieldNames.cpp index e6af94ad26..612d250c97 100644 --- a/src/FieldNames.cpp +++ b/src/FieldNames.cpp @@ -5,6 +5,7 @@ #include #include +#include // These must stay at the top of this file @@ -82,3 +83,15 @@ std::string SField::getName() const return boost::lexical_cast(static_cast(fieldType)) + "/" + boost::lexical_cast(fieldValue); } + +SField::ref SField::getField(const std::string& fieldName) +{ // OPTIMIZEME me with a map. CHECKME this is case sensitive + boost::mutex::scoped_lock sl(mapMutex); + typedef std::pair int_sfref_pair; + BOOST_FOREACH(const int_sfref_pair& fieldPair, codeToField) + { + if (fieldPair.second->fieldName == fieldName) + return *(fieldPair.second); + } + return sfInvalid; +} diff --git a/src/FieldNames.h b/src/FieldNames.h index 4d966c547c..ed51006499 100644 --- a/src/FieldNames.h +++ b/src/FieldNames.h @@ -58,6 +58,7 @@ public: static SField::ref getField(int fieldCode); static SField::ref getField(int fieldType, int fieldValue); + static SField::ref getField(const std::string& fieldName); static SField::ref getField(SerializedTypeID type, int value) { return getField(FIELD_CODE(type, value)); } std::string getName() const; diff --git a/src/LedgerFormats.cpp b/src/LedgerFormats.cpp index 84aaf73d14..bc4ab86ed1 100644 --- a/src/LedgerFormats.cpp +++ b/src/LedgerFormats.cpp @@ -2,9 +2,9 @@ #include "LedgerFormats.h" #define LEF_BASE \ + { sfLedgerIndex, SOE_OPTIONAL }, \ { sfLedgerEntryType, SOE_REQUIRED }, \ - { sfFlags, SOE_REQUIRED }, \ - { sfLedgerIndex, SOE_OPTIONAL }, + { sfFlags, SOE_REQUIRED }, LedgerEntryFormat LedgerFormats[]= { diff --git a/src/SerializedObject.cpp b/src/SerializedObject.cpp index af7ac0c47b..0bfab6c928 100644 --- a/src/SerializedObject.cpp +++ b/src/SerializedObject.cpp @@ -429,6 +429,20 @@ void STObject::makeFieldAbsent(SField::ref field) mData.replace(index, makeDefaultObject(f.getFName())); } +bool STObject::delField(SField::ref field) +{ + int index = getFieldIndex(field); + if (index == -1) + return false; + delField(index); + return true; +} + +void STObject::delField(int index) +{ + mData.erase(mData.begin() + index); +} + std::string STObject::getFieldString(SField::ref field) const { const SerializedType* rf = peekAtPField(field); @@ -777,18 +791,126 @@ STArray* STArray::construct(SerializerIterator& sit, SField::ref field) return new STArray(field, value); } -STObject::STObject(const Json::Value& object, SField::ref name) : SerializedType(name) +std::auto_ptr STObject::parseJson(const Json::Value& object, SField::ref name, int depth) { if (!object.isObject()) throw std::runtime_error("Value is not an object"); + boost::ptr_vector data; Json::Value::Members members(object.getMemberNames()); for (Json::Value::Members::iterator it = members.begin(), end = members.end(); it != end; ++it) { const std::string& name = *it; const Json::Value& value = object[name]; - // WRITEME + + SField::ref field = SField::getField(name); + if (field == sfInvalid) + throw std::runtime_error("Unknown field: " + name); + + switch (field.fieldType) + { + case STI_UINT8: + if (value.isString()) + data.push_back(new STUInt8(field, boost::lexical_cast(value.asString()))); + else if (value.isInt()) + data.push_back(new STUInt8(field, boost::lexical_cast(value.asInt()))); + else if (value.isUInt()) + data.push_back(new STUInt8(field, boost::lexical_cast(value.asUInt()))); + else + throw std::runtime_error("Incorrect type"); + break; + + case STI_UINT16: + if (value.isString()) + { + std::string strValue = value.asString(); + if (!strValue.empty() && (strValue[0]<'0' || strValue[0]>'9')) + { + if (field == sfTransactionType) + { + // WRITEME + } + else if (field == sfLedgerEntryType) + { + // WRITEME + } + else + throw std::runtime_error("Invalid field data"); + } + data.push_back(new STUInt16(field, boost::lexical_cast(strValue))); + } + else if (value.isInt()) + data.push_back(new STUInt16(field, boost::lexical_cast(value.asInt()))); + else if (value.isUInt()) + data.push_back(new STUInt16(field, boost::lexical_cast(value.asUInt()))); + else + throw std::runtime_error("Incorrect type"); + break; + + case STI_UINT32: + if (value.isString()) + data.push_back(new STUInt32(field, boost::lexical_cast(value.asString()))); + else if (value.isInt()) + data.push_back(new STUInt32(field, boost::lexical_cast(value.asInt()))); + else if (value.isUInt()) + data.push_back(new STUInt32(field, boost::lexical_cast(value.asUInt()))); + else + throw std::runtime_error("Incorrect type"); + break; + + case STI_UINT64: + if (value.isString()) + data.push_back(new STUInt64(field, boost::lexical_cast(value.asString()))); + else if (value.isInt()) + data.push_back(new STUInt64(field, boost::lexical_cast(value.asInt()))); + else if (value.isUInt()) + data.push_back(new STUInt64(field, boost::lexical_cast(value.asUInt()))); + else + throw std::runtime_error("Incorrect type"); + break; + + + case STI_HASH128: + // WRITEME + + case STI_HASH160: + // WRITEME + + case STI_HASH256: + // WRITEME + + case STI_VL: + // WRITEME + + case STI_AMOUNT: + // WRITEME + + case STI_VECTOR256: + // WRITEME + + case STI_PATHSET: + // WRITEME + + case STI_OBJECT: + case STI_ACCOUNT: + case STI_TRANSACTION: + case STI_LEDGERENTRY: + case STI_VALIDATION: + if (!value.isObject()) + throw std::runtime_error("Inner value is not an object"); + if (depth > 64) + throw std::runtime_error("Json nest depth exceeded"); + data.push_back(parseJson(value, field, depth + 1)); + break; + + case STI_ARRAY: + // WRITEME + + default: + throw std::runtime_error("Invalid field type"); + } } + return std::auto_ptr(new STObject(name, data)); } #if 0 diff --git a/src/SerializedObject.h b/src/SerializedObject.h index bfcc7c090c..58a926d983 100644 --- a/src/SerializedObject.h +++ b/src/SerializedObject.h @@ -28,6 +28,7 @@ protected: std::vector mType; STObject* duplicate() const { return new STObject(*this); } + STObject(SField::ref name, boost::ptr_vector& data) : SerializedType(name) { mData.swap(data); } public: STObject() { ; } @@ -40,7 +41,7 @@ public: STObject(SOElement::ptrList type, SerializerIterator& sit, SField::ref name) : SerializedType(name) { set(sit); setType(type); } - STObject(const Json::Value& value, SField::ref name); + static std::auto_ptr parseJson(const Json::Value& value, SField::ref name, int depth = 0); virtual ~STObject() { ; } @@ -127,6 +128,8 @@ public: bool isFieldPresent(SField::ref field) const; SerializedType* makeFieldPresent(SField::ref field); void makeFieldAbsent(SField::ref field); + bool delField(SField::ref field); + void delField(int index); static std::auto_ptr makeDefaultObject(SerializedTypeID id, SField::ref name); static std::auto_ptr makeDeserializedObject(SerializedTypeID id, SField::ref name, diff --git a/src/SerializedTypes.h b/src/SerializedTypes.h index 33706ae456..de1fb75eb6 100644 --- a/src/SerializedTypes.h +++ b/src/SerializedTypes.h @@ -91,7 +91,7 @@ protected: public: STUInt8(unsigned char v = 0) : value(v) { ; } - STUInt8(SField::ref n, unsigned char v=0) : SerializedType(n), value(v) { ; } + STUInt8(SField::ref n, unsigned char v = 0) : SerializedType(n), value(v) { ; } static std::auto_ptr deserialize(SerializerIterator& sit, SField::ref name) { return std::auto_ptr(construct(sit, name)); } @@ -116,8 +116,8 @@ protected: public: - STUInt16(uint16 v=0) : value(v) { ; } - STUInt16(SField::ref n, uint16 v=0) : SerializedType(n), value(v) { ; } + STUInt16(uint16 v = 0) : value(v) { ; } + STUInt16(SField::ref n, uint16 v = 0) : SerializedType(n), value(v) { ; } static std::auto_ptr deserialize(SerializerIterator& sit, SField::ref name) { return std::auto_ptr(construct(sit, name)); } @@ -143,7 +143,7 @@ protected: public: STUInt32(uint32 v = 0) : value(v) { ; } - STUInt32(SField::ref n, uint32 v=0) : SerializedType(n), value(v) { ; } + STUInt32(SField::ref n, uint32 v = 0) : SerializedType(n), value(v) { ; } static std::auto_ptr deserialize(SerializerIterator& sit, SField::ref name) { return std::auto_ptr(construct(sit, name)); } @@ -168,8 +168,8 @@ protected: public: - STUInt64(uint64 v=0) : value(v) { ; } - STUInt64(SField::ref n, uint64 v=0) : SerializedType(n), value(v) { ; } + STUInt64(uint64 v = 0) : value(v) { ; } + STUInt64(SField::ref n, uint64 v = 0) : SerializedType(n), value(v) { ; } static std::auto_ptr deserialize(SerializerIterator& sit, SField::ref name) { return std::auto_ptr(construct(sit, name)); } @@ -225,6 +225,8 @@ protected: : SerializedType(name), mCurrency(cur), mIssuer(iss), mValue(val), mOffset(off), mIsNative(isNat), mIsNegative(isNeg) { ; } + STAmount(SField::ref name, const Json::Value& value); + uint64 toUInt64() const; static uint64 muldiv(uint64, uint64, uint64); @@ -232,13 +234,13 @@ public: static uint64 uRateOne; STAmount(uint64 v = 0, bool isNeg = false) : mValue(v), mOffset(0), mIsNative(true), mIsNegative(isNeg) - { if (v==0) mIsNegative = false; } + { if (v == 0) mIsNegative = false; } STAmount(SField::ref n, uint64 v = 0) : SerializedType(n), mValue(v), mOffset(0), mIsNative(true), mIsNegative(false) { ; } - STAmount(const uint160& uCurrencyID, const uint160& uIssuerID, uint64 uV=0, int iOff=0, bool bNegative=false) + STAmount(const uint160& uCurrencyID, const uint160& uIssuerID, uint64 uV = 0, int iOff = 0, bool bNegative = false) : mCurrency(uCurrencyID), mIssuer(uIssuerID), mValue(uV), mOffset(iOff), mIsNegative(bNegative) { canonicalize(); } @@ -254,14 +256,10 @@ public: { return std::auto_ptr(construct(sit, name)); } static STAmount saFromRate(uint64 uRate = 0) - { - return STAmount(CURRENCY_ONE, ACCOUNT_ONE, uRate, -9, false); - } + { return STAmount(CURRENCY_ONE, ACCOUNT_ONE, uRate, -9, false); } - static STAmount saFromSigned(const uint160& uCurrencyID, const uint160& uIssuerID, int64 iV=0, int iOff=0) - { - return STAmount(uCurrencyID, uIssuerID, iV < 0 ? -iV : iV, iOff, iV < 0); - } + static STAmount saFromSigned(const uint160& uCurrencyID, const uint160& uIssuerID, int64 iV = 0, int iOff = 0) + { return STAmount(uCurrencyID, uIssuerID, iV < 0 ? -iV : iV, iOff, iV < 0); } SerializedTypeID getSType() const { return STI_AMOUNT; } std::string getText() const;