zorba-coders team mailing list archive
-
zorba-coders team
-
Mailing list archive
-
Message #08054
[Merge] lp:~zorba-coders/zorba/serializer into lp:zorba
Markos Zaharioudakis has proposed merging lp:~zorba-coders/zorba/serializer into lp:zorba.
Requested reviews:
Markos Zaharioudakis (markos-za)
For more details, see:
https://code.launchpad.net/~zorba-coders/zorba/serializer/+merge/102459
removed forward-referencing stuff
--
https://code.launchpad.net/~zorba-coders/zorba/serializer/+merge/102459
Your team Zorba Coders is subscribed to branch lp:zorba.
=== modified file 'src/zorbaserialization/archiver.cpp'
--- src/zorbaserialization/archiver.cpp 2012-04-16 20:56:43 +0000
+++ src/zorbaserialization/archiver.cpp 2012-04-18 08:33:27 +0000
@@ -21,6 +21,7 @@
#include "functions/function.h"
#include "store/api/item.h"
#include "diagnostics/xquery_diagnostics.h"
+#include "diagnostics/assert.h"
#include "zorbautils/hashmap.h"
#include "archiver.h"
@@ -114,19 +115,18 @@
********************************************************************************/
Archiver::Archiver(bool is_serializing_out, bool internal_archive)
:
+ theArchiveVersion(ClassSerializer::g_zorba_classes_version),
theSerializingOut(is_serializing_out),
- serialize_base_class(false),
- all_reference_list(0),
- theArchiveVersion(ClassSerializer::g_zorba_classes_version),
+ theSerializeBaseClass(false),
+ theIsTempField(0),
+ theFieldCounter(0),
theRootField(0),
theCurrentCompoundField(0),
- theSimpleFieldsMap(0),
- hash_out_fields(0),
- nr_ids(0),
- current_class_version(0),
+ theCurrentLevel(0),
+ theNonClassFieldsMap(0),
+ theClassFieldsMap(0),
+ all_reference_list(0),
read_optional(false),
- theIsTempField(0),
- theCurrentLevel(0),
internal_archive(internal_archive),
theOnlyForEval(0),
theSerializeEverything(false),
@@ -151,15 +151,15 @@
theCurrentCompoundField = theRootField;
- theSimpleFieldsMap = new HashMap<SIMPLE_HASHOUT_FIELD, archive_field*,
+ theNonClassFieldsMap = new HashMap<SIMPLE_HASHOUT_FIELD, archive_field*,
SimpleHashoutFieldCompare>(1000, false);
- hash_out_fields = new hash64map<archive_field*>(10000, 0.6f);
+ theClassFieldsMap = new hash64map<archive_field*>(10000, 0.6f);
}
if (!internal_archive)
{
Archiver* har = ClassSerializer::getInstance()->harcoded_objects_archive;
- nr_ids = har->get_nr_ids();
+ theFieldCounter = har->get_num_fields();
}
}
@@ -171,15 +171,8 @@
{
delete theRootField;
delete [] all_reference_list;
- delete theSimpleFieldsMap;
- delete hash_out_fields;
-
- std::list<fwd_ref>::iterator it;
- for (it = fwd_reference_list.begin(); it != fwd_reference_list.end(); ++it)
- {
- if ((*it).class_name)
- free((*it).class_name);
- }
+ delete theNonClassFieldsMap;
+ delete theClassFieldsMap;
std::vector<archive_field*>::const_iterator orphan_it;
for (orphan_it = orphan_fields.begin(); orphan_it != orphan_fields.end(); ++orphan_it)
@@ -226,7 +219,7 @@
SIMPLE_HASHOUT_FIELD f(type, ptr);
- theSimpleFieldsMap->get(f, duplicate_field);
+ theNonClassFieldsMap->get(f, duplicate_field);
if (!duplicate_field)
{
@@ -252,7 +245,7 @@
archive_field* duplicate_field = NULL;
- hash_out_fields->get((uint64_t)ptr, duplicate_field);
+ theClassFieldsMap->get((uint64_t)ptr, duplicate_field);
if (!duplicate_field)
{
@@ -287,7 +280,6 @@
{
archive_field* new_field;
archive_field* ref_field = NULL;
- bool exch_fields = false;
assert(fieldKind != ARCHIVE_FIELD_BASECLASS);
assert(fieldKind != ARCHIVE_FIELD_REFERENCING);
@@ -312,14 +304,13 @@
if (ref_field)
{
- assert(ref_field->theKind == ARCHIVE_FIELD_PTR ||
- ref_field->theKind == ARCHIVE_FIELD_NORMAL);
+ // special case: we have registered already a pointer to the obj (before
+ // the obj itself) and now we try to register the obj itself. In theory,
+ // this scenario is possible, but in practice it never happens.
+ ZORBA_ASSERT(fieldKind != ARCHIVE_FIELD_NORMAL);
- // If we are trying to register the actual obj (i.e. fieldKind == FIELD_NORMAL)
- // and there is already a field for the same obj, then the pre-existing field
- // must be a PTR or REFERENCING field.
- assert(fieldKind != ARCHIVE_FIELD_NORMAL ||
- ref_field->theKind == ARCHIVE_FIELD_PTR);
+ ZORBA_ASSERT(ref_field->theKind == ARCHIVE_FIELD_PTR ||
+ ref_field->theKind == ARCHIVE_FIELD_NORMAL);
if (get_is_temp_field_one_level() &&
fieldKind == ARCHIVE_FIELD_PTR &&
@@ -328,13 +319,6 @@
theAllowDelay2 = DONT_ALLOW_DELAY;
}
- if (fieldKind == ARCHIVE_FIELD_NORMAL)
- {
- // special case: we have registered already a pointer to the obj (before
- // the obj itself) and now we try to register the obj itself.
- exch_fields = true;
- }
-
fieldKind = ARCHIVE_FIELD_REFERENCING;
value = NULL;
ptr = NULL;
@@ -362,27 +346,20 @@
assert(fieldKind == ARCHIVE_FIELD_NORMAL || fieldKind == ARCHIVE_FIELD_PTR);
SIMPLE_HASHOUT_FIELD f(type, ptr);
- theSimpleFieldsMap->insert(f, new_field);
- }
-
- if (!exch_fields)
- {
- new_field->theId = ++nr_ids;
- new_field->theOrder = new_field->theId;
-
- new_field->theParent = theCurrentCompoundField;
-
- if (theCurrentCompoundField->theLastChild)
- theCurrentCompoundField->theLastChild->theNextSibling = new_field;
- else
- theCurrentCompoundField->theFirstChild = new_field;
-
- theCurrentCompoundField->theLastChild = new_field;
- }
+ theNonClassFieldsMap->insert(f, new_field);
+ }
+
+ new_field->theId = ++theFieldCounter;
+ new_field->theOrder = new_field->theId;
+
+ new_field->theParent = theCurrentCompoundField;
+
+ if (theCurrentCompoundField->theLastChild)
+ theCurrentCompoundField->theLastChild->theNextSibling = new_field;
else
- {
- exchange_fields(new_field, ref_field);
- }
+ theCurrentCompoundField->theFirstChild = new_field;
+
+ theCurrentCompoundField->theLastChild = new_field;
theCurrentLevel--;
@@ -391,65 +368,6 @@
/*******************************************************************************
- Place new_field in the position occupied by ref_field, and disconnect
- ref_field from the tree.
-********************************************************************************/
-void Archiver::replace_field(archive_field* new_field, archive_field* ref_field)
-{
- archive_field* ref_field_parent = ref_field->theParent;
- archive_field* ref_field_prev = ref_field_parent->theFirstChild;
-
- if (ref_field_prev == ref_field)//is first child
- {
- ref_field_parent->theFirstChild = new_field;
- new_field->theNextSibling = ref_field->theNextSibling;
- }
- else
- {
- while (ref_field_prev->theNextSibling != ref_field)
- ref_field_prev = ref_field_prev->theNextSibling;
-
- ref_field_prev->theNextSibling = new_field;
- new_field->theNextSibling = ref_field->theNextSibling;
- }
-
- new_field->theParent = ref_field_parent;
-
- if (ref_field_parent->theLastChild == ref_field)
- ref_field_parent->theLastChild = new_field;
-
- new_field->theOrder = ref_field->theOrder;
-}
-
-
-/*******************************************************************************
-
-********************************************************************************/
-void Archiver::exchange_fields(archive_field* new_field, archive_field* ref_field)
-{
- ref_field->theKind = ARCHIVE_FIELD_NORMAL;
-
- assert(new_field->theKind == ARCHIVE_FIELD_REFERENCING);
- new_field->theId = ++nr_ids;
- new_field->theAllowDelay2 = ref_field->theAllowDelay2;
-
- replace_field(new_field, ref_field);
-
- ref_field->theParent = theCurrentCompoundField;
-
- if(theCurrentCompoundField->theLastChild)
- theCurrentCompoundField->theLastChild->theNextSibling = ref_field;
- else
- theCurrentCompoundField->theFirstChild = ref_field;
-
- ref_field->theNextSibling = NULL;
- theCurrentCompoundField->theLastChild = ref_field;
-
- ref_field->theOrder = nr_ids;
-}
-
-
-/*******************************************************************************
********************************************************************************/
bool Archiver::add_compound_field(
@@ -461,7 +379,6 @@
{
archive_field* new_field;
archive_field* ref_field = NULL;
- bool exch_fields = false;
theCurrentLevel++;
@@ -471,7 +388,6 @@
theCurrentLevel--;
}
else if (fieldKind != ARCHIVE_FIELD_BASECLASS &&
- ptr &&
!get_is_temp_field() &&
(!get_is_temp_field_one_level() ||
(fieldKind == ARCHIVE_FIELD_PTR && !get_is_temp_field_also_for_ptr())))
@@ -484,11 +400,9 @@
if (ref_field)
{
- assert(ref_field->theKind == ARCHIVE_FIELD_PTR ||
- ref_field->theKind == ARCHIVE_FIELD_NORMAL);
-
- assert(fieldKind != ARCHIVE_FIELD_NORMAL ||
- ref_field->theKind != ARCHIVE_FIELD_NORMAL);
+ ZORBA_ASSERT(fieldKind != ARCHIVE_FIELD_NORMAL);
+ ZORBA_ASSERT(ref_field->theKind == ARCHIVE_FIELD_PTR ||
+ ref_field->theKind == ARCHIVE_FIELD_NORMAL);
if (get_is_temp_field_one_level() &&
fieldKind == ARCHIVE_FIELD_PTR &&
@@ -497,18 +411,12 @@
theAllowDelay2 = DONT_ALLOW_DELAY;
}
- if (fieldKind == ARCHIVE_FIELD_NORMAL)
- {
- exch_fields = true;
- }
-
fieldKind = ARCHIVE_FIELD_REFERENCING;
-
ptr = NULL;
}
new_field = new archive_field(type,
- false,
+ false, // is_simple
is_class,
info,
ptr,
@@ -517,6 +425,7 @@
get_serialize_only_for_eval(),
theAllowDelay2,
theCurrentLevel);
+
theAllowDelay2 = ALLOW_DELAY;
if (!ref_field &&
@@ -529,34 +438,27 @@
if (!is_class)
{
SIMPLE_HASHOUT_FIELD f(type, ptr);
- theSimpleFieldsMap->insert(f, new_field);
+ theNonClassFieldsMap->insert(f, new_field);
}
else
{
- hash_out_fields->put((uint64_t)ptr, new_field);
+ theClassFieldsMap->put((uint64_t)ptr, new_field);
}
}
- if (!exch_fields)
- {
- new_field->theParent = theCurrentCompoundField;
- new_field->theId = ++nr_ids;
- new_field->theOrder = new_field->theId;
-
- if (theCurrentCompoundField->theLastChild)
- theCurrentCompoundField->theLastChild->theNextSibling = new_field;
- else
- theCurrentCompoundField->theFirstChild = new_field;
-
- theCurrentCompoundField->theLastChild = new_field;
-
- if (!ref_field && ptr)
- theCurrentCompoundField = new_field;
- }
+ new_field->theParent = theCurrentCompoundField;
+ new_field->theId = ++theFieldCounter;
+ new_field->theOrder = new_field->theId;
+
+ if (theCurrentCompoundField->theLastChild)
+ theCurrentCompoundField->theLastChild->theNextSibling = new_field;
else
- {
- exchange_fields(new_field, ref_field);
- }
+ theCurrentCompoundField->theFirstChild = new_field;
+
+ theCurrentCompoundField->theLastChild = new_field;
+
+ if (!ref_field && ptr)
+ theCurrentCompoundField = new_field;
if (ref_field)
theCurrentLevel--;
@@ -576,6 +478,38 @@
/*******************************************************************************
+ Place new_field in the position occupied by ref_field, and disconnect
+ ref_field from the tree.
+********************************************************************************/
+void Archiver::replace_field(archive_field* new_field, archive_field* ref_field)
+{
+ archive_field* ref_field_parent = ref_field->theParent;
+ archive_field* ref_field_prev = ref_field_parent->theFirstChild;
+
+ if (ref_field_prev == ref_field)//is first child
+ {
+ ref_field_parent->theFirstChild = new_field;
+ new_field->theNextSibling = ref_field->theNextSibling;
+ }
+ else
+ {
+ while (ref_field_prev->theNextSibling != ref_field)
+ ref_field_prev = ref_field_prev->theNextSibling;
+
+ ref_field_prev->theNextSibling = new_field;
+ new_field->theNextSibling = ref_field->theNextSibling;
+ }
+
+ new_field->theParent = ref_field_parent;
+
+ if (ref_field_parent->theLastChild == ref_field)
+ ref_field_parent->theLastChild = new_field;
+
+ new_field->theOrder = ref_field->theOrder;
+}
+
+
+/*******************************************************************************
********************************************************************************/
bool Archiver::read_next_field(
@@ -767,51 +701,6 @@
/*******************************************************************************
********************************************************************************/
-void Archiver::register_delay_reference(
- void** ptr,
- bool is_class,
- const char* class_name,
- int referencing)
-{
- struct fwd_ref fid;
- fid.referencing = referencing;
- fid.is_class = is_class;
- fid.ptr = ptr;
- *ptr = NULL;
-
- if(class_name)
- fid.class_name = strdup(class_name);
- else
- fid.class_name = NULL;
-
- fid.to_add_ref = false;
- fwd_reference_list.push_back(fid);
-}
-
-
-/*******************************************************************************
-
-********************************************************************************/
-void Archiver::reconf_last_delayed_rcobject(
- void** last_obj,
- void** new_last_obj,
- bool to_add_ref)
-{
- if (fwd_reference_list.size() > 0)
- {
- struct fwd_ref& fid = fwd_reference_list.back();
- if (fid.ptr == last_obj)
- {
- fid.ptr = new_last_obj;
- fid.to_add_ref = to_add_ref;
- }
- }
-}
-
-
-/*******************************************************************************
-
-********************************************************************************/
void Archiver::register_pointers_internal(archive_field* fields)
{
archive_field* child;
@@ -833,7 +722,7 @@
********************************************************************************/
void* Archiver::get_reference_value(int refid)
{
- if(internal_archive && !all_reference_list)
+ if (internal_archive && !all_reference_list)
{
//construct all_reference_list
root_tag_is_read();
@@ -857,59 +746,6 @@
********************************************************************************/
void Archiver::finalize_input_serialization()
{
- std::list<fwd_ref>::iterator it;
- void* ptr;
-
- for (it = fwd_reference_list.begin(); it != fwd_reference_list.end(); it++)
- {
- ptr = get_reference_value((*it).referencing);
-
- if (!ptr)
- {
- throw ZORBA_EXCEPTION(zerr::ZCSE0004_UNRESOLVED_FIELD_REFERENCE,
- ERROR_PARAMS(it->referencing));
- }
-
- //search the list for the pointer
- if (!(*it).is_class)
- {
- *((*it).ptr) = ptr;
- }
- else
- {
- ClassDeserializer* cls_factory;
-
- cls_factory = ClassSerializer::getInstance()->get_class_factory((*it).class_name);
-
- if (cls_factory == NULL)
- {
- throw ZORBA_EXCEPTION(zerr::ZCSE0003_UNRECOGNIZED_CLASS_FIELD,
- ERROR_PARAMS(it->class_name));
- }
-
- cls_factory->cast_ptr((SerializeBaseClass*)ptr, (*it).ptr);
-
- SimpleRCObject* rcobj1;
- store::Item* rcobj2;
-
- if (!(*it).to_add_ref)
- {
- }
- else if ((rcobj1 = dynamic_cast<SimpleRCObject*>((SerializeBaseClass*)ptr)) != NULL)
- {
- RCHelper::addReference(rcobj1); //this can lead to memory leaks
- }
- else if ((rcobj2 = dynamic_cast<store::Item*>((SerializeBaseClass*)ptr)) != NULL)
- {
- rcobj2->addReference(); //this can lead to memory leaks
- }
- else
- {
- ZORBA_FATAL(0, (*it).class_name);
- }
- }
- }
-
//decrement RC on Items
std::vector<store::Item*>::iterator item_it;
int j = 0;
@@ -941,17 +777,8 @@
ERROR_PARAMS(theArchiveVersion, ClassSerializer::g_zorba_classes_version));
}
- all_reference_list = new void*[nr_ids+1];
- memset(all_reference_list, 0, sizeof(void*)*(nr_ids+1));
-}
-
-
-/*******************************************************************************
-
-********************************************************************************/
-int Archiver::get_nr_ids()
-{
- return nr_ids;
+ all_reference_list = new void*[theFieldCounter+1];
+ memset(all_reference_list, 0, sizeof(void*)*(theFieldCounter+1));
}
@@ -988,7 +815,7 @@
false,
ALLOW_DELAY,
current_field->theLevel);
- null_field->theId = ++nr_ids;
+ null_field->theId = ++theFieldCounter;
replace_field(null_field, current_field);
current_field->theParent = NULL;
current_field->theNextSibling = NULL;
@@ -1005,8 +832,8 @@
********************************************************************************/
int Archiver::compute_field_depth(archive_field* field)
{
- archive_field *temp;
- int i=0;
+ archive_field* temp;
+ int i = 0;
temp = field->theParent;
while(temp)
{
@@ -1022,14 +849,16 @@
********************************************************************************/
int Archiver::get_only_for_eval(archive_field* field)
{
- if(field->theOnlyForEval)
+ if (field->theOnlyForEval)
return field->theOnlyForEval;
- archive_field *child;
- for(child = field->theFirstChild; child; child = child->theNextSibling)
+
+ archive_field* child;
+ for (child = field->theFirstChild; child; child = child->theNextSibling)
{
- if(child->theOnlyForEval)
+ if (child->theOnlyForEval)
return child->theOnlyForEval;
}
+
return 0;
}
@@ -1080,55 +909,16 @@
/*******************************************************************************
********************************************************************************/
-void Archiver::exchange_mature_fields(archive_field* field1, archive_field* field2)
-{
- archive_field *field1_prev = get_prev(field1);
- archive_field *field1_next = field1->theNextSibling;
- archive_field *field1_parent = field1->theParent;
- archive_field *field2_prev = get_prev(field2);
- archive_field *field2_parent = field2->theParent;
- archive_field *field2_next = field2->theNextSibling;
- //move field2
- if(field1_prev)
- field1_prev->theNextSibling = field2;
- else
- field1_parent->theFirstChild = field2;
- field2->theNextSibling = field1_next;
- if(!field1_next)
- field1_parent->theLastChild = field2;
- field2->theParent = field1_parent;
- //move field1
- if(field2_prev)
- field2_prev->theNextSibling = field1;
- else
- field2_parent->theFirstChild = field1;
- field1->theNextSibling = field2_next;
- if(!field2_next)
- field2_parent->theLastChild = field1;
- field1->theParent = field2_parent;
-
- ENUM_ALLOW_DELAY temp_delay = field1->theAllowDelay2;
- field1->theAllowDelay2 = field2->theAllowDelay2;
- field2->theAllowDelay2 = temp_delay;
-
- unsigned int temp_order;
- temp_order = field1->theOrder;
- field1->theOrder = field2->theOrder;
- field2->theOrder = temp_order;
-}
-
-
-/*******************************************************************************
-
-********************************************************************************/
void Archiver::check_compound_fields(archive_field* parent_field)
{
//resolve all references first
//iterate: find the reference to the top most eval_only field and resolve it
- archive_field *refering_field;
- while(1)
+ archive_field* refering_field;
+
+ while (1)
{
refering_field = find_top_most_eval_only_field(parent_field);
+
if(!refering_field)
break;
@@ -1137,7 +927,7 @@
!refering_field->theReferredField->theOnlyForEval)
{
//must preserve this serialization
- archive_field *temp_field = refering_field->theReferredField->theParent;
+ archive_field* temp_field = refering_field->theReferredField->theParent;
while(temp_field)
{
temp_field->theOnlyForEval = 0;
@@ -1149,10 +939,15 @@
exchange_mature_fields(refering_field, refering_field->theReferredField);
refering_field->theOnlyForEval = refering_field->theReferredField->theOnlyForEval;
}
- clean_only_for_eval(refering_field->theReferredField, get_only_for_eval(refering_field->theReferredField));
+
+ clean_only_for_eval(refering_field->theReferredField,
+ get_only_for_eval(refering_field->theReferredField));
}
+
while(check_only_for_eval_nondelay_referencing(parent_field))
- {}
+ {
+ }
+
replace_only_for_eval_with_null(parent_field);
}
@@ -1162,7 +957,8 @@
********************************************************************************/
bool Archiver::check_only_for_eval_nondelay_referencing(archive_field* parent_field)
{
- archive_field *current_field = parent_field->theFirstChild;
+ archive_field* current_field = parent_field->theFirstChild;
+
while(current_field)
{
if(current_field->theOnlyForEval && (current_field->theKind != ARCHIVE_FIELD_NORMAL))
@@ -1203,24 +999,26 @@
********************************************************************************/
void Archiver::replace_only_for_eval_with_null(archive_field* parent_field)
{
- archive_field *current_field = parent_field->theFirstChild;
- while(current_field)
+ archive_field* current_field = parent_field->theFirstChild;
+
+ while (current_field)
{
- if(current_field->theOnlyForEval &&
- (current_field->theKind != ARCHIVE_FIELD_NORMAL) &&
- (current_field->theKind != ARCHIVE_FIELD_BASECLASS))
+ if (current_field->theOnlyForEval &&
+ (current_field->theKind != ARCHIVE_FIELD_NORMAL) &&
+ (current_field->theKind != ARCHIVE_FIELD_BASECLASS))
{
- //don't save it, replace it with NULL if possible
- archive_field *null_field = replace_with_null(current_field);
+ //don't save it, replace it with NULL if possible
+ archive_field* null_field = replace_with_null(current_field);
orphan_fields.push_back(current_field);
current_field = null_field;
}
- if(!current_field->theIsSimple)
+ if (!current_field->theIsSimple)
{
replace_only_for_eval_with_null(current_field);
}
+
current_field = current_field->theNextSibling;
}
}
@@ -1231,14 +1029,15 @@
********************************************************************************/
void Archiver::clean_only_for_eval(archive_field* field, int substract_value)
{
- if(field->theOnlyForEval >= substract_value)
+ if (field->theOnlyForEval >= substract_value)
field->theOnlyForEval -= substract_value;
else
field->theOnlyForEval = 0;
- if(!field->theIsSimple)
+
+ if (!field->theIsSimple)
{
- archive_field *child = field->theFirstChild;
- while(child)
+ archive_field* child = field->theFirstChild;
+ while (child)
{
clean_only_for_eval(child, substract_value);
child = child->theNextSibling;
@@ -1248,67 +1047,21 @@
/*******************************************************************************
- return 0 if not found
- return -1 if field1 is before field2
- return 1 if field1 is after field2
-********************************************************************************/
-int Archiver::check_order(
- archive_field* parent_field,
- archive_field* field1,
- archive_field* field2)
-{
-
- if(field1->theOrder < field2->theOrder)
- return -1;
- else if(field1->theOrder == field2->theOrder)
- return 0;
- else
- return 1;
-/*
- archive_field *child;
- int check_ret;
- child = parent_field->theFirstChild;
- while(child)
- {
- if(child == field1)
- return -1;
- else if(child == field2)
- return 1;
- else
- {
- check_ret = check_order(child, field1, field2);
- if(check_ret)
- return check_ret;
- }
- child = child->theNextSibling;
- }
- return 0;
-*/
-}
-
-
-/*******************************************************************************
********************************************************************************/
bool Archiver::check_allowed_delays(archive_field* parent_field)
{
//check all fields with dont_allow_delay and see if they are delayed
//exchange field with the reference then
- archive_field* child;
- child = parent_field->theFirstChild;
+ archive_field* child = parent_field->theFirstChild;
while (child)
{
if (child->theKind == ARCHIVE_FIELD_REFERENCING &&
((child->theAllowDelay2 == DONT_ALLOW_DELAY &&
- check_order(theRootField, child, child->theReferredField) < 1 &&
- child->theAllowDelay2 == DONT_ALLOW_DELAY) ||
+ check_order(child, child->theReferredField) < 1) ||
child->theAllowDelay2 == SERIALIZE_NOW))
{
- if (child->theAllowDelay2 == SERIALIZE_NOW)
- {
- }
-
if (child->theReferredField->theKind == ARCHIVE_FIELD_NORMAL ||
child->theReferredField->theAllowDelay2 == SERIALIZE_NOW)
{
@@ -1316,10 +1069,10 @@
//need to change the serialization order somewhere
throw ZORBA_EXCEPTION(zerr::ZCSE0014_INFINITE_CIRCULAR_DEPENDENCIES);
}
+
//exchange fields
exchange_mature_fields(child, child->theReferredField);
- // child->theReferredField->theAllowDelay2 = ALLOW_DELAY;
child = child->theReferredField;
return true;
@@ -1334,6 +1087,73 @@
return false;
}
+
+/*******************************************************************************
+ return 0 if not found
+ return -1 if field1 is before field2
+ return 1 if field1 is after field2
+********************************************************************************/
+int Archiver::check_order(archive_field* field1, archive_field* field2)
+{
+
+ if (field1->theOrder < field2->theOrder)
+ return -1;
+ else if (field1->theOrder == field2->theOrder)
+ return 0;
+ else
+ return 1;
+}
+
+
+/*******************************************************************************
+
+********************************************************************************/
+void Archiver::exchange_mature_fields(archive_field* field1, archive_field* field2)
+{
+ archive_field* field1_prev = get_prev(field1);
+ archive_field* field1_next = field1->theNextSibling;
+ archive_field* field1_parent = field1->theParent;
+ archive_field* field2_prev = get_prev(field2);
+ archive_field* field2_parent = field2->theParent;
+ archive_field* field2_next = field2->theNextSibling;
+
+ //move field2
+ if (field1_prev)
+ field1_prev->theNextSibling = field2;
+ else
+ field1_parent->theFirstChild = field2;
+
+ field2->theNextSibling = field1_next;
+
+ if (!field1_next)
+ field1_parent->theLastChild = field2;
+
+ field2->theParent = field1_parent;
+
+ //move field1
+ if (field2_prev)
+ field2_prev->theNextSibling = field1;
+ else
+ field2_parent->theFirstChild = field1;
+
+ field1->theNextSibling = field2_next;
+
+ if (!field2_next)
+ field2_parent->theLastChild = field1;
+
+ field1->theParent = field2_parent;
+
+ ENUM_ALLOW_DELAY temp_delay = field1->theAllowDelay2;
+ field1->theAllowDelay2 = field2->theAllowDelay2;
+ field2->theAllowDelay2 = temp_delay;
+
+ unsigned int temp_order;
+ temp_order = field1->theOrder;
+ field1->theOrder = field2->theOrder;
+ field2->theOrder = temp_order;
+}
+
+
} // namsspace serialization
} // namespace zorba
/* vim:set et sw=2 ts=2: */
=== modified file 'src/zorbaserialization/archiver.h'
--- src/zorbaserialization/archiver.h 2012-04-16 20:56:43 +0000
+++ src/zorbaserialization/archiver.h 2012-04-18 08:33:27 +0000
@@ -88,20 +88,24 @@
------------------
See comment for ARCHIVE_FIELD_NORMAL.
- ARCHIVE_FIELD_REFERENCING :
- ------------------------------
+ ARCHIVE_FIELD_REFERENCING:
+ --------------------------
A field A that references another field B (of kind NORMAL or PTR), where both
A and B represent the "same" object.
- ARCHIVE_FIELD_BASECLASS :
- ----------------------------
- A field representing a "partial" class object: If an obj Os belong to a class C
- and C is a subclass of a base class B, then a field of IS_BASECLASS kind is
- created to represent the serialization of the data members of B. This field
- is placed as a child of the NORMAL or PTR field
+ ARCHIVE_FIELD_BASECLASS:
+ ------------------------
+ A field representing a "partial" class object: If an obj O belongs to a
+ concrete class C and C is a subclass of a base class B, then a field of
+ BASECLASS kind is created to represent the serialization of the data members
+ of B. This field is placed as the 1st child of the NORMAL or PTR field that
+ represents the serialization of O, and the children of the BASECALSS field
+ represent the serializations of B's data members. If B itself is a subclass
+ of another class A, then the 1st child of the B BASECLASS field is another
+ BASECLASS field representing class A, etc.
- ARCHIVE_FIELD_NULL :
- -----------------------
+ ARCHIVE_FIELD_NULL:
+ -------------------
A field representing a NULL pointer.
********************************************************************************/
@@ -127,19 +131,6 @@
/*******************************************************************************
-
-********************************************************************************/
-struct fwd_ref
-{
- int referencing;
- void ** ptr;
- bool is_class;
- char * class_name;
- bool to_add_ref;
-};
-
-
-/*******************************************************************************
theId :
-------
The unique id of the field. Not initialized by constructor.
@@ -310,6 +301,27 @@
-------------------
Whether the archiver is used to serialize or deserialize a plan.
+ theSerializeBaseClass:
+ ----------------------
+ If true, then we are in the process of (de)serializing a class obj O, and the
+ next bunch of data members to serialize belong to an internal class in the
+ class hierarchy. These data members will form a fields subtree, rooted at a
+ field of kind BASECLASS, within the bigger subtree of obj O. This data member
+ is required in order for the function operator&(Archiver& ar, T*& obj) to know
+ which serialize_internal() method to invoke.
+
+ theIsTempField:
+ ---------------
+ If > 0, then the next obj to (de)serialize should not be registered or looked
+ up in any of the fields registries. This is the case when, for example, we are
+ seriazing an obj that resides on the program stack
+
+ theFieldCounter:
+ ----------------
+ The number of fields generated so far (during serialization). It is used to
+ generated field ids. It is written to "disk" and used, during deserializrion
+ to allocate the correct size for the all_references_list.
+
theRootField :
--------------
The root of the fields tree.
@@ -370,37 +382,39 @@
SimpleHashoutFieldCompare> SimpleFieldMap;
protected:
- bool theSerializingOut;
-
- int serialize_base_class;
-
- void ** all_reference_list;
-
- std::list<struct fwd_ref> fwd_reference_list;
-
std::string theArchiveName;
+
std::string theArchiveInfo;
+
unsigned long theArchiveVersion;
+ bool theSerializingOut;
+
+ int theSerializeBaseClass;
+
+ int theIsTempField;
+
+ int theFieldCounter;
+
archive_field * theRootField;
archive_field * theCurrentCompoundField;
- SimpleFieldMap * theSimpleFieldsMap;
-
- hash64map<archive_field*> * hash_out_fields;//key is ptr, value is archive_field*, for non-simple types
+ unsigned int theCurrentLevel;
+
+ SimpleFieldMap * theNonClassFieldsMap;
+
+ hash64map<archive_field*> * theClassFieldsMap;
+
+
+ void ** all_reference_list;
+
std::vector<archive_field*> orphan_fields;
- int nr_ids;
-
int current_class_version;
bool read_optional;
- int theIsTempField;
-
- unsigned int theCurrentLevel;
-
std::stack< std::pair<unsigned int, bool> > limit_temp_level_stack;
bool internal_archive;
@@ -485,6 +499,18 @@
archive_field* lookup_class_field(const SerializeBaseClass* ptr);
+ archive_field* get_prev(archive_field* field);
+
+ void prepare_serialize_out();
+
+ void check_compound_fields(archive_field* parent_field);
+
+ bool check_allowed_delays(archive_field* parent_field);
+
+ int check_order(archive_field* field1, archive_field* field2);
+
+ void exchange_mature_fields(archive_field* field1, archive_field* field2);
+
virtual void serialize_out() = 0;
//
@@ -500,7 +526,7 @@
*archive_name = theArchiveName;
*archive_info = theArchiveInfo;
*archive_version = theArchiveVersion;
- *nr_ids = this->nr_ids;
+ *nr_ids = this->theFieldCounter;
}
//
@@ -508,14 +534,10 @@
//
void replace_field(archive_field* new_field, archive_field* ref_field);
- void exchange_fields(archive_field* new_field, archive_field* ref_field);
-
void root_tag_is_read();
void register_pointers_internal(archive_field* fields);
- void prepare_serialize_out();
-
archive_field* replace_with_null(archive_field* current_field);
int compute_field_depth(archive_field* field);
@@ -524,26 +546,40 @@
archive_field* find_top_most_eval_only_field(archive_field* parent_field);
- void check_compound_fields(archive_field* parent_field);
-
bool check_only_for_eval_nondelay_referencing(archive_field* parent_field);
void replace_only_for_eval_with_null(archive_field* parent_field);
void clean_only_for_eval(archive_field* field, int substract_value);
- void exchange_mature_fields(archive_field* field1, archive_field* field2);
-
- archive_field* get_prev(archive_field* field);
-
- int check_order(
- archive_field* parent_field,
- archive_field* field1,
- archive_field* field2);
-
- bool check_allowed_delays(archive_field* parent_field);
-
public:
+ void set_serialize_base_class(bool s)
+ {
+ if (s)
+ theSerializeBaseClass++;
+ else
+ theSerializeBaseClass--;
+
+ assert(theSerializeBaseClass >= 0);
+ assert(theSerializeBaseClass <= 1);
+ }
+
+ bool is_serialize_base_class() { return theSerializeBaseClass > 0; }
+
+ void set_is_temp_field(bool is_temp)
+ {
+ if (is_temp)
+ theIsTempField++;
+ else
+ theIsTempField--;
+
+ assert(theIsTempField >= 0);
+ }
+
+ bool get_is_temp_field() { return (theIsTempField > 0); }
+
+ int get_num_fields() { return theFieldCounter; }
+
void check_simple_field(
bool retval,
const char* type,
@@ -578,33 +614,8 @@
enum ArchiveFieldKind field_treat,
const void* ptr);
- void register_delay_reference(
- void** ptr,
- bool is_class,
- const char* class_name,
- int referencing);
-
- void reconf_last_delayed_rcobject(
- void** last_obj,
- void** new_last_obj,
- bool to_add_ref);
-
void register_item(store::Item* i);
- //to help check class name at runtime
- void set_serialize_base_class(bool s)
- {
- if (s)
- serialize_base_class++;
- else
- serialize_base_class--;
-
- assert(serialize_base_class >= 0);
- assert(serialize_base_class <= 1);
- }
-
- bool is_serialize_base_class() { return serialize_base_class > 0; }
-
void* get_reference_value(int refid);
void finalize_input_serialization();
@@ -616,18 +627,6 @@
bool get_read_optional_field() { return this->read_optional; }
- void set_is_temp_field(bool is_temp)
- {
- if (is_temp)
- theIsTempField++;
- else
- theIsTempField--;
-
- assert(theIsTempField >= 0);
- }
-
- bool get_is_temp_field() { return (theIsTempField > 0); }
-
void set_is_temp_field_one_level(bool is_temp, bool also_for_ptr = false)
{
if (is_temp)
@@ -674,8 +673,6 @@
limit_temp_level_stack.top().second);
}
- int get_nr_ids();
-
bool is_serialize_everything() { return theSerializeEverything; }
void set_serialize_everything() { theSerializeEverything = true; }
=== modified file 'src/zorbaserialization/bin_archiver.cpp'
--- src/zorbaserialization/bin_archiver.cpp 2012-04-16 20:56:43 +0000
+++ src/zorbaserialization/bin_archiver.cpp 2012-04-18 08:33:27 +0000
@@ -78,7 +78,7 @@
read_string(theArchiveName);
read_string(theArchiveInfo);
theArchiveVersion = read_int();
- nr_ids = read_int();
+ theFieldCounter = read_int();
unsigned int is_release = read_int();
#ifndef NDEBUG
if(is_release)
@@ -223,7 +223,7 @@
os->write(theArchiveInfo.c_str(), (std::streamsize)theArchiveInfo.length()+1);
write_int(theArchiveVersion);
- write_int(nr_ids);
+ write_int(theFieldCounter);
#ifndef NDEBUG
write_int(0);//for debug
=== modified file 'src/zorbaserialization/class_serializer.h'
--- src/zorbaserialization/class_serializer.h 2012-04-16 20:56:43 +0000
+++ src/zorbaserialization/class_serializer.h 2012-04-18 08:33:27 +0000
@@ -164,8 +164,6 @@
virtual ~ClassDeserializer() { }
virtual SerializeBaseClass* create_new(Archiver& ar) = 0;
-
- virtual void cast_ptr(SerializeBaseClass* ptr, void** class_ptr) = 0;
};
@@ -184,11 +182,6 @@
{ \
return creator; \
} \
- \
- virtual void cast_ptr(serialization::SerializeBaseClass* ptr, void** class_ptr)\
- { \
- *class_ptr = (void*)dynamic_cast<T_serialized_class*>(ptr); \
- } \
};
=== modified file 'src/zorbaserialization/serialize_basic_types.cpp'
--- src/zorbaserialization/serialize_basic_types.cpp 2012-04-08 06:14:11 +0000
+++ src/zorbaserialization/serialize_basic_types.cpp 2012-04-18 08:33:27 +0000
@@ -26,6 +26,7 @@
#include "diagnostics/xquery_diagnostics.h"
#include "diagnostics/util_macros.h"
+#include "diagnostics/assert.h"
namespace zorba
@@ -489,7 +490,7 @@
}
else if ((obj = (char*)ar.get_reference_value(referencing)) == NULL)// ARCHIVE_FIELD_IS_REFERENCING
{
- ar.register_delay_reference((void**)&obj, !FIELD_IS_CLASS, NULL, referencing);
+ ZORBA_ASSERT(false);
}
}
}
@@ -802,7 +803,7 @@
}
else if ((obj = (std::string*)ar.get_reference_value(referencing)) == NULL)
{
- ar.register_delay_reference((void**)&obj, !FIELD_IS_CLASS, NULL, referencing);
+ ZORBA_ASSERT(false);
}
}
}
=== modified file 'src/zorbaserialization/serialize_basic_types.h'
--- src/zorbaserialization/serialize_basic_types.h 2012-04-04 09:57:46 +0000
+++ src/zorbaserialization/serialize_basic_types.h 2012-04-18 08:33:27 +0000
@@ -68,7 +68,7 @@
#define SERIALIZE_ENUM(enum_type, obj) \
{ \
- ar.set_is_temp_field_one_level(true); \
+ ar.set_is_temp_field(true); \
\
int int_enum = (int)obj; \
ar & int_enum; \
@@ -76,7 +76,7 @@
if (!ar.is_serializing_out()) \
obj = (enum_type)int_enum; \
\
- ar.set_is_temp_field_one_level(false); \
+ ar.set_is_temp_field(false); \
}
=== modified file 'src/zorbaserialization/serialize_template_types.h'
--- src/zorbaserialization/serialize_template_types.h 2012-04-13 18:41:58 +0000
+++ src/zorbaserialization/serialize_template_types.h 2012-04-18 08:33:27 +0000
@@ -28,6 +28,7 @@
#include "util/string_util.h"
#include "util/stl_util.h"
#include "diagnostics/xquery_diagnostics.h"
+#include "diagnostics/assert.h"
#include "zorbatypes/zstring.h"
#include "archiver.h"
@@ -270,15 +271,15 @@
}
else
{
- ar.register_delay_reference((void**)&obj,
- FIELD_IS_CLASS,
- obj->T::get_class_name_str(),
- referencing);
+ ZORBA_ASSERT(false);
}
}
}
+/*******************************************************************************
+
+********************************************************************************/
template<class T>
void operator&(Archiver& ar, checked_vector<T>& obj)
{
@@ -514,10 +515,7 @@
}
else
{
- ar.register_delay_reference((void**)&obj,
- !FIELD_IS_CLASS,
- "std::vector<T>*",
- referencing);
+ ZORBA_ASSERT(false);
}
}
}
@@ -798,10 +796,7 @@
}
else
{
- ar.register_delay_reference((void**)&obj,
- !FIELD_IS_CLASS,
- "std::pair<T1, T2>",
- referencing);
+ ZORBA_ASSERT(false);
}
}
}
@@ -925,10 +920,7 @@
}
else
{
- ar.register_delay_reference((void**)&obj,
- !FIELD_IS_CLASS,
- "std::map<T1, T2>",
- referencing);
+ ZORBA_ASSERT(false);
}
}
}
=== modified file 'src/zorbaserialization/serialize_zorba_types.cpp'
--- src/zorbaserialization/serialize_zorba_types.cpp 2012-04-13 18:41:58 +0000
+++ src/zorbaserialization/serialize_zorba_types.cpp 2012-04-18 08:33:27 +0000
@@ -840,6 +840,7 @@
{
if(!is_node)
ar.register_item(obj);
+
ar.read_end_current_level();
}
else
@@ -855,8 +856,10 @@
);
}
}
- else if(!ar.get_is_temp_field() && !ar.get_is_temp_field_one_level())
- ar.register_delay_reference((void**)&obj, FIELD_IS_CLASS, "store::Item*", referencing);
+ else if (!ar.get_is_temp_field() && !ar.get_is_temp_field_one_level())
+ {
+ ZORBA_ASSERT(false);
+ }
else
obj = NULL;
}
@@ -1081,7 +1084,9 @@
}
}
else if(!ar.get_is_temp_field() && !ar.get_is_temp_field_one_level())
- ar.register_delay_reference((void**)&obj, FIELD_IS_CLASS, "store::Item*", referencing);
+ {
+ ZORBA_ASSERT(false);
+ }
else
obj = NULL;
}
@@ -1204,7 +1209,7 @@
}
else
{
- ar.register_delay_reference((void**)&obj, !FIELD_IS_CLASS, "Diagnostic*", referencing);
+ ZORBA_ASSERT(false);
}
}
@@ -1284,13 +1289,15 @@
ar.read_end_current_level();
return;
}
- if(field_treat == ARCHIVE_FIELD_PTR)
+
+ if (field_treat == ARCHIVE_FIELD_PTR)
{
int is_user, is_xquery;
sscanf(value.c_str(), "u%dx%d", &is_user, &is_xquery);
- UserException *user_ex = NULL;
- XQueryException *xquery_ex = NULL;
- if(is_user)
+ UserException* user_ex = NULL;
+ XQueryException* xquery_ex = NULL;
+
+ if (is_user)
{
user_ex = new UserException(ar);
xquery_ex = user_ex;
@@ -1327,7 +1334,7 @@
}
else
{
- ar.register_delay_reference((void**)&obj, !FIELD_IS_CLASS, "ZorbaException*", referencing);
+ ZORBA_ASSERT(false);
}
}
@@ -1337,7 +1344,7 @@
/*******************************************************************************
********************************************************************************/
-void operator&(Archiver &ar, zorba::internal::diagnostic::location &obj)
+void operator&(Archiver& ar, zorba::internal::diagnostic::location& obj)
{
if(ar.is_serializing_out())
{
@@ -1385,7 +1392,7 @@
/*******************************************************************************
********************************************************************************/
-void operator&(Archiver &ar, zorba::Item &obj)
+void operator&(Archiver& ar, zorba::Item& obj)
{
if(ar.is_serializing_out())
{
=== modified file 'src/zorbaserialization/serialize_zorba_types.h'
--- src/zorbaserialization/serialize_zorba_types.h 2012-04-12 15:21:51 +0000
+++ src/zorbaserialization/serialize_zorba_types.h 2012-04-18 08:33:27 +0000
@@ -182,19 +182,6 @@
obj = p;
- if (p == NULL)
- {
- //workaround for the strict_aliasing warning in gcc
- union
- {
- T **t;
- void **v;
- } u_p;
-
- u_p.t = &p;
- ar.reconf_last_delayed_rcobject(u_p.v, obj.getp_ref().v, true);
- }
-
ar.read_end_current_level();
}
}
@@ -267,24 +254,15 @@
is_temp = true;
ar.set_is_temp_field_one_level(true, ar.get_is_temp_field_also_for_ptr());
}
- T *p;
+
+ T* p;
+
ar & p;
- if(is_temp)
+
+ if (is_temp)
ar.set_is_temp_field_one_level(false);
+
obj = p;
- if(p == NULL)
- {
- //workaround for the strict_aliasing warning in gcc
- union
- {
- T **t;
- void **v;
- } u_p;
-
- u_p.t = &p;
-
- ar.reconf_last_delayed_rcobject(u_p.v, obj.getp_ref().v, true);
- }
ar.read_end_current_level();
}
@@ -306,7 +284,7 @@
ARCHIVE_FIELD_NORMAL);
if (!is_ref)
{
- T *p = (T*)obj.getp();
+ T* p = (T*)obj.getp();
if (allow_delay != ALLOW_DELAY)
ar.dont_allow_delay(allow_delay);
@@ -360,23 +338,14 @@
}
T* p;
+
ar & p;
+
obj = p;
if (is_temp)
ar.set_is_temp_field_one_level(false);
- if (p == NULL)
- {
- //workaround for the strict_aliasing warning in gcc
- union
- {
- T **t;
- void **v;
- }u_p;
- u_p.t = &p;
- ar.reconf_last_delayed_rcobject(u_p.v, obj.getp_ref().v, true);
- }
ar.read_end_current_level();
}
}
=== modified file 'src/zorbaserialization/xml_archiver.cpp'
--- src/zorbaserialization/xml_archiver.cpp 2012-04-16 20:56:43 +0000
+++ src/zorbaserialization/xml_archiver.cpp 2012-04-18 08:33:27 +0000
@@ -96,7 +96,7 @@
encode_string(theArchiveInfo.c_str());
write_string("\" ");
*os << "archive_version=\"" << theArchiveVersion << "\" ";
- *os << "nr_ids=\"" << nr_ids << "\" >" << std::endl;
+ *os << "nr_ids=\"" << theFieldCounter << "\" >" << std::endl;
serialize_compound_fields(theRootField);
write_string("</zorba_archive>\n");
}
@@ -420,7 +420,7 @@
else if(!strcmp(attrib_name, "nr_ids"))
{
read_attrib_value(attrib_value);
- nr_ids = atoi(attrib_value);
+ theFieldCounter = atoi(attrib_value);
}
}
root_tag_is_read();
Follow ups