summaryrefslogtreecommitdiffstats
path: root/server
diff options
context:
space:
mode:
authorConstantin Jucovschi <cj@ubuntu.localdomain>2009-04-24 07:20:22 -0400
committerConstantin Jucovschi <cj@ubuntu.localdomain>2009-04-24 07:20:22 -0400
commit8f27e65bddd7d4b8515ce620fb485fdd78fcdf89 (patch)
treebd328a4dd4f92d32202241b5e3a7f36177792c5f /server
downloadrasdaman-upstream-8f27e65bddd7d4b8515ce620fb485fdd78fcdf89.tar.gz
rasdaman-upstream-8f27e65bddd7d4b8515ce620fb485fdd78fcdf89.tar.xz
rasdaman-upstream-8f27e65bddd7d4b8515ce620fb485fdd78fcdf89.zip
Initial commitv8.0
Diffstat (limited to 'server')
-rw-r--r--server/Makefile.am58
-rw-r--r--server/createinitmdd.cc397
-rw-r--r--server/createinitmdd.hh105
-rw-r--r--server/rasserver_config.cc297
-rw-r--r--server/rasserver_config.hh138
-rw-r--r--server/rasserver_entry.cc528
-rw-r--r--server/rasserver_entry.hh140
-rw-r--r--server/rasserver_main.cc360
-rw-r--r--server/template_inst.hh132
-rw-r--r--server/test/Makefile59
-rw-r--r--server/test/test_mult-db-open.cc165
11 files changed, 2379 insertions, 0 deletions
diff --git a/server/Makefile.am b/server/Makefile.am
new file mode 100644
index 0000000..5a36db5
--- /dev/null
+++ b/server/Makefile.am
@@ -0,0 +1,58 @@
+# -*-Makefile-*-
+#
+# This file is part of rasdaman community.
+#
+# Rasdaman community is free software: you can redistribute it and/or modify
+# it under the terms of the GNU General Public License as published by
+# the Free Software Foundation, either version 3 of the License, or
+# (at your option) any later version.
+#
+# Rasdaman community is distributed in the hope that it will be useful,
+# but WITHOUT ANY WARRANTY; without even the implied warranty of
+# MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
+# GNU General Public License for more details.
+#
+# You should have received a copy of the GNU General Public License
+# along with rasdaman community. If not, see <http://www.gnu.org/licenses/>.
+#
+# Copyright 2003, 2004, 2005, 2006, 2007, 2008, 2009 Peter Baumann /
+# rasdaman GmbH.
+#
+# For more information please see <http://www.rasdaman.org>
+# or contact Peter Baumann via <baumann@rasdaman.com>.
+#
+# MAKEFILE FOR:
+# rasdaman server binaries, raslic
+#
+# COMMENTS:
+# - For static link you have to do: setenv STATIC_LIBS=TRUE
+#
+##################################################################
+
+AM_CXXFLAGS=@BASEDBCXXFLAGS@
+AM_LDFLAGS=@BASEDBLDFLAGS@
+
+bin_PROGRAMS=rasserver
+rasserver_SOURCES=rasserver_main.cc rasserver_config.cc rasserver_entry.cc \
+ createinitmdd.cc rasserver_config.hh rasserver_entry.hh \
+ createinitmdd.hh template_inst.hh\
+ ../debug/debug-clt.hh ../debug/debug.hh ../debug/debug-srv.hh \
+ ../include/bool.h ../include/globals.hh ../include/rasdaman.hh \
+ ../include/stdexcept.h
+rasserver_LDADD=../rnprotocol/libservercomm.a ../servercomm/libservercomm.a ../qlparser/libqlparser.a ../conversion/libconversion.a \
+ ../raslib/libraslib.a ../storagemgr/libstoragemgr.a ../reladminif/libreladminif.a \
+ ../tilemgr/libtilemgr.a ../mddmgr/libmddmgr.a \
+ ../catalogmgr/libcatalogmgr.a ../relmddif/librelmddif.a ../relstorageif/librelstorageif.a \
+ ../relcatalogif/librelcatalogif.a ../indexmgr/libindexmgr.a ../relblobif/librelblobif.a \
+ ../relindexif/librelindexif.a ../httpserver/libhttpserver.a \
+ ../network/libnetwork.a ../commline/libcommline.a \
+ ../time/libtime.a ../compression/libcompression.a \
+ ../relcatalogif/librelcatalogif.a ../raslib/libraslib.a
+
+SUBDIRS = ../relblobif ../relindexif ../relmddif ../relcatalogif ../reladminif ../relstorageif \
+ ../indexmgr ../catalogmgr ../tilemgr ../storagemgr ../commline ../network \
+ ../raslib ../servercomm ../rnprotocol ../rasodmg ../qlparser ../conversion \
+ ../mddmgr ../httpserver ../mymalloc ../time
+
+$(RECURSIVE_CLEAN_TARGETS):
+ @$(MAKE) $(AM_MAKEFLAGS) `echo $@ | sed s/-recursive/-am/`
diff --git a/server/createinitmdd.cc b/server/createinitmdd.cc
new file mode 100644
index 0000000..13098af
--- /dev/null
+++ b/server/createinitmdd.cc
@@ -0,0 +1,397 @@
+#include "mymalloc/mymalloc.h"
+/*
+* This file is part of rasdaman community.
+*
+* Rasdaman community is free software: you can redistribute it and/or modify
+* it under the terms of the GNU General Public License as published by
+* the Free Software Foundation, either version 3 of the License, or
+* (at your option) any later version.
+*
+* Rasdaman community is distributed in the hope that it will be useful,
+* but WITHOUT ANY WARRANTY; without even the implied warranty of
+* MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
+* GNU General Public License for more details.
+*
+* You should have received a copy of the GNU General Public License
+* along with rasdaman community. If not, see <http://www.gnu.org/licenses/>.
+*
+* Copyright 2003, 2004, 2005, 2006, 2007, 2008, 2009 Peter Baumann /
+rasdaman GmbH.
+*
+* For more information please see <http://www.rasdaman.org>
+* or contact Peter Baumann via <baumann@rasdaman.com>.
+*/
+/*************************************************************
+ *
+ *
+ * PURPOSE:
+ *
+ *
+ * COMMENTS:
+ *
+ ************************************************************/
+
+using namespace std;
+
+#include "server/createinitmdd.hh"
+#include <iomanip>
+#include "reladminif/objectbroker.hh"
+#include "raslib/mitera.hh"
+
+// #undef DEBUG_HH
+// #include "debug.hh"
+#define ENTER(a) cout << "ENTER " << a << endl << flush;
+#define LEAVE(a) cout << "LEAVE " << a << endl << flush;
+
+//#include <akgtime.hh>
+
+
+
+FastCollectionCreator::FastCollectionCreator(const char *collName, const char *collTypeName)
+ {
+ ENTER( "FastCollectionCreator::FastCollectionCreator(" << collName << "," << collTypeName << ")" );
+ collectionName = collName;
+
+ collectionTypeName = collTypeName;
+ LEAVE( "FastCollectionCreator::FastCollectionCreator()" );
+ }
+
+r_OId FastCollectionCreator::createCollection()
+ {
+ ENTER( "FastCollectionCreator::createCollection()" );
+
+ verifyName(collectionName);
+
+ // allocate a new OId
+ EOId eOId; EOId::allocateEOId( eOId, OId::MDDCOLLOID );
+ r_OId oid = r_OId( eOId.getSystemName(), eOId.getBaseName(), eOId.getOId() );
+
+ CollectionType* collType = (CollectionType*)TypeFactory::mapSetType( collectionTypeName );
+
+ RMInit::logOut<<"Creating collection "<<collectionName<<" with type "<<collectionTypeName<<"...";
+ if( collType )
+ {
+ try
+ {
+ MDDColl* coll = MDDColl::createMDDCollection(collectionName, OId(oid.get_local_oid()), collType);
+ delete coll;
+ RMInit::logOut << "OK" << std::endl;
+ }
+ catch( r_Error& obj )
+ {
+ if (obj.get_kind() == r_Error::r_Error_NameNotUnique)
+ {
+ RMInit::logOut << "collection name exists already... FAILED" << std::endl;
+ }
+ else
+ {
+ RMInit::logOut << obj.get_errorno() << " " << obj.what() << std::endl;
+ }
+ throw;
+ }
+ }
+ else
+ {
+ RMInit::logOut << "collection type not found... FAILED" << std::endl;
+ throw r_Error(COLLTYPE_NULL);
+ }
+
+ ENTER( "FastCollectionCreator::createCollection()" );
+ return oid;
+ }
+
+void FastCollectionCreator::verifyName( const char* name ) throw(r_Error)
+ {
+ ENTER( "FastCollectionCreator::verifyName(" << (long) name << ")" );
+
+ if(!name)
+ {
+ RMInit::logOut << "FastCollectionCreator::verifyName() name is null!" << std::endl;
+ throw r_Error(INVALIDOBJECTNAME);
+ }
+
+ const char* cptr=name;
+
+ //check if the name contains only [a-zA-Z0-9_]
+ while(*cptr) {
+ if( ((*cptr >= 'a') && (*cptr <='z')) ||
+ ((*cptr >= 'A') && (*cptr <='Z')) ||
+ ((*cptr >= '0') && (*cptr <='9')) ||
+ (*cptr == '_') )
+ cptr++;
+ else
+ break;
+ }
+
+ if(*cptr) {
+ //invalid character in object name
+ RMInit::logOut << "FastCollectionCreator::verifyName(" << name << ") invalid name!" << std::endl;
+ throw r_Error(INVALIDOBJECTNAME);
+ }
+
+ LEAVE( "FastCollectionCreator::verifyName(" << name << ") -> ok" );
+ }
+
+
+//###################################################################################################
+
+FastMDDCreator::FastMDDCreator()
+ {
+ ENTER( "FastMDDCreator::FastMDDCreator()" );
+
+ comprData = 0;
+
+ storageFormat = r_TMC;
+ formatParams = NULL;
+
+ LEAVE( "FastMDDCreator::FastMDDCreator()" );
+ }
+
+FastMDDCreator::~FastMDDCreator()
+ {
+ ENTER( "FastMDDCreator::~FastMDDCreator()" );
+
+ if(comprData) free(comprData);
+
+ LEAVE( "FastMDDCreator::~FastMDDCreator()" );
+ }
+
+void FastMDDCreator::setCollectionName(const char* collName)
+ {
+ ENTER( "FastMDDCreator::setCollectionName(" << collName << ")" );
+
+ collectionName = collName;
+
+ LEAVE( "FastMDDCreator::setCollectionName()" );
+ }
+
+void FastMDDCreator::setMDDTypeName(const char* _mddTypeName)
+ {
+ ENTER( "FastMDDCreator::setMDDTypeName(" << _mddTypeName << ")" );
+
+ mddTypeName = _mddTypeName;
+
+ LEAVE( "FastMDDCreator::setMDDTypeName()" );
+ }
+
+void FastMDDCreator::verifyCompatibility(MDDColl* collection) throw (r_Error)
+ {
+ ENTER( "FastMDDCreator::verifyCompatibility(_)" );
+
+ if (collection->isPersistent())
+ {
+ //cout<<"OK, colection exists and is persistent"<<endl;
+ }
+ else
+ {
+ throw r_Error(SYSTEM_COLLECTION_NOT_WRITABLE);
+ }
+
+ char* collTypeStructure = collection->getCollectionType()->getTypeStructure();
+ //cout<<"collTypeStructure="<<collTypeStructure<<endl;
+
+ const MDDType* mddType = TypeFactory::mapMDDType( mddTypeName.c_str() );
+ if(mddType == NULL) throw r_Error(MDDTYPE_NULL);
+
+ char* mddTypeStructure = mddType->getTypeStructure();
+ //cout<<"mddTypeStructure="<<mddTypeStructure<<endl;
+
+
+ if(mddType->compatibleWithDomain( &definitionInterval ))
+ {
+ //cout<<"compatibil with domain: "<<definitionInterval<<endl;
+ }
+ else throw r_Error(r_Error::r_Error_CollectionElementTypeMismatch);
+ //cout<<"incompatibil with domain"<<endl;
+
+ if(collection->getCollectionType()->compatibleWith( mddType ))
+ {
+ //cout<<"compatibil with collection"<<endl;
+ }
+ else
+ throw r_Error(r_Error::r_Error_CollectionElementTypeMismatch);
+ //cout<<"incompatibil with collection"<<endl;
+
+ free( collTypeStructure );
+ free( mddTypeStructure );
+
+ LEAVE( "FastMDDCreator::verifyCompatibility()" );
+ }
+
+r_OId FastMDDCreator::createMDD(const char *domain)
+ {
+ ENTER( "FastMDDCreator::createMDD(" << domain << ")" );
+
+ definitionInterval = r_Minterval(domain);
+
+ MDDColl* collection = MDDColl::getMDDCollection( collectionName.c_str() );
+
+ verifyCompatibility(collection);
+
+ const MDDType* mddType = TypeFactory::mapMDDType( mddTypeName.c_str() );
+ MDDBaseType* mddBaseType = (MDDBaseType*)mddType;
+
+ //allocate oid-ul;
+ EOId eOId; EOId::allocateEOId( eOId, OId::MDDOID );
+
+ mddOId = r_OId( eOId.getSystemName(), eOId.getBaseName(), eOId.getOId() );
+
+ StorageLayout ms;
+ ms.setTileSize(StorageLayout::DefaultTileSize);
+ ms.setIndexType(StorageLayout::DefaultIndexType);
+ ms.setTilingScheme(StorageLayout::DefaultTilingScheme);
+ if (definitionInterval.dimension() == StorageLayout::DefaultTileConfiguration.dimension())
+ ms.setTileConfiguration(StorageLayout::DefaultTileConfiguration);
+
+ mymdd = new MDDObj(mddBaseType, definitionInterval, eOId.getOId(), ms);
+
+ cellSize = mymdd->getCellType()->getSize();
+
+ collection->insert( mymdd );
+
+ collection->releaseAll();
+
+ delete collection;
+
+ LEAVE( "FastMDDCreator::createMDD() -> " << mddOId );
+ return mddOId;
+ }
+
+r_OId FastMDDCreator::createRCxMDD(const char *domain, const char *tileDomain)
+ {
+ ENTER( "FastMDDCreator::createRCxMDD(" << domain << "," << tileDomain << ")" );
+
+ definitionInterval = r_Minterval(domain);
+ r_Minterval tileInterval = r_Minterval(tileDomain);
+
+ MDDColl* collection = MDDColl::getMDDCollection( collectionName.c_str() );
+
+ verifyCompatibility(collection);
+
+ const MDDType* mddType = TypeFactory::mapMDDType( mddTypeName.c_str() );
+ MDDBaseType* mddBaseType = (MDDBaseType*)mddType;
+
+ //allocate oid-ul;
+ EOId eOId; EOId::allocateEOId( eOId, OId::MDDOID );
+
+ mddOId = r_OId( eOId.getSystemName(), eOId.getBaseName(), eOId.getOId() );
+
+ StorageLayout ms;
+ ms.setTileSize(tileInterval.cell_count() * mddBaseType->getBaseType()->getSize());
+ ms.setDataFormat(r_ZLib);
+ ms.setIndexType(r_Reg_Computed_Index);
+ ms.setTilingScheme(r_RegularTiling);
+ ms.setTileConfiguration(tileInterval);
+ mymdd = new MDDObj(mddBaseType, definitionInterval, eOId.getOId(), ms);
+
+
+ cellSize = mymdd->getCellType()->getSize();
+
+ collection->insert( mymdd );
+
+ collection->releaseAll();
+
+ delete collection;
+
+ LEAVE( "FastMDDCreator::createRCxMDD() -> " << mddOId );
+ return mddOId;
+ }
+
+vector<r_Minterval> FastMDDCreator::getTileDomains(r_OId mddOId, const char *stripeDomain)
+ {
+ ENTER( "FastMDDCreator::getTileDomains(" << mddOId << "," << stripeDomain << ")" );
+
+ mymdd = new MDDObj( OId(mddOId.get_local_oid()) );
+
+ r_Minterval stripeInterval(stripeDomain);
+
+ vector< Tile* >* tiles = mymdd->intersect(stripeInterval);
+
+ vector<r_Minterval> result;
+
+ for(int i=0; i < tiles->size(); i++)
+ {
+ result.push_back( (*tiles)[i]->getDomain());
+ }
+ delete mymdd;
+
+ LEAVE( "FastMDDCreator::getTileDomains()" );
+ return result;
+ }
+
+void FastMDDCreator::addStripe(r_OId _mddOId, const char *stripeDomain, const char *tileDomain)
+ {
+ ENTER( "FastMDDCreator::addStripe(" << _mddOId << "," << stripeDomain << "," << tileDomain << ")" );
+
+ mddOId = _mddOId;
+
+ r_Minterval stripeInterval(stripeDomain);
+ r_Minterval tileInterval(tileDomain);
+
+
+ mymdd = new MDDObj( OId(mddOId.get_local_oid()) );
+ cellSize = mymdd->getCellType()->getSize();
+ const BaseType* baseType = mymdd->getMDDBaseType()->getBaseType();
+
+
+ r_MiterArea iter(&tileInterval, &stripeInterval);
+
+ while (!iter.isDone())
+ {//iterate through the partitions in the search domain
+ r_Minterval currentSlInterval = iter.nextArea();
+ //cout<<"inserting tile: "<< currentSlInterval<<endl;
+
+ createCompressedTileData(currentSlInterval, baseType);
+
+ Tile* tile = new Tile( currentSlInterval, baseType, comprData, true, comprDataSize, storageFormat);
+ tile->setParameters(formatParams);
+ tile->setPersistent(true);
+
+ mymdd->insertTile( tile );
+ }
+
+ delete mymdd;
+
+ LEAVE( "FastMDDCreator::addStripe()" );
+ }
+
+
+void FastMDDCreator::createCompressedTileData(r_Minterval& tileInterval, const BaseType* baseType)
+ {
+ ENTER( "FastMDDCreator::createCompressedTileData(" << tileInterval << "," << baseType << ")" );
+
+ static int lastSize = 0;
+ int uncompressedSize = tileInterval.cell_count() * cellSize;
+
+ if(comprData)
+ {
+ if(lastSize == uncompressedSize)
+ {
+ return;
+ }
+ else { free(comprData); comprData = 0; }
+ }
+
+
+ r_Data_Format comprMode = storageFormat; ;
+
+ char* dataPtr = (char*)mymalloc(uncompressedSize); memset(dataPtr,0,uncompressedSize);
+
+ r_Base_Type *compType = (r_Base_Type*)(r_Type::get_any_type(baseType->getTypeStructure()));
+
+ r_Tile_Compression *engine = r_Tile_Compression::create(comprMode, tileInterval, compType);
+
+ r_ULong newSize = uncompressedSize;
+ comprData = (char*)(engine->compress(dataPtr, newSize, formatParams));
+ comprDataSize = newSize;
+ delete engine;
+ //cout<<"Compression of "<<uncompressedSize<<" of zeroes resulted in "<<comprDataSize<<" bytes"<<endl;
+
+ free(dataPtr);
+ delete compType;
+
+ lastSize= uncompressedSize;
+
+ LEAVE( "FastMDDCreator::createCompressedTileData()" );
+ }
+
diff --git a/server/createinitmdd.hh b/server/createinitmdd.hh
new file mode 100644
index 0000000..5165c6f
--- /dev/null
+++ b/server/createinitmdd.hh
@@ -0,0 +1,105 @@
+#ifndef CREATE_INIT_MDD_HH
+#define CREATE_INIT_MDD_HH
+/*
+* This file is part of rasdaman community.
+*
+* Rasdaman community is free software: you can redistribute it and/or modify
+* it under the terms of the GNU General Public License as published by
+* the Free Software Foundation, either version 3 of the License, or
+* (at your option) any later version.
+*
+* Rasdaman community is distributed in the hope that it will be useful,
+* but WITHOUT ANY WARRANTY; without even the implied warranty of
+* MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
+* GNU General Public License for more details.
+*
+* You should have received a copy of the GNU General Public License
+* along with rasdaman community. If not, see <http://www.gnu.org/licenses/>.
+*
+* Copyright 2003, 2004, 2005, 2006, 2007, 2008, 2009 Peter Baumann /
+rasdaman GmbH.
+*
+* For more information please see <http://www.rasdaman.org>
+* or contact Peter Baumann via <baumann@rasdaman.com>.
+*/
+/*************************************************************
+ *
+ *
+ * COMMENTS:
+ *
+ * These are tools for fast, low level acces to MDD and Colelctions
+ * The main purpose is speeding up initialization and import operations
+ *
+ ************************************************************/
+
+
+#include "mddmgr/mddcoll.hh"
+#include "mddmgr/mddobj.hh"
+#include "mddmgr/mddcolliter.hh"
+#include "tilemgr/tile.hh"
+#include "catalogmgr/typefactory.hh"
+#include "relcatalogif/mddtype.hh"
+#include "relcatalogif/mdddomaintype.hh"
+#include "relcatalogif/settype.hh"
+#include "reladminif/eoid.hh"
+#include "raslib/basetype.hh"
+#include "compression/tilecompression.hh"
+#include "raslib/oid.hh"
+#include "servercomm/servercomm.hh"
+
+
+class FastCollectionCreator
+ {
+ public:
+ FastCollectionCreator(const char *collName, const char* collTypeName);
+
+ r_OId createCollection();
+
+ private:
+ // allow only [A-Z,a-z,_]
+ void verifyName( const char* name ) throw(r_Error);
+
+ const char *collectionName;
+ const char *collectionTypeName;
+
+ };
+
+
+class FastMDDCreator
+ {
+ public:
+ FastMDDCreator();
+ ~FastMDDCreator();
+
+ void setCollectionName(const char *collName);
+ void setMDDTypeName(const char* mddTypeName);
+
+ r_OId createMDD(const char *domain);
+ r_OId createRCxMDD(const char *domain, const char *tileDomain);
+
+ void addStripe(r_OId mddOId, const char *stripeDomain, const char *tileDomain);
+
+ vector<r_Minterval> getTileDomains(r_OId mddOId, const char *stripeDomain);
+ private:
+ void verifyCompatibility(MDDColl *collection) throw(r_Error);
+
+ void createCompressedTileData(r_Minterval&, const BaseType* baseType);
+
+ std::string collectionName;
+ std::string mddTypeName;
+
+ r_Minterval definitionInterval;
+
+ r_Data_Format storageFormat;
+ const char *formatParams;
+
+ r_OId mddOId;
+ int cellSize;
+
+ char *comprData;
+ int comprDataSize;
+
+ MDDObj *mymdd;
+ };
+
+#endif
diff --git a/server/rasserver_config.cc b/server/rasserver_config.cc
new file mode 100644
index 0000000..94c2963
--- /dev/null
+++ b/server/rasserver_config.cc
@@ -0,0 +1,297 @@
+/*
+* This file is part of rasdaman community.
+*
+* Rasdaman community is free software: you can redistribute it and/or modify
+* it under the terms of the GNU General Public License as published by
+* the Free Software Foundation, either version 3 of the License, or
+* (at your option) any later version.
+*
+* Rasdaman community is distributed in the hope that it will be useful,
+* but WITHOUT ANY WARRANTY; without even the implied warranty of
+* MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
+* GNU General Public License for more details.
+*
+* You should have received a copy of the GNU General Public License
+* along with rasdaman community. If not, see <http://www.gnu.org/licenses/>.
+*
+* Copyright 2003, 2004, 2005, 2006, 2007, 2008, 2009 Peter Baumann /
+rasdaman GmbH.
+*
+* For more information please see <http://www.rasdaman.org>
+* or contact Peter Baumann via <baumann@rasdaman.com>.
+*/
+/*
+ * 2003-nov-05 PB makeLogFileName: use constants, use /tmp if RMANHOME env var not defined
+ * 2005-sep-05 PB parseCommandLine(): exit -2 on help
+ * 2006-apr-21 PB added debug output
+ */
+
+using namespace std;
+
+#include <unistd.h>
+#include <netdb.h>
+#include <sys/stat.h>
+#include <iostream>
+#include <string>
+#include <sstream>
+
+#include "debug.hh" // ENTER, LEAVE, TALK
+#include "globals.hh" // DEFAULT_PORT, LOGDIR, ALT_LOGDIR, LOG_SUFFIX
+#include "rasserver_config.hh"
+
+#include "storagemgr/sstoragelayout.hh"
+#include "servercomm/httpserver.hh"
+
+Configuration configuration;
+
+Configuration::Configuration()
+ {
+ logToStdOut = true;
+ logFileName = 0;
+ }
+
+
+bool Configuration::parseCommandLine(int argc, char** argv)
+ {
+ CommandLineParser &cmlInter = CommandLineParser::getInstance();
+ initParameters();
+
+ try
+ {
+ myExecutable = argv[0];
+ cmlInter.processCommandLine(argc, argv);
+
+ if(cmlHelp->isPresent())
+ {
+ printHelp();
+ exit( -2 ); // Unix code for 'help' -- PB 2005-sep-18
+ }
+ checkParameters();
+ }
+
+ catch(CmlException &ex)
+ {
+ cout<<"Error: " << ex.what()<<endl;
+
+ if(!logToStdOut)
+ {
+ RMInit::logOut<<"Error: " << ex.what()<<endl;
+ }
+ return false;
+ }
+ return true;
+ }
+
+// just for shorter lines...
+#define NSN CommandLineParser::noShortName
+
+void Configuration::initParameters()
+ {
+ CommandLineParser &cmlInter = CommandLineParser::getInstance();
+
+ cmlHelp = &cmlInter.addFlagParameter('h', "help", "print this help");
+
+ //connection
+ cmlRsn = &cmlInter.addStringParameter(NSN, "rsn", "<srv-name> rasserver instance name");
+ cmlPort = &cmlInter.addStringParameter(NSN, "lport", "<nnnn> rasserver listen port (RPC or HTTP)");
+ cmlMgr = &cmlInter.addStringParameter(NSN, "mgr", "<mgr-host> name of RasMGR host", DEFAULT_HOSTNAME);
+ cmlMgrPort = &cmlInter.addLongParameter(NSN, "mgrport", "<nnnn> port of RasMGR", DEFAULT_PORT );
+ cmlMgrSync = &cmlInter.addStringParameter(NSN, "sync", NULL); // deprecated
+
+ cmlTransBuffer = &cmlInter.addLongParameter(NSN, "transbuffer", "<nnnn> maximal size of the transfer buffer in bytes", MAX_BUFFER_SIZE);
+ cmlTimeOut = &cmlInter.addLongParameter(NSN, "timeout", "<nnn> client time out in seconds.\n\t\tif it is set to 0 server doesn't check for client timeouts", CLIENT_TIMEOUT);
+ cmlMgmntInt = &cmlInter.addStringParameter(NSN, "mgmntint", NULL); // deprecated
+ cmlHttp = &cmlInter.addFlagParameter(NSN, "http", "start HTTP version of rasserver");
+ cmlRnp = &cmlInter.addFlagParameter(NSN, "rnp", "start RNP version of rasserver");
+
+ cmlOptLevel = &cmlInter.addLongParameter(NSN, "opt", "<nn> optimization level(0-4)\n\t\t 0 = no / 4 = maximal optimization", 4L);
+ cmlConnectStr = &cmlInter.addStringParameter(NSN, "connect", "<connect-str> connect string for underlying database(e.g. test/test@julep)", "/");
+ cmlLog = &cmlInter.addStringParameter('l', "log", "<log-file> log is printed to <log-file>\n\t\tif <log-file> is stdout , log output is printed to standard out", "$RMANHOME/log/<srv-name>.<pid>.log");
+
+#ifdef RMANDEBUG
+ cmlTileSize = &cmlInter.addLongParameter(NSN, "tilesize", "<nnnn> specifies maximal size of tiles in bytes\n\t\t-regular tiles with equal edge lengthes", 2097152);
+ cmlPctMin = &cmlInter.addLongParameter(NSN, "pctmin", "<nnnn> specifies minimal size of blobtiles in bytes", 2048);
+ cmlPctMax = &cmlInter.addLongParameter(NSN, "pctmax", "<nnnn> specifies maximal size of inlinetiles in bytes", 4096);
+ cmlUseTC = &cmlInter.addFlagParameter(NSN, "usetc", "use TileContainerIndex");
+ cmlTileConf = &cmlInter.addStringParameter(NSN, "tileconf", "<dom> default tile configuration (e.g. [0:1,0:2])", "[0:511,0:511]");
+
+ string tilingDesc = string("<tiling-name> retiling strategy, specified as:") + CommandLineParameter::descLineSep +
+ " " + tiling_name_notiling + "," + CommandLineParameter::descLineSep +
+ " " + tiling_name_regulartiling;
+ cmlTiling = &cmlInter.addStringParameter(NSN, "tiling", tilingDesc.c_str(), tiling_name_notiling);
+
+ string indexDesc = string("<index-name> index for created objects, specified as:") + CommandLineParameter::descLineSep +
+ " " + index_name_auto + "," + CommandLineParameter::descLineSep +
+ " " + index_name_directory + "," + CommandLineParameter::descLineSep +
+ " " + index_name_regdirectory + "," + CommandLineParameter::descLineSep +
+ " " + index_name_rplustree + "," + CommandLineParameter::descLineSep +
+ " " + index_name_regrplustree + "," + CommandLineParameter::descLineSep +
+ " " + index_name_tilecontainer + "," + CommandLineParameter::descLineSep +
+ " " + index_name_regcomputed;
+ cmlIndex = &cmlInter.addStringParameter(NSN, "index", indexDesc.c_str(), index_name_rplustree);
+
+ // for systemtest use e.g.3 together with tileSize 12
+ string indexsizeDesc = string("<nnnn> make the index use n nodes");
+ cmlIndexSize = &cmlInter.addLongParameter(NSN, "indexsize", indexsizeDesc.c_str(),0L);
+ cmlDbg = &cmlInter.addStringParameter('d', "debug", "<dgb-file> debug output is printed to <dbg-file>; if <dbg-file> is stdout, debug output is printed to standard out","<srv-name>.log");
+ cmlDbgLevel = &cmlInter.addLongParameter(NSN, "dl", "<nn> debug level (0-4; 0 = no / 4 = maximal debug information)", 0L);
+#endif // RMANDEBUG
+
+ }
+#undef NSN
+
+void Configuration::checkParameters()
+ {
+ ENTER( "Configuration::checkParameters()" );
+
+ serverName = cmlRsn->getValueAsString();
+
+ initLogFiles();
+
+ listenPort = cmlPort->getValueAsLong();
+
+ rasmgrHost = cmlMgr->getValueAsString();
+ rasmgrPort = cmlMgrPort->getValueAsLong();
+ TALK( "rasmgrHost = " << rasmgrHost << ", rasmgrPort = " << rasmgrPort );
+
+ deprecated(cmlMgrSync);
+
+ maxTransferBufferSize = cmlTransBuffer->getValueAsLong();
+ timeout = cmlTimeOut->getValueAsLong();
+ deprecated(cmlMgmntInt);
+ httpServ = cmlHttp->isPresent();
+ rnpServ = cmlRnp->isPresent();
+
+ optLevel = cmlOptLevel->getValueAsLong();
+ dbConnection = cmlConnectStr->getValueAsString();
+
+#ifdef RMANDEBUG
+ tileSize = cmlTileSize->getValueAsLong();
+ pctMin = cmlPctMin->getValueAsLong();
+ pctMax = cmlPctMax->getValueAsLong();
+ useTC = cmlUseTC->isPresent();
+
+
+ tileConf = cmlTileConf->getValueAsString();//(r_Minterval..)
+ tilingName = cmlTiling->getValueAsString();
+ indexType = cmlIndex->getValueAsString();
+ indexSize = cmlIndexSize->getValueAsLong();
+ deprecated(cmlDbg);
+ dbgLevel = cmlDbgLevel->getValueAsLong();
+#endif
+
+ LEAVE( "Configuration::checkParameters()" );
+ }
+
+void Configuration::printHelp()
+ {
+ CommandLineParser &cmlInter = CommandLineParser::getInstance();
+
+ cout << "Usage: rasserver [options]" << endl;
+ cout << "Options:" << endl;
+ cmlInter.printHelp();
+
+ cout << endl;
+
+ }
+
+void
+Configuration::initLogFiles()
+ {
+ if( cmlLog->isPresent())
+ {
+ if( strcasecmp(cmlLog->getValueAsString(), "stdout") != 0)
+ { logFileName = cmlLog->getValueAsString();
+ logToStdOut = false;
+ }
+ else
+ {
+ logFileName = "stdout";
+ logToStdOut = true;
+ }
+ }
+ else
+ { // default
+ logFileName = makeLogFileName( serverName, LOG_SUFFIX );
+ logToStdOut = false;
+ }
+
+ if( logToStdOut == true)
+ {
+ RMInit::logOut.rdbuf(cout.rdbuf());
+ RMInit::dbgOut.rdbuf(cout.rdbuf());
+ RMInit::bmOut.rdbuf(cout.rdbuf());
+ }
+ else
+ {
+ if (RMInit::logFileOut.is_open())
+ RMInit::logFileOut.close();
+ RMInit::logFileOut.open(logFileName, ios::out | ios::ate);
+ RMInit::logOut.rdbuf(RMInit::logFileOut.rdbuf());
+ RMInit::dbgOut.rdbuf(RMInit::logFileOut.rdbuf());
+ RMInit::bmOut.rdbuf(RMInit::logFileOut.rdbuf());
+ }
+ cout<<"This server's log file is: " << logFileName << endl;
+ }
+
+const char *
+Configuration::makeLogFileName(const char *srvName,const char *desExt)
+ {
+ static char buffer[ FILENAME_MAX ];
+ int pid =getpid();
+ char *dir = getenv( RMANHOME_VAR );
+ if (dir == NULL)
+ {
+ cout << "Error: environment variable " << RMANHOME_VAR << " not set. Using " << ALT_LOGDIR << " for the moment being." << endl;
+ strcpy( buffer, ALT_LOGDIR );
+ }
+ else
+ {
+ strcpy( buffer, dir );
+ strcat( buffer, LOGDIR );
+ }
+ mkdir(buffer,S_IRWXU + S_IRGRP+S_IXGRP + S_IROTH+S_IXOTH); // create if not exist, rwxr-xr-x
+ sprintf(buffer+strlen(buffer),"/%s.%06d.%s",srvName,pid,desExt);
+ return buffer;
+ }
+
+void
+Configuration::deprecated(CommandLineParameter *cml)
+ {
+ if(cml->isPresent())
+ {
+ cout<<"WARNING: parameter '"<<cml->calledName()<<"' is deprecated, will be removed in next version!"<<endl;
+ }
+ }
+
+const char* Configuration::getServerName() { return serverName; }
+int Configuration::getListenPort() { return listenPort; }
+bool Configuration::isHttpServer() { return httpServ; }
+bool Configuration::isRnpServer() { return rnpServ; }
+
+const char* Configuration::getRasmgrHost() { return rasmgrHost; }
+int Configuration::getRasmgrPort() { return rasmgrPort; }
+
+bool Configuration::isLogToStdOut() { return logToStdOut; }
+
+int Configuration::getDefaultOptimizationLevel() { return optLevel; }
+int Configuration::getMaxTransferBufferSize() { return maxTransferBufferSize; }
+int Configuration::getTimeout() { return timeout; }
+const char* Configuration::getDbConnectionID() { return dbConnection; }
+
+#ifdef RMANDEBUG
+int Configuration::getDefaultTileSize() { return tileSize; }
+int Configuration::getDefaultPCTMin() { return pctMin; }
+int Configuration::getDefaultPCTMax() { return pctMax; }
+
+int Configuration::getDefaultIndexSize(){ return indexSize; }
+
+int Configuration::getDebugLevel() { return dbgLevel; }
+
+const char* Configuration::getDefaultTileConfig() { return tileConf; }
+const char* Configuration::getTilingScheme() { return tilingName; }
+const char* Configuration::getIndexType() { return indexType; }
+bool Configuration::useTileContainer() { return useTC; }
+
+#endif
+
diff --git a/server/rasserver_config.hh b/server/rasserver_config.hh
new file mode 100644
index 0000000..dcb777d
--- /dev/null
+++ b/server/rasserver_config.hh
@@ -0,0 +1,138 @@
+/*
+* This file is part of rasdaman community.
+*
+* Rasdaman community is free software: you can redistribute it and/or modify
+* it under the terms of the GNU General Public License as published by
+* the Free Software Foundation, either version 3 of the License, or
+* (at your option) any later version.
+*
+* Rasdaman community is distributed in the hope that it will be useful,
+* but WITHOUT ANY WARRANTY; without even the implied warranty of
+* MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
+* GNU General Public License for more details.
+*
+* You should have received a copy of the GNU General Public License
+* along with rasdaman community. If not, see <http://www.gnu.org/licenses/>.
+*
+* Copyright 2003, 2004, 2005, 2006, 2007, 2008, 2009 Peter Baumann /
+rasdaman GmbH.
+*
+* For more information please see <http://www.rasdaman.org>
+* or contact Peter Baumann via <baumann@rasdaman.com>.
+*/
+#ifndef RASSERVER_CONFIG_HH
+#define RASSERVER_CONFIG_HH
+
+
+#include "commline/cmlparser.hh"
+
+class Configuration
+ {
+ public:
+ Configuration();
+
+ bool parseCommandLine(int argc, char** argv);
+
+ const char* getServerName();
+ int getListenPort();
+ bool isHttpServer();
+ bool isRnpServer();
+
+ const char* getRasmgrHost();
+ int getRasmgrPort();
+ bool isLogToStdOut();
+
+ int getDefaultOptimizationLevel();
+ int getMaxTransferBufferSize();
+ int getTimeout();
+ const char* getDbConnectionID();
+
+#ifdef RMANDEBUG
+ int getDefaultTileSize();
+ int getDefaultPCTMin();
+ int getDefaultPCTMax();
+
+ int getDefaultIndexSize();
+
+ int getDebugLevel();
+
+ const char* getDefaultTileConfig();
+ const char* getTilingScheme();
+ const char* getIndexType();
+ bool useTileContainer();
+
+#endif
+ private:
+ void printHelp();
+
+ void initParameters();
+ void checkParameters();
+ void initLogFiles();
+ void deprecated(CommandLineParameter*);
+
+ const char* makeLogFileName(const char *srvName,const char *desExt);
+
+ // Parameters
+ CommandLineParameter *cmlHelp;
+ CommandLineParameter *cmlRsn;
+ CommandLineParameter *cmlPort;
+ CommandLineParameter *cmlMgr;
+ CommandLineParameter *cmlMgrPort;
+ CommandLineParameter *cmlMgrSync;
+
+ CommandLineParameter *cmlTransBuffer;
+ CommandLineParameter *cmlTimeOut;
+ CommandLineParameter *cmlMgmntInt;
+ CommandLineParameter *cmlHttp;
+ CommandLineParameter *cmlRnp;
+
+ CommandLineParameter *cmlOptLevel;
+ CommandLineParameter *cmlConnectStr;
+ CommandLineParameter *cmlLog;
+
+#ifdef RMANDEBUG
+ CommandLineParameter *cmlTileSize;
+ CommandLineParameter *cmlPctMin;
+ CommandLineParameter *cmlPctMax;
+ CommandLineParameter *cmlUseTC;
+ CommandLineParameter *cmlTileConf;
+ CommandLineParameter *cmlTiling;
+ CommandLineParameter *cmlIndex;
+ CommandLineParameter *cmlIndexSize;
+ CommandLineParameter *cmlDbg;
+ CommandLineParameter *cmlDbgLevel;
+#endif
+ const char* myExecutable;
+
+ const char* serverName;
+ int listenPort;
+
+ const char* rasmgrHost;
+ int rasmgrPort;
+
+ bool logToStdOut;
+ const char* logFileName; // == 0 if stdout
+
+ int maxTransferBufferSize;
+ int timeout;
+ bool httpServ;
+ bool rnpServ;
+ int optLevel;
+ const char* dbConnection;
+
+#ifdef RMANDEBUG
+ int tileSize;
+ int pctMin;
+ int pctMax;
+ bool useTC;
+ const char* tileConf;
+ const char* tilingName;
+ const char* indexType;
+ int indexSize;
+ int dbgLevel;
+#endif
+ };
+
+extern Configuration configuration;
+
+#endif
diff --git a/server/rasserver_entry.cc b/server/rasserver_entry.cc
new file mode 100644
index 0000000..2296ec8
--- /dev/null
+++ b/server/rasserver_entry.cc
@@ -0,0 +1,528 @@
+/*
+* This file is part of rasdaman community.
+*
+* Rasdaman community is free software: you can redistribute it and/or modify
+* it under the terms of the GNU General Public License as published by
+* the Free Software Foundation, either version 3 of the License, or
+* (at your option) any later version.
+*
+* Rasdaman community is distributed in the hope that it will be useful,
+* but WITHOUT ANY WARRANTY; without even the implied warranty of
+* MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
+* GNU General Public License for more details.
+*
+* You should have received a copy of the GNU General Public License
+* along with rasdaman community. If not, see <http://www.gnu.org/licenses/>.
+*
+* Copyright 2003, 2004, 2005, 2006, 2007, 2008, 2009 Peter Baumann /
+rasdaman GmbH.
+*
+* For more information please see <http://www.rasdaman.org>
+* or contact Peter Baumann via <baumann@rasdaman.com>.
+*/
+/*************************************************************
+ *
+ *
+ * PURPOSE:
+ *
+ *
+ * COMMENTS:
+ *
+ ************************************************************/
+
+using namespace std;
+
+#include "mymalloc/mymalloc.h"
+
+#include "rasserver_entry.hh"
+
+#include "debug-srv.hh"
+
+// console output describing successful/unsuccessful actions (cf. servercomm/servercomm.cc)
+#define MSG_OK "ok"
+#define MSG_FAILED "failed"
+
+
+struct HTTPRequest
+{
+ char *Database;
+ int Command;
+ char *QueryString;
+ int ClientType;
+ char *ClientID;
+ int Endianess;
+ int NumberOfQueryParams;
+ char *BinData;
+ int BinDataSize;
+ char *Capability;
+};
+
+
+RasServerEntry* RasServerEntry::myself = 0;
+
+RasServerEntry& RasServerEntry::getInstance()
+{
+ if(myself == 0)
+ myself = new RasServerEntry;
+ return *myself;
+}
+
+RasServerEntry::RasServerEntry()
+{
+}
+
+RasServerEntry::~RasServerEntry()
+{
+}
+
+void RasServerEntry::compat_connectToDBMS() throw( r_Error )
+{
+ // here no log output, this is a server startup function!
+
+ admin = AdminIf::instance();
+ if( !admin )
+ throw r_Error( r_Error::r_Error_BaseDBMSFailed );
+}
+
+void RasServerEntry::compat_connectNewClient(const char *capability)
+{
+ // we need to add the log information which otherwise is provided in ServerComm (servercomm/servercomm2.cc)
+ RMInit::logOut << "Request: connectNewClient..." << flush;
+
+ char client[256]; strcpy( client, "unknown" );
+
+#if 0 // client table is a relict from 1-process, multi-user rasdaman;
+ // now it conflicts with rasmgr dispatcher mimics, so we disable -- PB 2005-sep-01
+ currentClientContext = new ClientTblElt( client, ++(clientCount) );
+ currentClientIdx = clientCount;
+#else
+// this id must be !=0 because otherwise in ServerComm::getClientContext() it will not be recognized as valid id, and then the "last action" time will not be updated (timeout!)
+#define SINGLETON_CLIENTID 42
+
+ // disable client list by using only 1 element (fixed id), initialize only once
+ currentClientIdx = SINGLETON_CLIENTID;
+ // if (currentClientContext==NULL)
+ currentClientContext = new ClientTblElt( client, currentClientIdx );
+ TALK( "using constant Client id " << currentClientIdx );
+
+ // make sure any old element is deleted; currently inhibited, crashes :( -- PB 2005-sep-02
+ // RMInit::logOut << "client table has " << clientTbl.size() << " elements before cleanup, ";
+ // ServerComm::deleteClientTblEntry( currentClientIdx );
+ // RMInit::logOut << " and " << clientTbl.size() << " after.";
+#endif // 0
+
+ // Put the context information in the static control list
+ ServerComm::addClientTblEntry( currentClientContext );
+
+ TALK( "assigned Client id " << currentClientIdx );
+
+ if(accessControl.crunchCapability(capability) == CAPABILITY_REFUSED)
+ throw r_Ecapability_refused();
+
+ RMInit::logOut << MSG_OK << endl;
+}
+
+void RasServerEntry::compat_disconnectClient()
+{
+ // we need to add the log information which otherwise is provided in ServerComm (servercomm/servercomm2.cc)
+ RMInit::logOut << "Request: disconnect..." << flush;
+
+#if 0 //
+ deleteClientTblEntry( currentClientIdx );
+ currentClientIdx = -1;
+#else
+ // disable client list, use 1 constant element (see above) -- PB 2005-sep-01
+ currentClientIdx = SINGLETON_CLIENTID;
+ ServerComm::deleteClientTblEntry( currentClientIdx );
+
+ // delete currentClientContext;
+ // currentClientContext = NULL;
+
+ // clientTbl.resize( 0 );
+
+ RMInit::logOut << MSG_OK << endl;
+#endif // 0
+
+// in a disconnect following an abortta, the client can't be found any more in the table.
+// the delete op below then doesn't decrease table size -> endless loop.
+// Therefore let us take the original approach: delete only the requested client. -- PB 2003-nov-24
+#if 0
+ // THIS IS PARANOIA, ONCE WE HAD SOME PROBLEMS, SO WE KILL ALL
+ while(!clientTbl.empty())
+ {
+ ClientTblElt *temp = clientTbl.front();
+
+ temp->currentUsers = 0; // forced!
+
+ deleteClientTblEntry(temp->clientId);
+ }
+#endif // 0
+}
+
+// we want the ServerComm version, we'll drop this client management anyway
+ServerComm::ClientTblElt* RasServerEntry::getClientContext( unsigned long ClientId )
+{
+#if 0 // see above -- we just have 1 single context -- PB 2005-sep-01
+ ClientId = SINGLETON_CLIENTID;
+#endif // 0
+
+ return ServerComm::getClientContext( ClientId );
+}
+
+
+void RasServerEntry::compat_openDB(const char* databaseName)
+{
+ // we use "ServercComm::" just to show that it's that function
+ ServerComm::openDB( currentClientIdx, databaseName, "" );
+}
+
+void RasServerEntry::compat_closeDB()
+{
+ ServerComm::closeDB( currentClientIdx);
+}
+
+void RasServerEntry::compat_beginTA(bool rw)
+{
+ ServerComm::beginTA( currentClientIdx, rw ? 0 : 1);
+}
+
+void RasServerEntry::compat_commitTA()
+{
+ ServerComm::commitTA( currentClientIdx);
+}
+
+void RasServerEntry::compat_abortTA()
+{
+ ServerComm::abortTA( currentClientIdx);
+}
+
+bool RasServerEntry::compat_isOpenTA()
+{
+ return ServerComm::isTAOpen( currentClientIdx );
+}
+
+int GetHTTPRequestTemp( char *Source, int SourceLen, struct HTTPRequest *RequestInfo);
+
+int RasServerEntry::compat_executeQueryHttp(const char* httpParams, int httpParamsLen, char*& resultBuffer)
+{
+ strcpy(currentClientContext->clientIdText, ServerComm::HTTPCLIENT);
+
+ HTTPRequest RequestInfo;
+ /* Initialize RequestInfo */
+ RequestInfo.Database = NULL;
+ RequestInfo.QueryString = NULL;
+ RequestInfo.ClientType = 0;
+ RequestInfo.ClientID = NULL;
+ RequestInfo.Command = 0;
+ RequestInfo.Endianess = 0;
+ RequestInfo.NumberOfQueryParams = 0;
+ RequestInfo.BinDataSize = 0;
+ RequestInfo.BinData = NULL;
+ RequestInfo.Capability = NULL;
+
+ int resultLen = 0;
+ if(GetHTTPRequestTemp( (char*)httpParams, httpParamsLen, &RequestInfo) == 0)
+ {
+ // we need to add the log information which otherwise is provided in ServerComm (servercomm/servercomm2.cc)
+ // logged now in rnprotocol modules -- PB 2005-sep-05
+ // RMInit::logOut << "Request: http query '" << RequestInfo.QueryString << "'..." << flush;
+ char* queryResult;
+
+ resultLen = HttpServer::processRequest(currentClientIdx, RequestInfo.Database, RequestInfo.Command,
+ RequestInfo.QueryString, RequestInfo.BinDataSize,
+ RequestInfo.BinData, RequestInfo.Endianess,
+ queryResult,RequestInfo.Capability);
+
+ resultBuffer = queryResult;
+ RMInit::logOut << MSG_OK << endl;
+ }
+ else
+ RMInit::logOut << "Error: Internal HTTP protocol mismatch." << endl;
+
+ // free RequestInfo
+ free(RequestInfo.Database);
+ free(RequestInfo.QueryString);
+ free(RequestInfo.Capability);
+ free(RequestInfo.BinData);
+ free(RequestInfo.ClientID);
+
+ return resultLen;
+}
+
+r_OId RasServerEntry::compat_getNewOId(unsigned short objType)
+{
+ r_OId result;
+
+ ServerComm::getNewOId(currentClientIdx, objType, result);
+
+ return result;
+}
+
+
+int RasServerEntry::compat_executeQueryRpc(const char* query, ExecuteQueryRes &queryResult)
+{
+ queryResult.token=NULL;
+ queryResult.typeName=NULL;
+ queryResult.typeStructure=NULL;
+
+ return ServerComm::executeQuery(currentClientIdx, query, queryResult);
+}
+
+int RasServerEntry::compat_getNextElement(char* &buffer, unsigned int &bufferSize )
+{
+ return ServerComm::getNextElement(currentClientIdx, buffer, bufferSize);
+}
+
+int RasServerEntry::compat_endTransfer()
+{
+ return ServerComm::endTransfer(currentClientIdx);
+}
+
+int RasServerEntry::compat_getNextMDD(r_Minterval &mddDomain, char* &typeName, char* &typeStructure, r_OId &oid,unsigned short &currentFormat)
+{
+ return ServerComm::getNextMDD( currentClientIdx, mddDomain, typeName, typeStructure, oid, currentFormat);
+}
+int RasServerEntry::compat_getNextTile(RPCMarray** rpcMarray)
+{
+ return ServerComm::getNextTile( currentClientIdx, rpcMarray);
+}
+
+int RasServerEntry::compat_ExecuteUpdateQuery(const char *query, ExecuteUpdateRes& returnStructure)
+{
+ return ServerComm::executeUpdate(currentClientIdx, query, returnStructure);
+}
+
+int RasServerEntry::compat_InitUpdate()
+{
+ return ServerComm::initExecuteUpdate(currentClientIdx);
+}
+
+int RasServerEntry::compat_StartInsertTransMDD(const char *domain, int typeLength, const char *typeName)
+{
+ r_Minterval mddDomain(domain);
+ return ServerComm::startInsertTransMDD(currentClientIdx, mddDomain, typeLength, typeName);
+}
+
+int RasServerEntry::compat_InsertTile(int persistent, RPCMarray *rpcMarray)
+{
+ return ServerComm::insertTile( currentClientIdx, persistent, rpcMarray );
+}
+
+int RasServerEntry::compat_EndInsertMDD(int persistent)
+{
+ return ServerComm::endInsertMDD( currentClientIdx, persistent );
+}
+
+int RasServerEntry::compat_GetTypeStructure(const char *typeName, int typeType, char* &typeStructure)
+{
+ return ServerComm::getTypeStructure( currentClientIdx, typeName, typeType, typeStructure );
+}
+
+int RasServerEntry::compat_StartInsertPersMDD(const char *collName, r_Minterval &mddDomain, int typeLength, const char *typeName, r_OId &oid)
+{
+ return ServerComm::startInsertPersMDD( currentClientIdx, collName, mddDomain, typeLength, typeName, oid );
+}
+
+int RasServerEntry::compat_InsertMDD(const char *collName, RPCMarray *rpcMarray, const char *typeName, r_OId &oid)
+{
+ return ServerComm::insertMDD( currentClientIdx, collName, rpcMarray, typeName, oid );
+}
+
+int RasServerEntry::compat_InsertCollection(const char *collName, const char *typeName, r_OId &oid)
+{
+ return ServerComm::insertColl( currentClientIdx, collName, typeName, oid );
+}
+
+int RasServerEntry::compat_DeleteCollByName(const char *collName)
+{
+ return ServerComm::deleteCollByName( currentClientIdx, collName );
+}
+
+int RasServerEntry::compat_DeleteObjByOId(r_OId &oid)
+{
+ return ServerComm::deleteObjByOId( currentClientIdx, oid );
+}
+
+int RasServerEntry::compat_RemoveObjFromColl(const char *collName, r_OId &oid)
+{
+ return ServerComm::removeObjFromColl( currentClientIdx, collName, oid );
+}
+
+int RasServerEntry::compat_GetCollectionByName(const char* collName, char* &typeName, char* &typeStructure, r_OId &oid)
+{
+ return ServerComm::getCollByName( currentClientIdx, collName, typeName, typeStructure, oid );
+}
+
+int RasServerEntry::compat_GetCollectionByName(r_OId oid, char* &typeName, char* &typeStructure, char* &collName)
+{
+ return ServerComm::getCollByOId( currentClientIdx, oid, typeName,typeStructure, collName );
+}
+
+int RasServerEntry::compat_GetCollectionOidsByName(const char* collName, char* &typeName, char* &typeStructure, r_OId &oid, RPCOIdEntry* &oidTable, unsigned int &oidTableSize)
+{
+ return ServerComm::getCollOIdsByName( currentClientIdx, collName, typeName, typeStructure, oid, oidTable, oidTableSize);
+}
+
+int RasServerEntry::compat_GetCollectionOidsByOId(r_OId oid, char* &typeName, char* &typeStructure, RPCOIdEntry* &oidTable, unsigned int &oidTableSize, char* &collName)
+{
+ return ServerComm::getCollOIdsByOId( currentClientIdx, oid, typeName, typeStructure, oidTable, oidTableSize, collName);
+}
+
+int RasServerEntry::compat_GetObjectType(r_OId &oid, unsigned short &objType)
+{
+ return ServerComm::getObjectType( currentClientIdx, oid, objType );
+}
+
+int RasServerEntry::compat_SetTransferFormat(int format, const char* params)
+{
+ return ServerComm::setTransferMode( currentClientIdx, format, params );
+}
+
+int RasServerEntry::compat_SetStorageFormat(int format, const char* params)
+{
+ return ServerComm::setStorageMode( currentClientIdx, format, params );
+}
+
+//### stupid inherited stuff, we'll lose them later #####
+void RasServerEntry::startRpcServer() throw( r_Error ){}
+void RasServerEntry::stopRpcServer(){}
+//#######################################################
+
+// local version of this function, with small adaptations to compile here.
+int GetHTTPRequestTemp( char *Source, int SourceLen, struct HTTPRequest *RequestInfo)
+{
+ ENTER( "GetHTTPRequestTemp, source=" << Source << ", SourceLen=" << SourceLen );
+
+ int result = 0; // function return value
+ char *Buffer = NULL; // ptr to current analysis point in Input
+ char *Input = NULL; // local copy of Source
+
+ Input = new char[ SourceLen + 1 ];
+ memcpy( Input, Source, SourceLen );
+ Input[SourceLen] = '\0';
+ // Read the message body and check for the post parameters
+ Buffer = strtok( Input, "=" );
+ while( Buffer != NULL )
+ {
+ if( strcmp(Buffer,"Database") == 0 )
+ {
+ RequestInfo->Database = strdup(strtok( NULL, "&" ));
+ TALK( "Parameter Database is " << RequestInfo->Database );
+ Buffer = strtok( NULL, "=" );
+ }
+ else if( strcmp(Buffer,"QueryString") == 0 )
+ {
+ RequestInfo->QueryString = strdup(strtok( NULL, "&" ));
+ TALK( "Parameter QueryString is " << RequestInfo->QueryString );
+ Buffer = strtok( NULL, "=" );
+ }
+ else if( strcmp(Buffer,"Capability") == 0 )
+ {
+ RequestInfo->Capability = strdup(strtok( NULL, "&\0" ));
+ TALK( "Parameter Capability is " << RequestInfo->Capability );
+ Buffer = strtok( NULL, "=" );
+ }
+ else if( strcmp(Buffer,"ClientID") == 0 )
+ {
+ RequestInfo->ClientID = strdup(strtok( NULL, "&" ));
+ TALK( "Parameter ClientID is " << RequestInfo->ClientID );
+ Buffer = strtok( NULL, "=" );
+ }
+ else if( strcmp(Buffer,"Command") == 0 )
+ {
+ RequestInfo->Command = atoi( strtok( NULL, "&" ) );
+ TALK( "Parameter Command is " << RequestInfo->Command );
+ Buffer = strtok( NULL, "=" );
+ }
+ else if( strcmp(Buffer,"Endianess") == 0 )
+ {
+ RequestInfo->Endianess = atoi( strtok( NULL, "&" ) );
+ TALK( "Parameter Endianess is " << RequestInfo->Endianess );
+ Buffer = strtok( NULL, "=" );
+ }
+ else if( strcmp(Buffer,"NumberOfQueryParameters") == 0 )
+ {
+ RequestInfo->NumberOfQueryParams = atoi( strtok( NULL, "&" ) );
+ TALK( "Parameter NumberOfQueryParams is " << RequestInfo->NumberOfQueryParams );
+ Buffer = strtok( NULL, "=" );
+ }
+ else if( strcmp(Buffer,"BinDataSize") == 0 )
+ {
+ RequestInfo->BinDataSize = atoi( strtok( NULL, "&" ) );
+ TALK( "Parameter BinDataSize is " << RequestInfo->BinDataSize );
+ Buffer = strtok( NULL, "=" );
+ }
+ else if( strcmp(Buffer,"BinData") == 0 )
+ {
+ // This parameter has to be the last one!
+ RequestInfo->BinData = new char[RequestInfo->BinDataSize ];
+ memcpy(RequestInfo->BinData, Source + (SourceLen-RequestInfo->BinDataSize), RequestInfo->BinDataSize );
+ //set Buffer to NULL => exit this while block
+ Buffer = NULL;
+ }
+ else if( strcmp(Buffer,"ClientType") == 0 )
+ {
+ Buffer = strtok( NULL, "&" );
+ TALK( "Parameter Type is " << Buffer );
+ /* BROWSER? */
+ if( strcmp(Buffer,"BROWSER") == 0 )
+ RequestInfo->ClientType = 1;
+ /* Rasclient? */
+ else if( strcmp(Buffer,"RASCLIENT") == 0 )
+ RequestInfo->ClientType = 2;
+ /* Sonstiges */
+ else
+ {
+ TALK( "Error: Unknown Parameter: " << Buffer );
+ result = 2;
+ }
+ Buffer = strtok( NULL, "=" );
+ }
+ else
+ result = 1;
+ }
+
+ if (result == 0)
+ delete[] Input;
+
+ LEAVE( "GetHTTPRequestTemp, result=" << result );
+ return result;
+}
+
+//#####################################################################################################
+#include "server/createinitmdd.hh"
+
+r_OId RasServerEntry::createCollection(const char* collName, const char* collTypeName)
+{
+ FastCollectionCreator fcc(collName, collTypeName);
+
+ return fcc.createCollection();
+}
+
+r_OId RasServerEntry::createMDD(const char* collName, const char* mddTypeName, const char* definitionDomain, const char* tileDomain, bool rcindex)
+{
+ FastMDDCreator fc;
+
+ fc.setCollectionName(collName);
+ fc.setMDDTypeName(mddTypeName);
+
+ if(rcindex)
+ return fc.createRCxMDD(definitionDomain, tileDomain);
+
+ return fc.createMDD(definitionDomain);
+}
+
+void RasServerEntry::extendMDD(r_OId mddOId, const char *stripeDomain, const char* tileDomain)
+{
+ FastMDDCreator fc;
+
+ fc.addStripe(mddOId, stripeDomain, tileDomain);
+}
+
+vector<r_Minterval> RasServerEntry::getTileDomains(r_OId mddOId, const char *stripeDomain)
+{
+ FastMDDCreator fc;
+
+ return fc.getTileDomains(mddOId, stripeDomain);
+}
+
diff --git a/server/rasserver_entry.hh b/server/rasserver_entry.hh
new file mode 100644
index 0000000..64dbbfc
--- /dev/null
+++ b/server/rasserver_entry.hh
@@ -0,0 +1,140 @@
+/*
+* This file is part of rasdaman community.
+*
+* Rasdaman community is free software: you can redistribute it and/or modify
+* it under the terms of the GNU General Public License as published by
+* the Free Software Foundation, either version 3 of the License, or
+* (at your option) any later version.
+*
+* Rasdaman community is distributed in the hope that it will be useful,
+* but WITHOUT ANY WARRANTY; without even the implied warranty of
+* MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
+* GNU General Public License for more details.
+*
+* You should have received a copy of the GNU General Public License
+* along with rasdaman community. If not, see <http://www.gnu.org/licenses/>.
+*
+* Copyright 2003, 2004, 2005, 2006, 2007, 2008, 2009 Peter Baumann /
+rasdaman GmbH.
+*
+* For more information please see <http://www.rasdaman.org>
+* or contact Peter Baumann via <baumann@rasdaman.com>.
+*/
+#ifndef RASSERVER_ENTRY_HH
+#define RASSERVER_ENTRY_HH
+
+/*
+ This class is the entry point of the rasdaman server. It's the interface of the server to the outside world
+ It's functions are called by the communication level.
+
+ For now the class inherites HttpServer which inherites ServerComm, but only to have nice acces to the stuff
+ found there. Later we will drop both of them and make the life easier.
+*/
+
+#include "servercomm/httpserver.hh"
+
+
+class RasServerEntry : public HttpServer
+ {
+ private:
+ RasServerEntry();
+ static RasServerEntry* myself;
+ public:
+ static RasServerEntry& getInstance();
+
+ ~RasServerEntry();
+
+ //### inherited stuff - we have to keep them for now
+ void startRpcServer() throw( r_Error );
+ void stopRpcServer();
+ //###
+
+ void compat_connectToDBMS() throw( r_Error );
+
+ // All "compat_" functions use old ServerComm and HttpServer stuff to do their job
+ // Later, the new functions will do the job proper and this old functions will be dropped!
+ void compat_connectNewClient(const char *capability);
+ unsigned long currentClientIdx;
+ ClientTblElt* getClientContext( unsigned long ClientId ); // inherited...
+ ClientTblElt* currentClientContext;
+
+ void compat_disconnectClient();
+
+ void compat_openDB(const char* databaseName);
+
+ void compat_closeDB();
+
+ void compat_beginTA(bool rw);
+
+ void compat_commitTA();
+
+ void compat_abortTA();
+
+ bool compat_isOpenTA();
+
+ // provided for temporary compatibility with the encoding of the java interface
+ // resultBuffer will be allocated and it's address stored in the given pointer
+ // result is the length of the result
+ int compat_executeQueryHttp(const char* httpParams, int httpParamsLen, char*& resultBuffer);
+
+ r_OId compat_getNewOId(unsigned short objType); // 1 - mddType, 2 -collType
+
+ int compat_executeQueryRpc(const char* query, ExecuteQueryRes &queryResult);
+
+ int compat_getNextElement(char* &buffer, unsigned int &bufferSize );
+
+ int compat_endTransfer();
+
+ int compat_getNextMDD(r_Minterval &mddDomain, char* &typeName, char* &typeStructure, r_OId &oid,unsigned short &currentFormat);
+
+ int compat_getNextTile(RPCMarray** rpcMarray);
+
+ int compat_ExecuteUpdateQuery(const char *query, ExecuteUpdateRes &returnStructure);
+
+ int compat_InitUpdate();
+
+ int compat_StartInsertTransMDD(const char *domain, int typeLength, const char *typeName);
+
+ int compat_InsertTile(int persistent, RPCMarray*);
+
+ int compat_EndInsertMDD(int persistent);
+
+ int compat_GetTypeStructure(const char *typeName, int typeType, char* &typeStructure);
+
+ int compat_StartInsertPersMDD(const char *collName, r_Minterval &mddDomain, int typeLength, const char *typeName, r_OId &oid);
+
+ int compat_InsertMDD(const char *collName, RPCMarray *rpcMarray, const char *typeName, r_OId &oid);
+
+ int compat_InsertCollection(const char *collName, const char *typeName, r_OId &oid);
+
+ int compat_DeleteCollByName(const char *collName);
+
+ int compat_DeleteObjByOId(r_OId &oid);
+
+ int compat_RemoveObjFromColl(const char *collName, r_OId &oid);
+
+ int compat_GetCollectionByName(const char* collName, char* &typeName, char* &typeStructure, r_OId &oid);
+
+ int compat_GetCollectionByName(r_OId oid, char* &typeName, char* &typeStructure, char* &collName);
+
+ int compat_GetCollectionOidsByName(const char* collName, char* &typeName, char* &typeStructure, r_OId &oid, RPCOIdEntry* &oidTable, unsigned int &oidTableSize);
+
+ int compat_GetCollectionOidsByOId(r_OId oid, char* &typeName, char* &typeStructure, RPCOIdEntry* &oidTable, unsigned int &oidTableSize, char* &collName);
+
+ int compat_GetObjectType(r_OId &oid, unsigned short &objType);
+
+ int compat_SetTransferFormat(int format, const char* params);
+
+ int compat_SetStorageFormat(int format, const char* params);
+
+
+ r_OId createCollection(const char* collName, const char* collTypeName);
+
+ r_OId createMDD(const char* collName, const char* mddTypeName, const char* definitionDomain, const char* tileDomain, bool rcindex);
+
+ void extendMDD(r_OId mddOId, const char *stripeDomain, const char* tileDomain);
+
+ vector<r_Minterval> getTileDomains(r_OId mddOId, const char *stripeDomain);
+
+ };
+#endif
diff --git a/server/rasserver_main.cc b/server/rasserver_main.cc
new file mode 100644
index 0000000..adaaa8c
--- /dev/null
+++ b/server/rasserver_main.cc
@@ -0,0 +1,360 @@
+/*
+* This file is part of rasdaman community.
+*
+* Rasdaman community is free software: you can redistribute it and/or modify
+* it under the terms of the GNU General Public License as published by
+* the Free Software Foundation, either version 3 of the License, or
+* (at your option) any later version.
+*
+* Rasdaman community is distributed in the hope that it will be useful,
+* but WITHOUT ANY WARRANTY; without even the implied warranty of
+* MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
+* GNU General Public License for more details.
+*
+* You should have received a copy of the GNU General Public License
+* along with rasdaman community. If not, see <http://www.gnu.org/licenses/>.
+*
+* Copyright 2003, 2004, 2005, 2006, 2007, 2008, 2009 Peter Baumann /
+rasdaman GmbH.
+*
+* For more information please see <http://www.rasdaman.org>
+* or contact Peter Baumann via <baumann@rasdaman.com>.
+*/
+/*************************************************************
+ *
+ *
+ * PURPOSE:
+ *
+ *
+ * COMMENTS:
+ *
+ ************************************************************/
+
+using namespace std;
+
+#ifndef RMANVERSION
+#error "Please specify RMANVERSION variable!"
+#endif
+
+#ifndef COMPDATE
+#error "Please specify the COMPDATE variable!"
+/*
+COMPDATE=`date +"%d.%m.%Y %H:%M:%S"`
+
+and -DCOMPDATE="\"$(COMPDATE)\"" when compiling
+*/
+#endif
+
+
+#ifdef EARLY_TEMPLATE
+#define __EXECUTABLE__
+#ifdef __GNUG__
+#include "template_inst.hh"
+#endif
+#endif
+
+#include <iostream>
+#include <netdb.h>
+#include <sys/stat.h>
+#include <unistd.h>
+#include <string>
+
+#include "globals.hh" // DEFAULT_PORT
+#include "raslib/rmdebug.hh"
+#include "servercomm/httpserver.hh"
+#include "storagemgr/sstoragelayout.hh"
+#include <signal.h>
+
+RMINITGLOBALS('C');
+
+#include "rasserver_config.hh"
+#include "rnprotocol/rnpserver.hh"
+
+// from some unknown location the debug-srv.hh guard seems to be defined already, so get rid of it -- PB 2005-jan-10
+#undef DEBUG_HH
+#define DEBUG_MAIN debug_main
+#include "debug-srv.hh"
+
+
+bool initialization();
+
+extern int globalOptimizationLevel = 4;
+extern unsigned long maxTransferBufferSize = 4000000;
+extern char* dbSchema = 0;
+extern int noTimeOut = 0;
+
+// here the id string for connecting to the RDBMS is stored (used by rel* modules).
+// FIXME: bad hack -- PB 2003-oct-12
+char globalConnectId[256];
+int globalHTTPPort;
+// do we allow for User-Defined Functions? (aka rasql routines)
+bool udfEnabled = true;
+
+// drop client after 5 minutes of no alive signal
+// can be changed via cmd line parameter
+unsigned long clientTimeOut = CLIENT_TIMEOUT;
+
+// server management every 2 minutes
+unsigned long managementInterval = 120;
+
+const char* rasmgrHost = 0;
+int rasmgrPort = DEFAULT_PORT;
+const char* serverName = 0;
+int serverListenPort = 0;
+
+int main ( int argc, char** argv )
+{
+ SET_OUTPUT( true ); // enable debug output, if compiled so
+ ENTER( "rasserver.main()" );
+
+ //print startup text (this line will still go into forking rasmgr's log!)
+ cout << "Spawned rasserver v" << RMANVERSION / 1000. << " on base DBMS " << BASEDBSTRING << " -- generated on " << COMPDATE << "." << endl;
+
+ if(configuration.parseCommandLine(argc, argv) == false)
+ {
+ RMInit::logOut << "Error: cannot parse command line." << endl;
+ LEAVE( "rasserver.main(): Error parsing command line." );
+ return -1;
+ }
+
+ RMInit::logOut << "rasserver: rasdaman server v" << RMANVERSION / 1000. << " on base DBMS " << BASEDBSTRING << " -- generated on " << COMPDATE << "." << endl;
+ std::cout << " Copyright 2003, 2004, 2005, 2006, 2007, 2008, 2009 Peter Baumann rasdaman GmbH." << std::endl
+ << "Rasdaman community is free software: you can redistribute it and/or modify "
+ "it under the terms of the GNU General Public License as published by "
+ "the Free Software Foundation, either version 3 of the License, or "
+ "(at your option) any later version. \n"
+ "Rasdaman community is distributed in the hope that it will be useful, "
+ "but WITHOUT ANY WARRANTY; without even the implied warranty of "
+ "MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the "
+ "GNU General Public License for more details. \n\n";
+
+ RMInit::logOut << "This program contains software which is in the public domain:" << endl;
+ RMInit::logOut << " zlib 1.1.4 (C) 1995-1998 Jean-loup Gailly and Mark Adler" << endl;
+ RMInit::logOut << " libpng 1.2.1 (C) 2002 Glenn Randers-Pehrson" << endl;
+ RMInit::logOut << " libtiff 3.8.0 (C) 1988-1997 Sam Leffler, (C) 1991-1997 Silicon Graphics, Inc." << endl;
+ RMInit::logOut << " libjpeg 6b (C) 1991-1998, Thomas G. Lane." << endl;
+ RMInit::logOut << " openssl 0.96c (C) 1998-2002 The OpenSSL Project, (C) 1995-1998 Eric A. Young, Tim J. Hudson" << endl;
+
+ if(initialization() == false )
+ {
+ RMInit::logOut << "Error during initialization. aborted." << endl;
+ LEAVE( "rasserver.main(): Error during initialization." );
+ return -1;
+ }
+
+ //
+ // body rasserver
+ //
+
+ RMInit::logOut << "Installing signal handler for ignoring broken pipe signal..." << flush;
+ signal( SIGPIPE, SIG_IGN );
+ RMInit::logOut << "ok" << endl;
+
+ int returnCode = 0;
+ ServerComm* server = NULL;
+
+ try
+ {
+ TALK( "selecting server type..." );
+
+ if(configuration.isRnpServer())
+ {
+ TALK( "startRnpServer()..." );
+ startRnpServer();
+ TALK( "startRnpServer() done." );
+ }
+ else if(configuration.isHttpServer())
+ {
+ TALK( "initializing HttpServer()..." );
+ server = new HttpServer( clientTimeOut, managementInterval, serverListenPort, (char*)rasmgrHost, rasmgrPort,(char*)serverName);
+ }
+ else
+ {
+ TALK( "initializing ServerComm() (ie: RPC)..." );
+ server = new ServerComm( clientTimeOut, managementInterval, serverListenPort, (char*)rasmgrHost, rasmgrPort,(char*)serverName);
+ }
+
+ // in case of HTTP or RPC server: launch previously generated object
+ if(server)
+ {
+ TALK( "server->startRpcServer()..." );
+ server->startRpcServer();
+ TALK( "server->startRpcServer() done." );
+ }
+ }
+ catch ( r_Error& errorObj )
+ {
+ TALK( "Error: encountered " << errorObj.get_errorno() << ": " << errorObj.what() );
+ RMInit::logOut << "Error: encountered " << errorObj.get_errorno() << ": " << errorObj.what() << endl;
+// we never write to stdout (= rasmgr log file), so we don't need this -- PB 2003-nov-24
+#if 0
+ if(!configuration.isLogToStdOut())
+ {
+ RMInit::logOut << "Error: encountered " << errorObj.get_errorno() << ": " << errorObj.what() << endl;
+ }
+#endif // 0
+ returnCode = -1;
+ }
+ catch(...)
+ {
+ TALK( "rasserver: general exception" );
+ RMInit::logOut << "rasserver: general exception" << endl;
+// we never write to stdout (= rasmgr log file), so we don't need this -- PB 2003-nov-24
+#if 0
+ if(!configuration.isLogToStdOut())
+ {
+ RMInit::logOut << "rasserver: general exception" << endl;
+ }
+#endif
+ returnCode = -1;
+ }
+
+ if(server)
+ delete server;
+ server = NULL;
+
+ if( dbSchema )
+ free( dbSchema );
+ dbSchema = NULL;
+
+ LEAVE( "rasserver.main(): -> " << returnCode );
+ return returnCode;
+}
+
+bool initialization()
+{
+ serverName = configuration.getServerName();
+ accessControl.setServerName(serverName);
+
+ serverListenPort = globalHTTPPort = configuration.getListenPort();
+
+ RMInit::logOut<<"Server "<< serverName << " of type ";
+
+ if(configuration.isRnpServer())
+ RMInit::logOut << "RNP, listening on port " << serverListenPort << flush;
+ else if(configuration.isHttpServer())
+ RMInit::logOut << "HTTP, listening on port " << serverListenPort << flush;
+ else
+ RMInit::logOut << "RPC, registered with prognum 0x" << hex <<serverListenPort << dec << flush;
+
+ // globalConnectId = configuration.getDbConnectionID();
+ strcpy(globalConnectId,configuration.getDbConnectionID());
+ RMInit::logOut << ", connecting to " << BASEDBSTRING << " as '" << globalConnectId << "'." << endl;
+
+// we never write to stdout (= rasmgr log file), so we don't need this -- PB 2003-nov-24
+#if 0
+ if(!configuration.isLogToStdOut())
+ {
+ RMInit::logOut<<"Server "<< serverName << " of type ";
+ if(configuration.isRnpServer())
+ RMInit::logOut << "RNP, listening on port " << serverListenPort << endl;
+ else if(configuration.isHttpServer())
+ RMInit::logOut << "HTTP, listening on port " << serverListenPort << endl;
+ else
+ RMInit::logOut << "RPC, registered with prognum 0x" << hex <<serverListenPort << dec << endl;
+ }
+#endif // 0
+
+ rasmgrHost = configuration.getRasmgrHost();
+ rasmgrPort = configuration.getRasmgrPort();
+
+ RMInit::logOut << "Verifying rasmgr host name: " << rasmgrHost << "...";
+// we don't write to stdout (=rasmgr log), so no need to duplicate -- PB 2003-nov-24
+#if 0
+ if(!configuration.isLogToStdOut())
+ RMInit::logOut << "Verifying RasMGR host name: " << rasmgrHost << "...";
+#endif // 0
+ if(!gethostbyname(rasmgrHost))
+ {
+ RMInit::logOut << "failed" << endl;
+ if(!configuration.isLogToStdOut()) RMInit::logOut << "failed" << endl;
+ return false;
+ }
+ RMInit::logOut << "ok" << endl;
+// we don't write to stdout (=rasmgr log), so no need to duplicate -- PB 2003-nov-24
+#if 0
+ if(!configuration.isLogToStdOut())
+ RMInit::logOut << " ok" << endl;
+#endif // 0
+
+ globalOptimizationLevel = configuration.getDefaultOptimizationLevel();
+
+ maxTransferBufferSize = configuration.getMaxTransferBufferSize();
+
+ clientTimeOut = configuration.getTimeout();
+ if(clientTimeOut == 0)
+ noTimeOut = 1;
+
+ managementInterval = clientTimeOut/4;
+
+#ifdef RMANDEBUG
+ //tilesize
+ StorageLayout::DefaultTileSize = configuration.getDefaultTileSize();
+ RMInit::logOut << "Tile size set to : " << StorageLayout::DefaultTileSize << endl;
+
+ //pctmin
+ StorageLayout::DefaultMinimalTileSize = configuration.getDefaultPCTMin();
+ RMInit::logOut << "PCTMin set to : " << StorageLayout::DefaultMinimalTileSize << endl;
+
+ //pctmax
+ StorageLayout::DefaultPCTMax = configuration.getDefaultPCTMax();
+ RMInit::logOut << "PCTMax set to : " << StorageLayout::DefaultPCTMax << endl;
+
+ //indexsize
+ StorageLayout::DefaultIndexSize = configuration.getDefaultIndexSize();
+ RMInit::logOut << "IndexSize set to : " << StorageLayout::DefaultIndexSize << endl;
+
+ RManDebug = configuration.getDebugLevel();
+ RMInit::logOut<<"Debug level: " << RManDebug << endl;
+
+ try
+ {
+ StorageLayout::DefaultTileConfiguration = r_Minterval(configuration.getDefaultTileConfig());
+ }
+ catch(r_Error& err)
+ {
+ RMInit::logOut << "Error converting " << configuration.getDefaultTileConfig() << " to r_Minterval" << endl;
+ RMInit::logOut << "Error " << err.get_errorno() << " : " << err.what() << endl;
+ if(!configuration.isLogToStdOut())
+ {
+ RMInit::logOut << "Error converting " << configuration.getDefaultTileConfig() << " to r_Minterval" << endl;
+ RMInit::logOut << "Error " << err.get_errorno() << " : " << err.what() << endl;
+ }
+ return false;
+ }
+ RMInit::logOut << "Default Tile Conf: " << StorageLayout::DefaultTileConfiguration << endl;
+
+ // Tiling
+ r_Tiling_Scheme tmpTS=get_tiling_scheme_from_name(configuration.getTilingScheme());
+
+ if(tmpTS != r_Tiling_Scheme_NUMBER)
+ StorageLayout::DefaultTilingScheme = tmpTS;
+
+ if((tmpTS != r_NoTiling) && (tmpTS != r_RegularTiling))
+ {
+ RMInit::logOut << "Error: unsupported tiling strategy: " << configuration.getTilingScheme() << endl;
+ if(configuration.isLogToStdOut())
+ {
+ RMInit::logOut << "Error: unsupported tiling strategy: " << configuration.getTilingScheme() << endl;
+ }
+ return false;
+ }
+
+ //retiling enabled only if tiling scheme is regular tiling
+ RMInit::tiling = (tmpTS == r_RegularTiling);
+ RMInit::logOut << "Default Tiling : " << StorageLayout::DefaultTilingScheme << endl;
+
+ // Index
+ r_Index_Type tmpIT = get_index_type_from_name(configuration.getIndexType());
+ if ( tmpIT != r_Index_Type_NUMBER)
+ StorageLayout::DefaultIndexType = tmpIT;
+ RMInit::logOut << "Default Index : " << StorageLayout::DefaultIndexType << endl;
+
+ //use tilecontainer
+ RMInit::useTileContainer = configuration.useTileContainer();
+ RMInit::logOut << "Use Tile Container: " << RMInit::useTileContainer << endl;
+#endif
+
+ return true;
+}
+
diff --git a/server/template_inst.hh b/server/template_inst.hh
new file mode 100644
index 0000000..7c5a2b8
--- /dev/null
+++ b/server/template_inst.hh
@@ -0,0 +1,132 @@
+/*
+* This file is part of rasdaman community.
+*
+* Rasdaman community is free software: you can redistribute it and/or modify
+* it under the terms of the GNU General Public License as published by
+* the Free Software Foundation, either version 3 of the License, or
+* (at your option) any later version.
+*
+* Rasdaman community is distributed in the hope that it will be useful,
+* but WITHOUT ANY WARRANTY; without even the implied warranty of
+* MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
+* GNU General Public License for more details.
+*
+* You should have received a copy of the GNU General Public License
+* along with rasdaman community. If not, see <http://www.gnu.org/licenses/>.
+*
+* Copyright 2003, 2004, 2005, 2006, 2007, 2008, 2009 Peter Baumann /
+rasdaman GmbH.
+*
+* For more information please see <http://www.rasdaman.org>
+* or contact Peter Baumann via <baumann@rasdaman.com>.
+*/
+//for rb_tree, select1st
+#include <ext/functional>
+#include <ext/rb_tree>
+#include <vector>
+#include <utility>
+#include <memory>
+
+#if(__GNUC__==2 &&__GNUC_MINOR__==95)
+using std::rb_tree;
+using std::select1st;
+#else
+using __gnu_cxx::rb_tree;
+using __gnu_cxx::select1st;
+#endif
+
+using std::vector;
+using std::pair;
+
+// commented by Constantin Jucovschi (gcc 3.4+ no longer supports __default_alloc_template)
+//using std::__default_alloc_template;
+using std::fill_n;
+
+#include "qlparser/symtab.hh"
+
+#include "raslib/attribute.hh"
+#include "raslib/itertype.hh"
+#include "raslib/dlist.hh"
+
+#include "tilemgr/tile.hh"
+
+#include "indexmgr/keyobject.hh"
+
+#include "reladminif/dbref.hh"
+#include "reladminif/dbobjectiditerator.hh"
+
+#include "relblobif/blobtile.hh"
+#include "relblobif/dbtile.hh"
+#include "relblobif/inlinetile.hh"
+
+#include "relcatalogif/typeiterator.hh"
+#include "relcatalogif/settype.hh"
+#include "relcatalogif/structtype.hh"
+#include "relcatalogif/mddtype.hh"
+#include "relcatalogif/inlineminterval.hh"
+#include "relcatalogif/dbminterval.hh"
+
+#include "relindexif/dbtcindex.hh"
+#include "relindexif/hierindex.hh"
+#include "relindexif/dbrcindexds.hh"
+
+#include "relmddif/dbmddobj.hh"
+#include "relmddif/dbmddset.hh"
+
+#include "relstorageif/dbstoragelayout.hh"
+
+template class SymbolTable<int>;
+
+template class r_IterType<r_Attribute>;
+
+template class DBRef<DBHierIndex>;
+template class DBRef<DBRCIndexDS>;
+template class DBRef<DBTCIndex>;
+template class DBRef<BLOBTile>;
+template class DBRef<DBTile>;
+template class DBRef<InlineTile>;
+template class DBRef<DBMDDSet>;
+template class DBRef<DBMinterval>;
+template class DBRef<DBStorageLayout>;
+template bool operator< (const DBRef<DBMDDObj>&, const DBRef<DBMDDObj>&);
+
+//template TypeIterator<StructType>;
+//template TypeIterator<SetType>;
+template class TypeIterator<MDDType>;
+template class DBRef<DBMDDObj>;
+template class DBRef<DBObject>;
+
+template class DBObjectIdIterator<DBMDDObj>;
+template class DBObjectIterator<DBMDDObj>;
+template class DBObjectIterator<DBMDDSet>;
+template class DBObjectIterator<StructType>;
+template class DBObjectIterator<SetType>;
+template class DBRef<StructType>;
+template class DBRef<SetType>;
+template class DBRef<MDDType>;
+
+template std::ostream& operator<< (const vector<KeyObject>&, std::ostream&);
+template std::ostream& operator<< (std::ostream &, const vector<KeyObject>&);
+template std::ostream& operator << (std::ostream& os, const std::vector<double>& list);
+template std::ostream& operator << (std::ostream& os, const std::vector<r_Minterval>& list);
+
+template class rb_tree<OId, pair<OId const, DBMDDObj *>, select1st<pair<OId const, DBMDDObj *> >, less<OId> >;
+template class rb_tree<OId, pair<OId const, DBMinterval *>, select1st<pair<OId const, DBMinterval *> >, less<OId> >;
+template class rb_tree<OId, pair<OId const, DBRef<DBMDDObj> >, select1st<pair<OId const, DBRef<DBMDDObj> > >, less<OId> >;
+template class rb_tree<OId, pair<OId const, DBMDDSet *>, select1st<pair<OId const, DBMDDSet *> >, less<OId> >;
+template class rb_tree<OId, pair<OId const, MDDType *>, select1st<pair<OId const, MDDType *> >, less<OId> >;
+template class rb_tree<OId, pair<OId const, SetType *>, select1st<pair<OId const, SetType *> >, less<OId> >;
+template class rb_tree<OId, pair<OId const, StructType *>, select1st<pair<OId const, StructType *> >, less<OId> >;
+template class rb_tree<long, pair<long const, BLOBTile *>, select1st<pair<long const, BLOBTile *> >, less<long> >;
+template class rb_tree<long, pair<long const, InlineTile *>, select1st<pair<long const, InlineTile *> >, less<long> >;
+template class vector<BaseType const * >;
+template class vector<OId >;
+template class vector<Tile * >;
+template class vector<Type * >;
+template class vector<char * >;
+template class vector<char >;
+template class vector<r_Data_Format >;
+template class vector<unsigned int >;
+
+template class Tile ** fill_n<Tile **, unsigned int, Tile *>(Tile **, unsigned int, Tile * const &);
+
diff --git a/server/test/Makefile b/server/test/Makefile
new file mode 100644
index 0000000..f86365f
--- /dev/null
+++ b/server/test/Makefile
@@ -0,0 +1,59 @@
+# -*-Makefile-*-
+#
+# This file is part of rasdaman community.
+#
+# Rasdaman community is free software: you can redistribute it and/or modify
+# it under the terms of the GNU General Public License as published by
+# the Free Software Foundation, either version 3 of the License, or
+# (at your option) any later version.
+#
+# Rasdaman community is distributed in the hope that it will be useful,
+# but WITHOUT ANY WARRANTY; without even the implied warranty of
+# MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
+# GNU General Public License for more details.
+#
+# You should have received a copy of the GNU General Public License
+# along with rasdaman community. If not, see <http://www.gnu.org/licenses/>.
+#
+# Copyright 2003, 2004, 2005, 2006, 2007, 2008, 2009 Peter Baumann /
+# rasdaman GmbH.
+#
+# For more information please see <http://www.rasdaman.org>
+# or contact Peter Baumann via <baumann@rasdaman.com>. # Top Level makefile. This points to the various modules that have to be build
+# and/or deployed
+#
+# MAKEFILE FOR:
+# testing rasserver
+#
+# COMMENTS:
+# List environment dependencies, known bugs, specialities etc.
+#
+##################################################################
+#
+# This is just an example Makefile for a test program.
+# The dependency of the test program on the lib of the
+# corresponding module is in the Makefile of the module.
+#
+
+######################### Definitions ############################
+
+# standard include with general options
+include $(RMANBASE)/Makefile.inc
+
+# object files for test program
+TESTOBJS =
+# name of test program
+TESTPRG =
+
+########################### Targets ##############################
+
+$(TESTPRG): $(TESTOBJS) $(OBJS)
+ $(CXX) $(LDFLAGS) -o $@ $^
+
+.PHONY : clean
+clean:
+ -rm $(TESTOBJS)
+ -rm $(TESTPRG)
+
+######################## Dependencies ############################
+
diff --git a/server/test/test_mult-db-open.cc b/server/test/test_mult-db-open.cc
new file mode 100644
index 0000000..b803026
--- /dev/null
+++ b/server/test/test_mult-db-open.cc
@@ -0,0 +1,165 @@
+/*
+* This file is part of rasdaman community.
+*
+* Rasdaman community is free software: you can redistribute it and/or modify
+* it under the terms of the GNU General Public License as published by
+* the Free Software Foundation, either version 3 of the License, or
+* (at your option) any later version.
+*
+* Rasdaman community is distributed in the hope that it will be useful,
+* but WITHOUT ANY WARRANTY; without even the implied warranty of
+* MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
+* GNU General Public License for more details.
+*
+* You should have received a copy of the GNU General Public License
+* along with rasdaman community. If not, see <http://www.gnu.org/licenses/>.
+*
+* Copyright 2003, 2004, 2005, 2006, 2007, 2008, 2009 Peter Baumann /
+rasdaman GmbH.
+*
+* For more information please see <http://www.rasdaman.org>
+* or contact Peter Baumann via <baumann@rasdaman.com>.
+*/
+/*************************************************************
+ *
+ *
+ * PURPOSE:
+ *
+ *
+ * COMMENTS:
+ *
+ ************************************************************/
+
+static const char rcsid[] = "@(#)exportutils,ExportData: $Id: exporttif.cc,v 1.1 2003/12/27 21:44:18 rasdev Exp $";
+
+#ifndef RMANVERSION
+#error "Please specify RMANVERSION variable!"
+#endif
+
+#ifndef COMPDATE
+#error "Please specify the COMPDATE variable!"
+/*
+COMPDATE=`date +"%d.%m.%Y %H:%M:%S"`
+
+and -DCOMPDATE="\"$(COMPDATE)\"" when compiling
+*/
+#endif
+
+
+#ifdef EARLY_TEMPLATE
+#define __EXECUTABLE__
+#ifdef __GNUG__
+#include "raslib/template_inst.hh"
+#endif
+#endif
+
+#include <iostream>
+#include <cstdio>
+#include <cctype>
+
+using std::vector;
+using std::iterator;
+
+#if defined(SOLARIS)
+# include <strings.h>
+#else
+# include <cstring>
+#endif
+
+#include "mymalloc/mymalloc.h"
+
+// here is the main prog for allocating debug macro vars
+#define DEBUG_MAIN
+#include "debug.hh"
+
+#include "rasodmg/transaction.hh"
+#include "rasodmg/database.hh"
+
+
+// global variables and default settings
+// -------------------------------------
+
+r_Database db;
+r_Transaction ta;
+
+const char* server = DEFAULT_SERV;
+unsigned int port = DEFAULT_PORT;
+const char* database = DEFAULT_DB;
+const char* user = DEFAULT_USER;
+const char* passwd = DEFAULT_PASSWD;
+
+
+void
+openDatabase() throw (r_Error)
+{
+ ENTER( "openDatabase" );
+
+ if (! dbIsOpen)
+ {
+ cout << "Opening database " << database << " at " << server << ":" << port << "..." << flush;
+ db.set_servername(server, port);
+ db.set_useridentification( user, passwd);
+ TALK( "database was closed, opening database=" << database << ", server=" << server << ", port=" << port << ", user=" << user << ", passwd=" << passwd << "..." );
+ db.open( database );
+ TALK( "done" );
+ dbIsOpen = true;
+ cout << "ok" << endl << flush;
+ }
+
+ LEAVE( "openDatabase" );
+}
+
+void
+closeDatabase() throw (r_Error)
+{
+ ENTER( "closeDatabase" );
+
+ if (dbIsOpen)
+ {
+ TALK( "database was open, closing it" );
+ db.close();
+ dbIsOpen = false;
+ }
+
+ LEAVE( "closeDatabase" );
+ return;
+}
+
+
+int main(int argc, char** argv)
+{
+ SET_OUTPUT( false ); // inhibit unconditional debug output, await cmd line evaluation
+
+ int retval = EXIT_FAILURE;
+
+ cout << argv[0] << ": rasdaman test 'failure upon multiple db open' for rasdaman v" << RMANVERSION/1000 << " -- generated on " << COMPDATE << endl;
+
+ try
+ {
+ openDatabase();
+
+ closeDatabase();
+
+ retval = EXIT_SUCCESS;
+ }
+ catch (ExportError& e)
+ {
+ cout << argv[0] << ": " << e.what() << endl;
+ retval = EXIT_FAILURE;
+ }
+ catch (const r_Error& e)
+ {
+ cout << argv[0] << ": rasdaman error " << e.get_errorno() << ": " << e.what() << endl;
+ retval = EXIT_FAILURE;
+ }
+ catch (...)
+ {
+ cout << argv[0] << ": panic: unexpected internal exception." << endl;
+ retval = EXIT_FAILURE;
+ }
+
+ cout << argv[0] << " done." << endl;
+
+ return retval;
+}
+