Commit a369387f authored by Thomas Witkowski's avatar Thomas Witkowski

Added support of reading and writing DOFVectors in arh files.

parent 0addc7a4
......@@ -51,32 +51,32 @@ build_old_libs=yes
pic_mode=default
# Whether or not to optimize for fast installation.
fast_install=needless
fast_install=yes
# The host system.
host_alias=
host=x86_64-unknown-linux-gnu
host=i686-redhat-linux-gnu
host_os=linux-gnu
# The build system.
build_alias=
build=x86_64-unknown-linux-gnu
build=i686-redhat-linux-gnu
build_os=linux-gnu
# A sed program that does not truncate output.
SED="/usr/bin/sed"
SED="/bin/sed"
# Sed that helps us avoid accidentally triggering echo(1) options like -n.
Xsed="$SED -e 1s/^X//"
# A grep program that handles long lines.
GREP="/usr/bin/grep"
GREP="/bin/grep"
# An ERE matcher.
EGREP="/usr/bin/grep -E"
EGREP="/bin/grep -E"
# A literal string matcher.
FGREP="/usr/bin/grep -F"
FGREP="/bin/grep -F"
# A BSD- or MS-compatible name lister.
NM="/usr/bin/nm -B"
......@@ -85,7 +85,7 @@ NM="/usr/bin/nm -B"
LN_S="ln -s"
# What is the maximum length of a command?
max_cmd_len=1572864
max_cmd_len=98304
# Object file suffix (normally "o").
objext=o
......@@ -128,7 +128,7 @@ old_postinstall_cmds="chmod 644 \$oldlib~\$RANLIB \$oldlib"
old_postuninstall_cmds=""
# A C compiler.
LTCC="/usr/lib64/mpi/gcc/openmpi//bin/mpicc"
LTCC="gcc"
# LTCC compiler flags.
LTCFLAGS="-g -O2"
......@@ -204,7 +204,7 @@ runpath_var=LD_RUN_PATH
shlibpath_var=LD_LIBRARY_PATH
# Is shlibpath searched before the hard-coded library search path?
shlibpath_overrides_runpath=yes
shlibpath_overrides_runpath=no
# Format of library name prefix.
libname_spec="lib\$name"
......@@ -233,10 +233,10 @@ finish_eval=""
hardcode_into_libs=yes
# Compile-time system search path for libraries.
sys_lib_search_path_spec="/usr/lib64/gcc/x86_64-suse-linux/4.5 /usr/lib64 /lib64 /usr/x86_64-suse-linux/lib"
sys_lib_search_path_spec="/u/witkowski/local/lib /u/witkowski/local/intel/mkl/10.0.1.014/lib/32 /usr/lib/gcc/i386-redhat-linux/4.1.2 /usr/lib /lib"
# Run-time system search path for libraries.
sys_lib_dlsearch_path_spec="/lib /usr/lib /usr/X11R6/lib64/Xaw3d /usr/X11R6/lib64 /usr/lib64/Xaw3d /usr/X11R6/lib/Xaw3d /usr/X11R6/lib /usr/lib/Xaw3d /usr/x86_64-suse-linux/lib /usr/local/lib /opt/kde3/lib /lib64 /lib /usr/lib64 /usr/lib /usr/local/lib64 /opt/kde3/lib64 /usr/lib64/graphviz /usr/lib64/graphviz/sharp /usr/lib64/graphviz/java /usr/lib64/graphviz/perl /usr/lib64/graphviz/php /usr/lib64/graphviz/ocaml /usr/lib64/graphviz/python /usr/lib64/graphviz/lua /usr/lib64/graphviz/tcl /usr/lib64/graphviz/guile /usr/lib64/graphviz/ruby /usr/lib64/octave-3.2.4 "
sys_lib_dlsearch_path_spec="/lib /usr/lib /usr/lib/mysql /usr/lib/octave-2.9.9 /usr/lib/qt-3.3/lib /usr/lib/qt4/lib /usr/lib/xulrunner-1.9.2 "
# Whether dlopen is supported.
dlopen_support=unknown
......@@ -253,13 +253,13 @@ striplib="strip --strip-unneeded"
# The linker used to build libraries.
LD="/usr/x86_64-suse-linux/bin/ld -m elf_x86_64"
LD="/usr/bin/ld"
# Commands used to build an old-style archive.
old_archive_cmds="\$AR \$AR_FLAGS \$oldlib\$oldobjs~\$RANLIB \$oldlib"
# A language specific compiler.
CC="/usr/lib64/mpi/gcc/openmpi//bin/mpicc"
CC="gcc"
# Is the compiler the GNU compiler?
with_gcc=yes
......@@ -274,7 +274,7 @@ wl="-Wl,"
pic_flag=" -fPIC -DPIC"
# Compiler flag to prevent dynamic linking.
link_static_flag=""
link_static_flag="-static"
# Does compiler simultaneously support -c and -o options?
compiler_c_o="yes"
......@@ -8908,13 +8908,13 @@ build_old_libs=`case $build_libtool_libs in yes) echo no;; *) echo yes;; esac`
# ### BEGIN LIBTOOL TAG CONFIG: CXX
# The linker used to build libraries.
LD="/usr/x86_64-suse-linux/bin/ld -m elf_x86_64"
LD="/usr/bin/ld"
# Commands used to build an old-style archive.
old_archive_cmds="\$AR \$AR_FLAGS \$oldlib\$oldobjs~\$RANLIB \$oldlib"
# A language specific compiler.
CC="/usr/lib64/mpi/gcc/openmpi//bin/mpicxx"
CC="g++"
# Is the compiler the GNU compiler?
with_gcc=yes
......@@ -8929,7 +8929,7 @@ wl="-Wl,"
pic_flag=" -fPIC -DPIC"
# Compiler flag to prevent dynamic linking.
link_static_flag=""
link_static_flag="-static"
# Does compiler simultaneously support -c and -o options?
compiler_c_o="yes"
......@@ -9039,17 +9039,17 @@ file_list_spec=""
hardcode_action=immediate
# The directories searched by this compiler when creating a shared library.
compiler_lib_search_dirs="/usr/lib64/mpi/gcc/openmpi/lib64 /usr/lib64/gcc/x86_64-suse-linux/4.5 /usr/lib64/gcc/x86_64-suse-linux/4.5/../../../../lib64 /lib/../lib64 /usr/lib/../lib64 /usr/lib64/gcc/x86_64-suse-linux/4.5/../../../../x86_64-suse-linux/lib /usr/lib64/gcc/x86_64-suse-linux/4.5/../../.."
compiler_lib_search_dirs="/u/witkowski/local/lib /u/witkowski/local/intel/mkl/10.0.1.014/lib/32 /usr/lib/gcc/i386-redhat-linux/4.1.2 /usr/lib/gcc/i386-redhat-linux/4.1.2 /usr/lib/gcc/i386-redhat-linux/4.1.2/../../.."
# Dependencies to place before and after the objects being linked to
# create a shared library.
predep_objects="/usr/lib64/gcc/x86_64-suse-linux/4.5/../../../../lib64/crti.o /usr/lib64/gcc/x86_64-suse-linux/4.5/crtbeginS.o"
postdep_objects="/usr/lib64/gcc/x86_64-suse-linux/4.5/crtendS.o /usr/lib64/gcc/x86_64-suse-linux/4.5/../../../../lib64/crtn.o"
predep_objects="/usr/lib/gcc/i386-redhat-linux/4.1.2/../../../crti.o /usr/lib/gcc/i386-redhat-linux/4.1.2/crtbeginS.o"
postdep_objects="/usr/lib/gcc/i386-redhat-linux/4.1.2/crtendS.o /usr/lib/gcc/i386-redhat-linux/4.1.2/../../../crtn.o"
predeps=""
postdeps="-lmpi_cxx -lmpi -lopen-rte -lopen-pal -ldl -lnsl -lutil -ldl -lstdc++ -lm -lgcc_s -lpthread -lc -lgcc_s"
postdeps="-lstdc++ -lm -lgcc_s -lc -lgcc_s"
# The library search path used internally by the compiler when linking
# a shared library.
compiler_lib_search_path="-L/usr/lib64/mpi/gcc/openmpi/lib64 -L/usr/lib64/gcc/x86_64-suse-linux/4.5 -L/usr/lib64/gcc/x86_64-suse-linux/4.5/../../../../lib64 -L/lib/../lib64 -L/usr/lib/../lib64 -L/usr/lib64/gcc/x86_64-suse-linux/4.5/../../../../x86_64-suse-linux/lib -L/usr/lib64/gcc/x86_64-suse-linux/4.5/../../.."
compiler_lib_search_path="-L/u/witkowski/local/lib -L/u/witkowski/local/intel/mkl/10.0.1.014/lib/32 -L/usr/lib/gcc/i386-redhat-linux/4.1.2 -L/usr/lib/gcc/i386-redhat-linux/4.1.2 -L/usr/lib/gcc/i386-redhat-linux/4.1.2/../../.."
# ### END LIBTOOL TAG CONFIG: CXX
......@@ -3,16 +3,36 @@
#include "ArhReader.h"
#include "Mesh.h"
#include "MeshStructure.h"
#include "Traverse.h"
#include "DOFVector.h"
namespace AMDiS {
using namespace std;
void ArhReader::read(string filename, Mesh *mesh, bool ignoreFinerMesh)
void ArhReader::read(std::string filename, Mesh *mesh)
{
std::vector<DOFVector<double>*> vecs(0);
ArhReader::read(filename, mesh, vecs);
}
void ArhReader::read(std::string filename, Mesh *mesh, DOFVector<double>* vec)
{
std::vector<DOFVector<double>*> vecs(1);
vecs[0] = vec;
ArhReader::read(filename, mesh, vecs);
}
void ArhReader::read(string filename, Mesh *mesh,
std::vector<DOFVector<double>*> vecs)
{
FUNCNAME("ArhReader::read()");
RefinementManager *refManager;
RefinementManager *refManager = NULL;
switch (mesh->getDim()) {
case 2:
refManager = new RefinementManager2d();
......@@ -37,6 +57,10 @@ namespace AMDiS {
file.read(reinterpret_cast<char*>(&nValueVectors), 4);
file.read(reinterpret_cast<char*>(&nAllValues), 4);
TEST_EXIT(nValueVectors == vecs.size())
("File has %d vectors, but %d DOFVectors are provided!\n",
nValueVectors, vecs.size());
for (unsigned int i = 0; i < nMacroElements; i++) {
uint32_t elIndex = 0;
uint32_t nStructureCodes = 0;
......@@ -46,20 +70,20 @@ namespace AMDiS {
file.read(reinterpret_cast<char*>(&nStructureCodes), 4);
file.read(reinterpret_cast<char*>(&codeSize), 4);
vector<unsigned long int> structureCode(nStructureCodes);
vector<uint64_t> structureCode(nStructureCodes);
file.read(reinterpret_cast<char*>(&(structureCode[0])), 8 * nStructureCodes);
MeshStructure elementStructure;
elementStructure.init(structureCode, codeSize);
elementStructure.fitMeshToStructure(mesh, refManager,
false, elIndex, ignoreFinerMesh);
elementStructure.fitMeshToStructure(mesh, refManager, false, elIndex);
uint32_t nValuesPerVector = 0;
file.read(reinterpret_cast<char*>(&nValuesPerVector), 4);
for (unsigned int j = 0; j < nValuesPerVector * nValueVectors; j++) {
double value = 0.0;
file.read(reinterpret_cast<char*>(&value), 8);
for (unsigned int j = 0; j < nValueVectors; j++) {
vector<double> values(nValuesPerVector);
file.read(reinterpret_cast<char*>(&(values[0])), 8 * nValuesPerVector);
setDofValues(elIndex, mesh, values, vecs[j]);
}
}
......@@ -67,4 +91,31 @@ namespace AMDiS {
MSG("ARH file read from: %s\n", filename.c_str());
}
void ArhReader::setDofValues(int macroElIndex, Mesh *mesh,
std::vector<double>& values, DOFVector<double>* vec)
{
FUNCNAME("ArhReader::setDofValues()");
bool macroElement = false;
int valuePos = 0;
TraverseStack stack;
ElInfo *elInfo = stack.traverseFirstOneMacro(mesh, macroElIndex, -1,
Mesh::CALL_EVERY_EL_PREORDER);
while (elInfo) {
if (!macroElement) {
Element *mEl = elInfo->getMacroElement()->getElement();
for (int i = 0; i <= mesh->getDim(); i++)
(*vec)[mEl->getDOF(i, 0)] = values[valuePos++];
macroElement = true;
}
Element *el = elInfo->getElement();
if (!el->isLeaf())
(*vec)[el->getChild(0)->getDOF(mesh->getDim(), 0)] = values[valuePos++];
elInfo = stack.traverseNext(elInfo);
}
}
}
......@@ -29,8 +29,16 @@ namespace AMDiS {
class ArhReader
{
public:
static void read(std::string filename, Mesh *mesh,
bool ignoreFinerMesh = true);
static void read(std::string filename, Mesh *mesh);
static void read(std::string filename, Mesh *mesh, DOFVector<double>* vec);
static void read(std::string filename, Mesh *mesh,
std::vector<DOFVector<double>*> vecs);
private:
static void setDofValues(int macroElIndex, Mesh *mesh,
std::vector<double>& values, DOFVector<double>* vec);
};
}
......
......@@ -4,19 +4,38 @@
#include "Mesh.h"
#include "MeshStructure.h"
#include "Traverse.h"
#include "DOFVector.h"
namespace AMDiS {
using namespace std;
void ArhWriter::write(string filename, Mesh *mesh)
{
std::vector<DOFVector<double>*> vecs(0);
ArhWriter::write(filename, mesh, vecs);
}
void ArhWriter::write(std::string filename, Mesh *mesh, DOFVector<double>* vec)
{
std::vector<DOFVector<double>*> vecs(1);
vecs[0] = vec;
ArhWriter::write(filename, mesh, vecs);
}
void ArhWriter::write(std::string filename, Mesh *mesh,
std::vector<DOFVector<double>*> vecs)
{
FUNCNAME("ArhWriter::write()");
ofstream file;
file.open(filename.c_str(), ios::out | ios::binary | ios::trunc);
string typeId = "arhS";
string typeId = "arhP";
file.write(typeId.c_str(), 4);
uint32_t nMacroElements = 0;
......@@ -29,13 +48,15 @@ namespace AMDiS {
file.write(reinterpret_cast<char*>(&nMacroElements), 4);
uint32_t nValueVectors = 0;
uint32_t nValueVectors = vecs.size();
file.write(reinterpret_cast<char*>(&nValueVectors), 4);
uint32_t nAllValues = 0;
uint32_t nAllValues =
(vecs.size() > 0 ? vecs[0]->getFeSpace()->getAdmin()->getUsedDOFs() : 0);
file.write(reinterpret_cast<char*>(&nAllValues), 4);
MeshStructure elementStructure;
std::vector<std::vector<double> > values(vecs.size());
int32_t macroElIndex = -1;
elInfo = stack.traverseFirst(mesh, -1, Mesh::CALL_EVERY_EL_PREORDER);
......@@ -43,21 +64,33 @@ namespace AMDiS {
if (elInfo->getLevel() == 0) {
if (macroElIndex != -1) {
elementStructure.commit();
writeMacroElement(file, elementStructure, macroElIndex);
writeMacroElement(file, elementStructure, values, macroElIndex);
}
elementStructure.clear();
macroElIndex = elInfo->getElement()->getIndex();
for (unsigned int i = 0; i < vecs.size(); i++) {
values[i].clear();
for (int j = 0; j <= mesh->getDim(); j++)
values[i].push_back((*vecs[i])[elInfo->getElement()->getDOF(j, 0)]);
}
}
elementStructure.insertElement(elInfo->getElement()->isLeaf());
if (!elInfo->getElement()->isLeaf()) {
for (unsigned int i = 0; i < vecs.size(); i++)
values[i].push_back((*vecs[i])[elInfo->getElement()->getChild(0)->getDOF(mesh->getDim(), 0)]);
}
elInfo = stack.traverseNext(elInfo);
}
// And write the last macro element to file.
TEST_EXIT_DBG(macroElIndex != -1)("Should not happen!\n");
elementStructure.commit();
writeMacroElement(file, elementStructure, macroElIndex);
writeMacroElement(file, elementStructure, values, macroElIndex);
file.close();
......@@ -66,7 +99,8 @@ namespace AMDiS {
void ArhWriter::writeMacroElement(std::ofstream &file,
MeshStructure &code,
MeshStructure &code,
std::vector<std::vector<double> >& values,
int32_t elIndex)
{
file.write(reinterpret_cast<char*>(&elIndex), 4);
......@@ -77,11 +111,14 @@ namespace AMDiS {
uint32_t codeSize = code.getNumElements();
file.write(reinterpret_cast<char*>(&codeSize), 4);
file.write(reinterpret_cast<char*>(&(const_cast<vector<unsigned long int>&>(code.getCode())[0])),
file.write(reinterpret_cast<char*>(&(const_cast<vector<uint64_t>&>(code.getCode())[0])),
8 * nStructureCodes);
uint32_t nValuesPerVector = 0;
uint32_t nValuesPerVector = (values.size() > 0 ? values[0].size() : 0);
file.write(reinterpret_cast<char*>(&nValuesPerVector), 4);
for (unsigned int i = 0; i < values.size(); i++)
file.write(reinterpret_cast<char*>(&(values[i][0])), 8 * nValuesPerVector);
}
}
......@@ -34,9 +34,15 @@ namespace AMDiS {
public:
static void write(std::string filename, Mesh *mesh);
static void write(std::string filename, Mesh *mesh, DOFVector<double>* vec);
static void write(std::string filename, Mesh *mesh,
std::vector<DOFVector<double>*> vecs);
protected:
static void writeMacroElement(std::ofstream &file,
MeshStructure &code,
std::vector<std::vector<double> >& values,
int32_t elIndex);
};
}
......
......@@ -9,13 +9,13 @@
namespace AMDiS {
const int MeshStructure::unsignedLongSize = sizeof(unsigned long int) * 8;
const int MeshStructure::structureSize = 64;
void MeshStructure::insertElement(bool isLeaf)
{
// overflow? -> next index
if (pos >= unsignedLongSize) {
if (pos >= structureSize) {
code.push_back(currentCode);
pos = 0;
currentCode = 0;
......@@ -23,7 +23,7 @@ namespace AMDiS {
// insert element in binary code
if (!isLeaf) {
unsigned long int one = 1;
uint64_t one = 1;
currentCode += (one << pos);
}
......@@ -160,7 +160,7 @@ namespace AMDiS {
if (currentElement >= nElements)
return false;
if (pos >= unsignedLongSize) {
if (pos >= structureSize) {
currentIndex++;
TEST_EXIT_DBG(currentIndex < static_cast<int>(code.size()))
("End of structure reached!\n");
......
......@@ -48,7 +48,7 @@ namespace AMDiS {
void init(BoundaryObject &bound);
void init(const std::vector<unsigned long int>& initCode, int n)
void init(const std::vector<uint64_t>& initCode, int n)
{
code = initCode;
nElements = n;
......@@ -117,7 +117,7 @@ namespace AMDiS {
void print(bool resetCode = true);
/// Returns the mesh structure code.
inline const std::vector<unsigned long int>& getCode()
inline const std::vector<uint64_t>& getCode()
{
return code;
}
......@@ -153,11 +153,11 @@ namespace AMDiS {
protected:
/// Mesh structure code.
std::vector<unsigned long int> code;
std::vector<uint64_t> code;
int currentIndex;
unsigned long int currentCode;
uint64_t currentCode;
int pos;
......@@ -168,7 +168,7 @@ namespace AMDiS {
/// If true, some output is printed to screen during mesh structure code generation.
bool debugMode;
static const int unsignedLongSize;
static const int structureSize;
friend class ArhWriter;
};
......
......@@ -48,6 +48,20 @@ namespace AMDiS {
}
ElInfo* TraverseStack::traverseFirstOneMacro(Mesh *mesh, int macroIndex, int level,
Flag fill_flag)
{
FUNCNAME("TraverseStack::traverseFirstOneMacro()");
TEST_EXIT_DBG(macroIndex >= 0)("Invalid macro element index!\n");
TEST_EXIT_DBG(traverse_fill_flag.isSet(Mesh::CALL_MG_LEVEL) == false)
("Multigrid level traverse not supported for one macro element only!\n");
limitedToMacroElement = macroIndex;
return TraverseStack::traverseFirst(mesh, level, fill_flag);
}
ElInfo* TraverseStack::traverseNext(ElInfo* elinfo_old)
{
FUNCNAME("TraverseStack::traverseNext()");
......@@ -135,9 +149,19 @@ namespace AMDiS {
if (stack_used == 0) { /* first call */
currentMacro = traverse_mesh->firstMacroElement();
while (((*currentMacro)->getIndex() % maxThreads != myThreadId) &&
currentMacro != traverse_mesh->endOfMacroElements())
currentMacro++;
if (limitedToMacroElement >= 0) {
while ((*currentMacro)->getIndex() != limitedToMacroElement &&
currentMacro != traverse_mesh->endOfMacroElements())
currentMacro++;
TEST_EXIT_DBG(currentMacro != traverse_mesh->endOfMacroElements())
("Coult not find macro element with index %d!\n", limitedToMacroElement);
} else {
while (((*currentMacro)->getIndex() % maxThreads != myThreadId) &&
currentMacro != traverse_mesh->endOfMacroElements())
currentMacro++;
}
if (currentMacro == traverse_mesh->endOfMacroElements())
return NULL;
......@@ -162,6 +186,9 @@ namespace AMDiS {
/* goto next macro element */
if (stack_used < 1) {
if (limitedToMacroElement >= 0)
return NULL;
do {
currentMacro++;
} while ((currentMacro != traverse_mesh->endOfMacroElements()) &&
......@@ -193,7 +220,7 @@ namespace AMDiS {
stack_used++;
TEST_EXIT_DBG(stack_used < stack_size)
("stack_size=%d too small, level=(%d,%d)\n",
("stack_size = %d too small, level = (%d, %d)\n",
stack_size, elinfo_stack[stack_used]->getLevel());
info_stack[stack_used] = 0;
......@@ -306,6 +333,16 @@ namespace AMDiS {
if (stack_used == 0) { /* first call */
currentMacro = traverse_mesh->firstMacroElement();
if (limitedToMacroElement >= 0) {
while ((*currentMacro)->getIndex() != limitedToMacroElement &&
currentMacro != traverse_mesh->endOfMacroElements())
currentMacro++;
TEST_EXIT_DBG(currentMacro != traverse_mesh->endOfMacroElements())
("Coult not find macro element with index %d!\n", limitedToMacroElement);
}
traverse_mel = *currentMacro;
if (traverse_mel == NULL)
return NULL;
......@@ -329,6 +366,9 @@ namespace AMDiS {
/* goto next macro element */
if (stack_used < 1) {
if (limitedToMacroElement >= 0)
return NULL;
currentMacro++;
if (currentMacro == traverse_mesh->endOfMacroElements())
return NULL;
......@@ -381,6 +421,15 @@ namespace AMDiS {
if (stack_used == 0) { /* first call */
currentMacro = traverse_mesh->firstMacroElement();
if (limitedToMacroElement >= 0) {
while ((*currentMacro)->getIndex() != limitedToMacroElement &&
currentMacro != traverse_mesh->endOfMacroElements())
currentMacro++;
TEST_EXIT_DBG(currentMacro != traverse_mesh->endOfMacroElements())
("Coult not find macro element with index %d!\n", limitedToMacroElement);
}
if (currentMacro == traverse_mesh->endOfMacroElements())
return NULL;
traverse_mel = *currentMacro;
......@@ -403,6 +452,9 @@ namespace AMDiS {
/* goto next macro element */
if (stack_used < 1) {
if (limitedToMacroElement >= 0)
return NULL;
currentMacro++;
if (currentMacro == traverse_mesh->endOfMacroElements())
return NULL;
......
......@@ -57,7 +57,8 @@ namespace AMDiS {
public:
/// Creates an empty TraverseStack
TraverseStack()
: traverse_mel(NULL),
: limitedToMacroElement(-1),
traverse_mel(NULL),
stack_size(0),
stack_used(0),
save_stack_used(0),
......@@ -84,6 +85,13 @@ namespace AMDiS {
*/
ElInfo* traverseFirst(Mesh *mesh, int level, Flag fill_flag);
/** \brief
* Works in the same way as \ref traverseFirst defined above, but limits the
* traversal to one macro mesh only.
*/
ElInfo* traverseFirstOneMacro(Mesh *mesh, int macroIndex, int level,
Flag fill_flag);
/** \brief
* Returns the next ElInfo in a traversal initiated by \ref traverseFirst()
* If NULL is returned, the traversal is finished.
......@@ -206,6 +214,10 @@ namespace AMDiS {
* information are filled to the ElInfo objects.
*/
Flag traverse_fill_flag;
/// If -1, the whole mesh is traversed. Otherwise, only the macro element
/// with the given element index is traversed.
int limitedToMacroElement;
/// current macro element
const MacroElement *traverse_mel;
......
Markdown is supported
0% or .
You are about to add 0 people to the discussion. Proceed with caution.
Finish editing this message first!
Please register or to comment