Commit 95a568f0 authored by Kirill Terekhov's avatar Kirill Terekhov
Browse files

Updates and bugfixes

Added 2-clause bsd license for cmake files requested in cmake script for
petsc.
Introduced cmake option for Mondriaan matrix partitioning package for
solvers.
Changed reading of solver's parameters database to fix uninitialized
access reported by dr.memory.
Fixed bug in svdnxn with static std::vector allocation.
Added features to OldDrawGrid example.
Added solutions to problems described in issue #13.
parent 821a833b
......@@ -80,6 +80,7 @@ option(COMPILE_TESTS "Compile some tests" OFF)
option(USE_PARTITIONER_PARMETIS "Use ParMetis partitioner" OFF)
option(USE_PARTITIONER_ZOLTAN "Use Zoltan partitioner" OFF)
option(USE_SOLVER_METIS "Use METIS for matrix reordering" OFF)
option(USE_SOLVER_MONDRIAAN "Use Mondriaan for matrix reordering" OFF)
option(USE_SOLVER_PETSC "Use PETSc solvers" OFF)
option(USE_SOLVER_TRILINOS "Use Trilinos solvers" OFF)
#option(USE_AUTODIFF_OPENCL "Use OpenCL for automatic differentiation (under work)" OFF)
......@@ -153,6 +154,20 @@ if(USE_SOLVER_METIS)
endif()
endif()
if(USE_SOLVER_MONDRIAAN)
find_package(MONDRIAAN)
if(NOT MONDRIAAN_FOUND)
set(USE_SOLVER_MONDRIAAN OFF)
message("Mondriaan NOT FOUND")
else()
link_directories(${MONDRIAAN_LIBRARY_DIRS})
include_directories(${MONDRIAAN_INCLUDE_DIRS})
set(USE_SOLVER_MONDRIAAN ON)
message("Mondriaan FOUND")
endif()
endif()
if(USE_PARTITIONER_ZOLTAN)
find_package(ZOLTAN)
if(NOT ZOLTAN_FOUND)
......
......@@ -2,6 +2,6 @@ Copy and paste contents of autoexp.dat into
C:\Program Files (x86)\Microsoft Visual Studio 10.0\Common7\Packages\Debugger\autoexp.dat
or the directry where Visual Studio was installed.
In future capabilities will grove.
In future capabilities will grow.
Tested with Visual studio 2010.
Copyright (c) 2014-2015
All rights reserved.
Redistribution and use in source and binary forms, with or without
modification, are permitted provided that the following conditions are met:
* Redistributions of source code must retain the above copyright notice, this
list of conditions and the following disclaimer.
* Redistributions in binary form must reproduce the above copyright notice,
this list of conditions and the following disclaimer in the documentation
and/or other materials provided with the distribution.
THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS "AS IS"
AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE
IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE
DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT HOLDER OR CONTRIBUTORS BE LIABLE
FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL
DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR
SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER
CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY,
OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE
OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
This folder contains scripts for CMake that aid in compilation of the INMOST library with third party libraries.
The original files were obtained through internet from the following projects:
- PETSc
- MSTK
- FindOpenCL
And may appear in original or modified form.
\ No newline at end of file
......@@ -34,6 +34,10 @@ if(OPENGL_FOUND)
message("linking DrawMatrix with Metis")
target_link_libraries(DrawMatrix ${METIS_LIBRARIES})
endif()
if(USE_SOLVER_MONDRIAAN)
message("linking DrawMatrix with Mondriaan")
target_link_libraries(DrawMatrix ${MONDRIAAN_LIBRARIES})
endif()
endif()
......
......@@ -25,6 +25,10 @@ if(USE_SOLVER)
message("linking FVDiscr with Metis")
target_link_libraries(FVDiscr ${METIS_LIBRARIES})
endif()
if(USE_SOLVER_MONDRIAAN)
message("linking FVDiscr with Mondriaan")
target_link_libraries(FVDiscr ${MONDRIAAN_LIBRARIES})
endif()
endif()
......
......@@ -127,7 +127,7 @@ int main(int argc,char ** argv)
if( m->GetProcessorRank() == 0 ) std::cout << "Exchange ghost: " << Timer()-ttt << std::endl;
ttt = Timer();
Solver S(Solver::INNER_ILU2); // Specify the linear solver to ASM+ILU2+BiCGStab one
Solver S(Solver::INNER_ILU2); // Specify the linear solver to ASM+ILU2+BiCGStab one
Solver::Matrix A; // Declare the matrix of the linear system to be solved
Solver::Vector x,b; // Declare the solution and the right-hand side vectors
......@@ -242,6 +242,8 @@ int main(int argc,char ** argv)
ttt = Timer();
Tag error = m->CreateTag("error",DATA_REAL,CELL,NONE,1);
Storage::real err_C = 0.0, err_L2 = 0.0;
for( Mesh::iteratorCell cell = m->BeginCell(); cell != m->EndCell(); ++cell )
if( cell->GetStatus() != Element::Ghost )
......@@ -251,6 +253,7 @@ int main(int argc,char ** argv)
if (err > err_C)
err_C = err;
err_L2 += err * err * cell->Volume();
cell->Real(error) = err;
// x[cell->Integer(id)] = err;
}
err_C = m->AggregateMax(err_C); // Compute the maximal C norm for the error
......
......@@ -33,6 +33,10 @@ if(USE_SOLVER)
message("linking MatSolve with Metis")
target_link_libraries(MatSolve ${METIS_LIBRARIES})
endif()
if(USE_SOLVER_MONDRIAAN)
message("linking MatSolve with Mondriaan")
target_link_libraries(MatSolve ${MONDRIAAN_LIBRARIES})
endif()
endif()
......
This diff is collapsed.
......@@ -168,6 +168,46 @@ void rotatevector(double * vec)
vec[2] = ret[2]/ret[3];
}
void reverse_rotatevector(double * vec)
{
int i;
double rot[16];
double temp[4] = {vec[0],vec[1],vec[2],1.0};
double ret[4];
q.x = -q.x;
q.y = -q.y;
q.z = -q.z;
rot[ 0] = (q.w*q.w + q.x*q.x - q.y*q.y - q.z*q.z);
rot[ 1] = 2.*(q.x*q.y - q.w*q.z);
rot[ 2] = 2.*(q.x*q.z + q.w*q.y);
rot[ 3] = 0.0;
rot[ 4] = 2.*(q.x*q.y + q.w*q.z);
rot[ 5] = (q.w*q.w - q.x*q.x + q.y*q.y - q.z*q.z);
rot[ 6] = 2.*(q.y*q.z - q.w*q.x);
rot[ 7] = 0.0;
rot[ 8] = 2.*(q.x*q.z - q.w*q.y);
rot[ 9] = 2.*(q.y*q.z + q.w*q.x);
rot[10] = (q.w*q.w - q.x*q.x - q.y*q.y + q.z*q.z);
rot[11] = 0.0;
rot[12] = 0.0;
rot[13] = 0.0;
rot[14] = 0.0;
rot[15] = (q.w*q.w + q.x*q.x + q.y*q.y + q.z*q.z);
for(i=0; i < 4; i++)
{
ret[i] = temp[0] * rot[i*4];
ret[i] += temp[1] * rot[i*4+1];
ret[i] += temp[2] * rot[i*4+2];
ret[i] += temp[3] * rot[i*4+3];
}
vec[0] = ret[0]/ret[3];
vec[1] = ret[1]/ret[3];
vec[2] = ret[2]/ret[3];
q.x = -q.x;
q.y = -q.y;
q.z = -q.z;
}
void revrotatevector(double * vec)
{
int i;
......@@ -240,6 +280,51 @@ void rotatevector_from_stack(double * vec)
vec[2] = ret[2]/ret[3];
}
void quatget(double *vec)
{
vec[0] = q.x / q.w;
vec[1] = q.y / q.w;
vec[2] = q.z / q.w;
}
void reverse_rotatevector_from_stack(double * vec)
{
int i;
struct quaternion q = storage.back();
q.x = -q.x;
q.y = -q.y;
q.z = -q.z;
double rot[16];
double temp[4] = {vec[0],vec[1],vec[2],1.0};
double ret[4];
rot[ 0] = (q.w*q.w + q.x*q.x - q.y*q.y - q.z*q.z);
rot[ 1] = 2.*(q.x*q.y - q.w*q.z);
rot[ 2] = 2.*(q.x*q.z + q.w*q.y);
rot[ 3] = 0.0;
rot[ 4] = 2.*(q.x*q.y + q.w*q.z);
rot[ 5] = (q.w*q.w - q.x*q.x + q.y*q.y - q.z*q.z);
rot[ 6] = 2.*(q.y*q.z - q.w*q.x);
rot[ 7] = 0.0;
rot[ 8] = 2.*(q.x*q.z - q.w*q.y);
rot[ 9] = 2.*(q.y*q.z + q.w*q.x);
rot[10] = (q.w*q.w - q.x*q.x - q.y*q.y + q.z*q.z);
rot[11] = 0.0;
rot[12] = 0.0;
rot[13] = 0.0;
rot[14] = 0.0;
rot[15] = (q.w*q.w + q.x*q.x + q.y*q.y + q.z*q.z);
for(i=0; i < 4; i++)
{
ret[i] = temp[0] * rot[i*4];
ret[i] += temp[1] * rot[i*4+1];
ret[i] += temp[2] * rot[i*4+2];
ret[i] += temp[3] * rot[i*4+3];
}
vec[0] = ret[0]/ret[3];
vec[1] = ret[1]/ret[3];
vec[2] = ret[2]/ret[3];
}
void rotate()
{
double rot[16];
......
......@@ -20,13 +20,16 @@
void clickmotion(int nmx, int nmy);
void motion(int nmx, int nmy);
void click(int b, int s, int nmx, int nmy);
void quatget(double * vec);
void quatinit();
void quatpush();
void quatpop();
void rotate();
void rotate_from_stack();
void rotatevector(double * vec);
void reverse_rotatevector(double * vec);
void revrotatevector(double * vec);
void rotatevector_from_stack(double * vec);
void reverse_rotatevector_from_stack(double * vec);
#endif
......@@ -25,6 +25,10 @@ if(USE_SOLVER)
message("linking Solver with Metis")
target_link_libraries(Solver ${METIS_LIBRARIES})
endif()
if(USE_SOLVER_MONDRIAAN)
message("linking Solver with Mondriaan")
target_link_libraries(Solver ${MONDRIAAN_LIBRARIES})
endif()
endif(USE_SOLVER)
if(USE_PARTITIONER)
......
......@@ -529,6 +529,9 @@ namespace INMOST
void Mesh::GetGeometricData(HandleType e, GeometricData type, Storage::real * ret)
{
assert(e != InvalidHandle());
assert(ret != NULL);
assert(type == MEASURE || type == CENTROID || type == BARYCENTER || type == NORMAL);
ElementType etype = GetHandleElementType(e);
integer edim = Element::GetGeometricDimension(GetGeometricType(e));
integer mdim = GetDimensions();
......
......@@ -27,6 +27,8 @@ set(INMOST_LIBRARIES inmost)
set(USE_MPI @USE_MPI@)
set(USE_PARTITIONER_ZOLTAN @USE_PARTITIONER_ZOLTAN@)
set(USE_PARTITIONER_PARMETIS @USE_PARTITIONER_PARMETIS@)
set(USE_SOLVER_MONDRIAAN @USE_SOLVER_MONDRIAAN@)
set(USE_SOLVER_METIS @USE_SOLVER_METIS@)
set(USE_SOLVER_TRILINOS @USE_SOLVER_TRILINOS@)
set(USE_SOLVER_PETSC @USE_SOLVER_PETSC@)
......@@ -49,6 +51,16 @@ if( USE_PARTITIONER_PARMETIS )
list(APPEND INMOST_INCLUDE_DIRS "@METIS_INCLUDE_DIR@")
endif( USE_PARTITIONER_PARMETIS )
if( USE_SOLVER_MONDRIAAN )
list(APPEND INMOST_LIBRARIES "@MONDRIAAN_LIBRARIES@")
list(APPEND INMOST_INCLUDE_DIRS "@MONDRIAAN_INCLUDE_DIRS@")
list(APPEND INMOST_LIBRARY_DIRS "@MONDRIAAN_LIBRARY_DIRS@")
endif( USE_SOLVER_MONDRIAAN )
if( USE_SOLVER_METIS )
list(APPEND INMOST_LIBRARIES "@METIS_LIBRARIES@")
list(APPEND INMOST_INCLUDE_DIRS "@METIS_INCLUDE_DIR@")
endif( USE_SOLVER_METIS )
if( USE_SOLVER_TRILINOS )
list(APPEND INMOST_LIBRARIES "@Trilinos_LIBRARIES@")
......
......@@ -15,6 +15,7 @@
#cmakedefine USE_PARTITIONER_PARMETIS
#cmakedefine USE_SOLVER
#cmakedefine USE_SOLVER_MONDRIAAN
#cmakedefine USE_SOLVER_METIS
#cmakedefine USE_SOLVER_PETSC
#cmakedefine USE_SOLVER_TRILINOS
......
......@@ -76,7 +76,7 @@ namespace INMOST
{
if( size )
{
const Storage::integer * recv = static_cast<const Storage::integer *>(static_cast<const void *>(data));
const Storage::integer * recv = static_cast<const Storage::integer *>(static_cast<const void *>(data));
Storage::integer_array arr = e->IntegerArray(tag);
arr.push_back(recv[0]);
}
......@@ -87,20 +87,26 @@ namespace INMOST
{
if( size )
{
bool flag = true;
const Storage::integer * recv = static_cast<const Storage::integer *>(static_cast<const void *>(data));
Storage::integer_array arr = e->IntegerArray(tag);
for(Storage::integer_array::iterator it = arr.begin(); it != arr.end(); it+=2)
if( *it == recv[0] )
{
flag = false;
break;
}
if( flag )
{
arr.push_back(recv[0]);
arr.push_back(recv[1]);
}
for(INMOST_DATA_ENUM_TYPE k = 0; k < size; k+=2 )
{
bool flag = true;
const Storage::integer * recv = static_cast<const Storage::integer *>(static_cast<const void *>(data))+k;
Storage::integer_array arr = e->IntegerArray(tag);
for(Storage::integer_array::iterator it = arr.begin(); it != arr.end(); it+=2)
{
if( *it == recv[0] )
{
flag = false;
break;
}
}
if( flag )
{
arr.push_back(recv[0]);
arr.push_back(recv[1]);
}
}
}
}
......@@ -1005,7 +1011,7 @@ namespace INMOST
//~ #else
std::vector<unsigned> sendsizeall(mpisize*2);
int pack_size2 = 0;
unsigned long usend[2] = {static_cast<unsigned>(sendsize),static_cast<unsigned>(pack_real.size())};
unsigned usend[2] = {static_cast<unsigned>(sendsize),static_cast<unsigned>(pack_real.size())};
MPI_Pack_size(2,MPI_UNSIGNED,comm,&pack_size2);
for(dynarray<integer,64>::size_type k = 0; k < procs.size(); k++)
{
......@@ -1160,6 +1166,8 @@ namespace INMOST
REPORT_VAL("type",ElementTypeName(current_mask));
//int owned_elems = 0;
//int shared_elems = 0;
int owner;
Element::Status estat;
......@@ -1173,10 +1181,19 @@ namespace INMOST
{
p.clear();
p.push_back(mpirank);
//++owned_elems;
}
else p.replace(p.begin(),p.end(),result.begin(),result.end());
else
{
p.replace(p.begin(),p.end(),result.begin(),result.end());
//if( result.size() == 1 && result[0] == mpirank )
// ++owned_elems;
//else ++shared_elems;
}
}
time = Timer() - time;
//REPORT_VAL("predicted owned elements",owned_elems);
//REPORT_VAL("predicted shared elements",shared_elems);
REPORT_STR("Predict processors for elements");
REPORT_VAL("time",time);
......@@ -1184,6 +1201,7 @@ namespace INMOST
time = Timer();
//Initialize mapping that helps get local id by global id
std::vector<std::pair<int,int> > mapping;
REPORT_VAL("mapping type",ElementTypeName(current_mask >> 1));
for(Mesh::iteratorElement it = BeginElement(current_mask >> 1); it != EndElement(); it++)
{
mapping.push_back(std::make_pair(it->GlobalID(),it->LocalID()));
......@@ -1191,6 +1209,7 @@ namespace INMOST
if( !mapping.empty() )
std::sort(mapping.begin(),mapping.end(),MappingComparator());
time = Timer() - time;
REPORT_VAL("mapping size",mapping.size())
REPORT_STR("Compute global to local indexes mapping");
REPORT_VAL("time",time);
//Initialize arrays
......@@ -1227,6 +1246,8 @@ namespace INMOST
elements[m].push_back(*it);
}
}
REPORT_VAL("for processor",*p);
REPORT_VAL("gathered elements",elements[m].size());
message_send[0] = static_cast<int>(message_send.size());
MPI_Pack_size(static_cast<INMOST_MPI_SIZE>(message_send.size()),MPI_INT,comm,&sendsize);
send_buffs[m].first = *p;
......@@ -1264,6 +1285,7 @@ namespace INMOST
}
if( pos == -1 ) throw Impossible;
MPI_Unpack(&recv_buffs[*qt].second[0],static_cast<INMOST_MPI_SIZE>(recv_buffs[*qt].second.size()),&position,&size,1,MPI_INT,comm);
REPORT_VAL("unpacked message size",size-1);
message_recv[pos].resize(size-1);
MPI_Unpack(&recv_buffs[*qt].second[0],static_cast<INMOST_MPI_SIZE>(recv_buffs[*qt].second.size()),&position,&message_recv[pos][0],static_cast<INMOST_MPI_SIZE>(message_recv[pos].size()),MPI_INT,comm);
}
......@@ -1301,7 +1323,7 @@ namespace INMOST
break;
}
int find_local_id = mapping[find].second;
sub_elements.push_back(ComposeHandle(current_mask >> 1, find_local_id));
sub_elements.push_back(ComposeHandle(PrevElementType(current_mask), find_local_id));
}
if( flag )
......@@ -1311,14 +1333,32 @@ namespace INMOST
remote_elements.push_back(e);
}
}
REPORT_VAL("number of unpacked remote elements",remote_elements.size());
if( !remote_elements.empty() )
{
REPORT_VAL("first",remote_elements.front());
REPORT_VAL("first type",ElementTypeName(GetHandleElementType(remote_elements.front())));
REPORT_VAL("last",remote_elements.back());
REPORT_VAL("last type",ElementTypeName(GetHandleElementType(remote_elements.back())));
}
std::sort(remote_elements.begin(),remote_elements.end());
REPORT_VAL("original elements size",elements[m].size());
if( !elements[m].empty() )
{
REPORT_VAL("first",elements[m].front());
REPORT_VAL("first type",ElementTypeName(GetHandleElementType(elements[m].front())));
REPORT_VAL("last",elements[m].back());
REPORT_VAL("last type",ElementTypeName(GetHandleElementType(elements[m].back())));
}
std::sort(elements[m].begin(),elements[m].end());
element_set result;
element_set::iterator set_end;
result.resize(elements[m].size());
set_end = std::set_difference(elements[m].begin(),elements[m].end(),remote_elements.begin(),remote_elements.end(), result.begin());
result.resize(set_end-result.begin());
result.resize(set_end-result.begin());
REPORT_VAL("set difference size",result.size());
//elements in result are wrongly marked as ghost
for(element_set::iterator qt = result.begin(); qt != result.end(); qt++)
......@@ -1799,6 +1839,9 @@ namespace INMOST
Tag tag_skin = CreateTag("TEMPORARY_COMPUTE_SHARED_SKIN_SET",DATA_INTEGER,FACE,FACE);
REPORT_STR("filling neighbouring cell's global identificators for faces")
#if defined(USE_PARALLEL_WRITE_TIME)
std::map<int,int> numfacesperproc;
#endif
for(iteratorFace it = BeginFace(); it != EndFace(); it++)
{
......@@ -1807,30 +1850,68 @@ namespace INMOST
{
Storage::integer_array arr = it->IntegerArray(tag_skin);
ElementArray<Element> adj = it->getAdjElements(CELL);
//REPORT_STR("face " << it->LocalID() << " global " << it->GlobalID() << " type " << Element::StatusName(estat));
for(ElementArray<Element>::iterator jt = adj.begin(); jt != adj.end(); jt++)
{
arr.push_back(jt->GlobalID()); //identificator of the cell
arr.push_back(jt->IntegerDF(tag_owner)); //owner of the cell
//REPORT_STR("id " << jt->GlobalID() << " owner " << jt->IntegerDF(tag_owner));
}
}
#if defined(USE_PARALLEL_WRITE_TIME)
++numfacesperproc[it->IntegerDF(tag_owner)];
#endif
}
REPORT_STR("number of ghosted or shared faces");
#if defined(USE_PARALLEL_WRITE_TIME)
for(std::map<int,int>::iterator it = numfacesperproc.begin(); it != numfacesperproc.end(); ++it)
{
REPORT_VAL("processor",it->first);
REPORT_VAL("skin faces",it->second);
}
#endif
REPORT_STR("exchanging cell's global identificators information")
REPORT_STR("reducing cell's global identificators information")
ReduceData(tag_skin,FACE,0,UnpackSkin);
REPORT_STR("exchanging cell's global identificators information")
#if defined(USE_PARALLEL_WRITE_TIME)
//for(iteratorFace it = BeginFace(); it != EndFace(); it++)
//{
// Element::Status estat1 = GetStatus(*it), estat2;
// if( estat1 == Element::Owned ) continue;
// Storage::integer_array skin_data = it->IntegerArray(tag_skin);
// REPORT_STR("face " << it->LocalID() << " global " << it->GlobalID() << " type " << Element::StatusName(estat1));
// for(Storage::integer_array::iterator kt = skin_data.begin(); kt != skin_data.end(); kt+=2)
// {
// REPORT_STR("id " << *kt << " owner " << *(kt+1));
// }
//}
#endif
ExchangeData(tag_skin,FACE,0);
REPORT_STR("exchanging cell's global identificators information")
REPORT_STR("synchornization done")
proc_elements skin_faces;
#if defined(USE_PARALLEL_WRITE_TIME)
std::map<int,int> numfacesperproc;
numfacesperproc.clear();
#endif
for(iteratorFace it = BeginFace(); it != EndFace(); it++)
{
bool flag = false;
Element::Status estat1 = GetStatus(*it), estat2;
if( estat1 == Element::Owned ) continue;
//Storage::integer_array skin_data = it->IntegerArray(tag_skin);
//REPORT_STR("face " << it->LocalID() << " global " << it->GlobalID() << " type " << Element::StatusName(estat1));
//for(Storage::integer_array::iterator kt = skin_data.begin(); kt != skin_data.end(); kt+=2)
//{
// REPORT_STR("id " << *kt << " owner " << *(kt+1));
//}
Cell c1 = it->BackCell();
Cell c2 = it->FrontCell();
if( !c1.isValid() && !c2.isValid() ) continue; //no cells per face - skip hanging face
......@@ -1856,6 +1937,7 @@ namespace INMOST
if( flag )
{
//printf("hello!\n");
for(int i = 0; i < 2; i++) //assert checks that there are two cells
{
Storage::integer owner = skin_data[i*2+1]; //cell owner
......@@ -1963,7 +2045,7 @@ namespace INMOST
for(element_set::iterator it = all_visited.begin(); it != all_visited.end(); it++)
{
Storage::integer_array os = IntegerArray(*it,on_skin);
for(Storage::integer_array::iterator p = os.begin(); p != os.end(); p++)
for(Storage::integer_array::iterator p = os.begin(); p != os.end(); p++)
{
if( *p != mpirank )
{
......@@ -2019,12 +2101,18 @@ namespace INMOST
for(eit = elements[i].begin(); eit != elements[i].end(); eit++)
if( (!select || GetMarker(*eit,select)) && HaveData(*eit,tag) )
{
//REPORT_STR("element type " << ElementTypeName(GetHandleElementType(*eit)) << " global id " << Integer(*eit,GlobalIDTag()));
array_size_send.push_back(static_cast<INMOST_DATA_ENUM_TYPE>(eit-elements[i].begin()));
array_size_send[count]++;
INMOST_DATA_ENUM_TYPE s = GetDataSize(*eit,tag);
INMOST_DATA_ENUM_TYPE had_s = static_cast<INMOST_DATA_ENUM_TYPE>(array_data_send.size());
array_data_send.resize(had_s+s*tag.GetBytesSize());
GetData(*eit,tag,0,s,&array_data_send[had_s]);
//REPORT_VAL("size",s);
//for(int qq = 0; qq < s; ++qq)
//{
// REPORT_VAL("value " << qq, (*(Storage::integer *)&array_data_send[had_s+qq*tag.GetBytesSize()]));
//}
if( size == ENUMUNDEF ) array_size_send.push_back(s);
++total_packed;
}
......@@ -2033,11 +2121,12 @@ namespace INMOST
{
for(eit = elements[i].begin(); eit != elements[i].end(); eit++) if( !select || GetMarker(*eit,select) )
{
// REPORT_STR("element type " << ElementTypeName(*eit) << " global id " << Integer(*eit,GlobalIDTag()));
INMOST_DATA_ENUM_TYPE s = GetDataSize(*eit,tag);
INMOST_DATA_ENUM_TYPE had_s = static_cast<INMOST_DATA_ENUM_TYPE>(array_data_send.size());
array_data_send.resize(had_s+s*tag.GetBytesSize());
GetData(*eit,tag,0,s,&array_data_send[had_s]);
if( size == ENUMUNDEF ) array_size_send.push_back(s);
if( size == ENUMUNDEF ) array_size_send.push_back(s);
++total_packed;
}
}
......@@ -2112,7 +2201,13 @@ namespace INMOST
for(unsigned j = 0; j < count; j++)
{