int runDbTests(int argc, char** argv) { frameworkGlobalParams.perfHist = 1; frameworkGlobalParams.seed = time( 0 ); frameworkGlobalParams.runsPerTest = 1; Client::initThread("testsuite"); acquirePathLock(); srand( (unsigned) frameworkGlobalParams.seed ); printGitVersion(); printOpenSSLVersion(); printSysInfo(); FileAllocator::get()->start(); dur::startup(); TestWatchDog twd; twd.go(); // set tlogLevel to -1 to suppress MONGO_TLOG(0) output in a test program tlogLevel = -1; int ret = ::mongo::unittest::Suite::run(frameworkGlobalParams.suites, frameworkGlobalParams.filter, frameworkGlobalParams.runsPerTest); #if !defined(_WIN32) && !defined(__sunos__) flock( lockFile, LOCK_UN ); #endif cc().shutdown(); dbexit( (ExitCode)ret ); // so everything shuts down cleanly return ret; }
void _initAndListen(int listenPort, const char *appserverLoc = null) { #if !defined(_WIN32) pid_t pid = 0; pid = getpid(); #else int pid=0; #endif bool is32bit = sizeof(int*) == 4; log() << "Mongo DB : starting : pid = " << pid << " port = " << cmdLine.port << " dbpath = " << dbpath << " master = " << master << " slave = " << (int) slave << " " << ( is32bit ? "32" : "64" ) << "-bit " << endl; show_32_warning(); stringstream ss; ss << "dbpath (" << dbpath << ") does not exist"; massert( ss.str().c_str(), boost::filesystem::exists( dbpath ) ); acquirePathLock(); theFileAllocator().start(); BOOST_CHECK_EXCEPTION( clearTmpFiles() ); clearTmpCollections(); if ( opLogging ) log() << "opLogging = " << opLogging << endl; _oplog.init(); mms.go(); #if 0 { stringstream indexpath; indexpath << dbpath << "/indexes.dat"; RecCache::tempStore.init(indexpath.str().c_str(), BucketSize); } #endif if ( useJNI ) { ScriptEngine::setup(); } repairDatabases(); if ( shouldRepairDatabases ) return; /* this is for security on certain platforms */ srand(curTimeMicros() ^ startupSrandTimer.micros()); listen(listenPort); // listen() will return when exit code closes its socket. while( 1 ) sleepsecs( 100 ); }
void _initAndListen(int listenPort ) { Client::initThread("initandlisten"); Database::_openAllFiles = false; Logstream::get().addGlobalTee( new RamLog("global") ); bool is32bit = sizeof(int*) == 4; { #if !defined(_WIN32) pid_t pid = getpid(); #else DWORD pid=GetCurrentProcessId(); #endif Nullstream& l = log(); l << "MongoDB starting : pid=" << pid << " port=" << cmdLine.port << " dbpath=" << dbpath; if( replSettings.master ) l << " master=" << replSettings.master; if( replSettings.slave ) l << " slave=" << (int) replSettings.slave; l << ( is32bit ? " 32" : " 64" ) << "-bit host=" << getHostNameCached() << endl; } DEV log() << "_DEBUG build (which is slower)" << endl; show_warnings(); log() << mongodVersion() << endl; printGitVersion(); printSysInfo(); printCommandLineOpts(); { stringstream ss; ss << endl; ss << "*********************************************************************" << endl; ss << " ERROR: dbpath (" << dbpath << ") does not exist." << endl; ss << " Create this directory or give existing directory in --dbpath." << endl; ss << " See http://www.mongodb.org/display/DOCS/Starting+and+Stopping+Mongo" << endl; ss << "*********************************************************************" << endl; uassert( 10296 , ss.str().c_str(), boost::filesystem::exists( dbpath ) ); } { stringstream ss; ss << "repairpath (" << repairpath << ") does not exist"; uassert( 12590 , ss.str().c_str(), boost::filesystem::exists( repairpath ) ); } acquirePathLock(forceRepair); boost::filesystem::remove_all( dbpath + "/_tmp/" ); FileAllocator::get()->start(); MONGO_ASSERT_ON_EXCEPTION_WITH_MSG( clearTmpFiles(), "clear tmp files" ); dur::startup(); if( cmdLine.durOptions & CmdLine::DurRecoverOnly ) return; // comes after getDur().startup() because this reads from the database clearTmpCollections(); checkIfReplMissingFromCommandLine(); Module::initAll(); if ( scriptingEnabled ) { ScriptEngine::setup(); globalScriptEngine->setCheckInterruptCallback( jsInterruptCallback ); globalScriptEngine->setGetInterruptSpecCallback( jsGetInterruptSpecCallback ); } repairDatabasesAndCheckVersion(); /* we didn't want to pre-open all files for the repair check above. for regular operation we do for read/write lock concurrency reasons. */ Database::_openAllFiles = true; if ( shouldRepairDatabases ) return; /* this is for security on certain platforms (nonce generation) */ srand((unsigned) (curTimeMicros() ^ startupSrandTimer.micros())); snapshotThread.go(); d.clientCursorMonitor.go(); PeriodicTask::theRunner->go(); startTTLBackgroundJob(); #ifndef _WIN32 CmdLine::launchOk(); #endif if( !noauth ) { // open admin db in case we need to use it later. TODO this is not the right way to // resolve this. Client::WriteContext c("admin",dbpath,false); } listen(listenPort); // listen() will return when exit code closes its socket. exitCleanly(EXIT_NET_ERROR); }
int Tool::main( int argc , char ** argv, char ** envp ) { setupSignalHandlers(true); static StaticObserver staticObserver; mongo::runGlobalInitializersOrDie(argc, argv, envp); // hide password from ps output for (int i=0; i < (argc-1); ++i) { if (!strcmp(argv[i], "-p") || !strcmp(argv[i], "--password")) { char* arg = argv[i+1]; while (*arg) { *arg++ = 'x'; } } } if (!toolGlobalParams.useDirectClient) { if (toolGlobalParams.noconnection) { // do nothing } else { string errmsg; ConnectionString cs = ConnectionString::parse(toolGlobalParams.connectionString, errmsg); if ( ! cs.isValid() ) { toolError() << "invalid hostname [" << toolGlobalParams.connectionString << "] " << errmsg << std::endl; ::_exit(-1); } _conn = cs.connect( errmsg ); if ( ! _conn ) { toolError() << "couldn't connect to [" << toolGlobalParams.connectionString << "] " << errmsg << std::endl; ::_exit(-1); } toolInfoOutput() << "connected to: " << toolGlobalParams.connectionString << std::endl; } } else { verify( lastError.get( true ) ); Client::initThread("tools"); _conn = new DBDirectClient(); storageGlobalParams.dbpath = toolGlobalParams.dbpath; try { acquirePathLock(); } catch ( DBException& ) { toolError() << std::endl << "If you are running a mongod on the same " "path you should connect to that instead of direct data " "file access" << std::endl << std::endl; dbexit( EXIT_FS ); ::_exit(EXIT_FAILURE); } FileAllocator::get()->start(); dur::startup(); } int ret = -1; try { if (!toolGlobalParams.useDirectClient && !toolGlobalParams.noconnection) auth(); ret = run(); } catch ( DBException& e ) { toolError() << "assertion: " << e.toString() << std::endl; ret = -1; } catch(const boost::filesystem::filesystem_error &fse) { /* https://jira.mongodb.org/browse/SERVER-2904 Simple tools that don't access the database, such as bsondump, aren't throwing DBExceptions, but are throwing boost exceptions. The currently available set of error codes don't seem to match boost documentation. boost::filesystem::not_found_error (from http://www.boost.org/doc/libs/1_31_0/libs/filesystem/doc/exception.htm) doesn't seem to exist in our headers. Also, fse.code() isn't boost::system::errc::no_such_file_or_directory when this happens, as you would expect. And, determined from experimentation that the command-line argument gets turned into "\\?" instead of "/?" !!! */ #if defined(_WIN32) if (/*(fse.code() == boost::system::errc::no_such_file_or_directory) &&*/ (fse.path1() == "\\?")) printHelp(cerr); else #endif // _WIN32 toolError() << "error: " << fse.what() << std::endl; ret = -1; } if ( currentClient.get() ) currentClient.get()->shutdown(); if (toolGlobalParams.useDirectClient) dbexit( EXIT_CLEAN ); fflush(stdout); fflush(stderr); ::_exit(ret); }
void _initAndListen(int listenPort ) { Client::initThread("initandlisten"); bool is32bit = sizeof(int*) == 4; { ProcessId pid = ProcessId::getCurrent(); LogstreamBuilder l = log(); l << "MongoDB starting : pid=" << pid << " port=" << serverGlobalParams.port << " dbpath=" << storageGlobalParams.dbpath; if( replSettings.master ) l << " master=" << replSettings.master; if( replSettings.slave ) l << " slave=" << (int) replSettings.slave; l << ( is32bit ? " 32" : " 64" ) << "-bit host=" << getHostNameCached() << endl; } DEV log() << "_DEBUG build (which is slower)" << endl; logStartupWarnings(); #if defined(_WIN32) printTargetMinOS(); #endif logProcessDetails(); { stringstream ss; ss << endl; ss << "*********************************************************************" << endl; ss << " ERROR: dbpath (" << storageGlobalParams.dbpath << ") does not exist." << endl; ss << " Create this directory or give existing directory in --dbpath." << endl; ss << " See http://dochub.mongodb.org/core/startingandstoppingmongo" << endl; ss << "*********************************************************************" << endl; uassert(10296, ss.str().c_str(), boost::filesystem::exists(storageGlobalParams.dbpath)); } { stringstream ss; ss << "repairpath (" << storageGlobalParams.repairpath << ") does not exist"; uassert(12590, ss.str().c_str(), boost::filesystem::exists(storageGlobalParams.repairpath)); } // TODO check non-journal subdirs if using directory-per-db checkReadAhead(storageGlobalParams.dbpath); acquirePathLock(mongodGlobalParams.repair); boost::filesystem::remove_all(storageGlobalParams.dbpath + "/_tmp/"); FileAllocator::get()->start(); // TODO: This should go into a MONGO_INITIALIZER once we have figured out the correct // dependencies. if (snmpInit) { snmpInit(); } MONGO_ASSERT_ON_EXCEPTION_WITH_MSG( clearTmpFiles(), "clear tmp files" ); dur::startup(); if (storageGlobalParams.durOptions & StorageGlobalParams::DurRecoverOnly) return; unsigned long long missingRepl = checkIfReplMissingFromCommandLine(); if (missingRepl) { log() << startupWarningsLog; log() << "** WARNING: mongod started without --replSet yet " << missingRepl << " documents are present in local.system.replset" << startupWarningsLog; log() << "** Restart with --replSet unless you are doing maintenance and no" << " other clients are connected." << startupWarningsLog; log() << "** The TTL collection monitor will not start because of this." << startupWarningsLog; log() << "** For more info see http://dochub.mongodb.org/core/ttlcollections" << startupWarningsLog; log() << startupWarningsLog; } if (mongodGlobalParams.scriptingEnabled) { ScriptEngine::setup(); globalScriptEngine->setCheckInterruptCallback( jsInterruptCallback ); globalScriptEngine->setGetCurrentOpIdCallback( jsGetCurrentOpIdCallback ); } // On replica set members we only clear temp collections on DBs other than "local" during // promotion to primary. On pure slaves, they are only cleared when the oplog tells them to. // The local DB is special because it is not replicated. See SERVER-10927 for more details. const bool shouldClearNonLocalTmpCollections = !(missingRepl || replSettings.usingReplSets() || replSettings.slave == SimpleSlave); repairDatabasesAndCheckVersion(shouldClearNonLocalTmpCollections); if (mongodGlobalParams.upgrade) return; uassertStatusOK(getGlobalAuthorizationManager()->initialize()); /* this is for security on certain platforms (nonce generation) */ srand((unsigned) (curTimeMicros() ^ startupSrandTimer.micros())); snapshotThread.go(); d.clientCursorMonitor.go(); PeriodicTask::startRunningPeriodicTasks(); if (missingRepl) { // a warning was logged earlier } else { startTTLBackgroundJob(); } #ifndef _WIN32 mongo::signalForkSuccess(); #endif if(getGlobalAuthorizationManager()->isAuthEnabled()) { // open admin db in case we need to use it later. TODO this is not the right way to // resolve this. Client::WriteContext c("admin", storageGlobalParams.dbpath); } authindex::configureSystemIndexes("admin"); getDeleter()->startWorkers(); // Starts a background thread that rebuilds all incomplete indices. indexRebuilder.go(); listen(listenPort); // listen() will return when exit code closes its socket. exitCleanly(EXIT_NET_ERROR); }
int runDbTests( int argc , char** argv , string default_dbpath ) { unsigned long long seed = time( 0 ); int runsPerTest = 1; string dbpathSpec; po::options_description shell_options("options"); po::options_description hidden_options("Hidden options"); po::options_description cmdline_options("Command line options"); po::positional_options_description positional_options; shell_options.add_options() ("help,h", "show this usage information") ("dbpath", po::value<string>(&dbpathSpec)->default_value(default_dbpath), "db data path for this test run. NOTE: the contents of this " "directory will be overwritten if it already exists") ("debug", "run tests with verbose output") ("list,l", "list available test suites") ("bigfiles", "use big datafiles instead of smallfiles which is the default") ("filter,f" , po::value<string>() , "string substring filter on test name" ) ("verbose,v", "verbose") ("dur", "enable journaling (currently the default)") ("nodur", "disable journaling") ("seed", po::value<unsigned long long>(&seed), "random number seed") ("runs", po::value<int>(&runsPerTest), "number of times to run each test") ("perfHist", po::value<unsigned>(&perfHist), "number of back runs of perf stats to display") ; hidden_options.add_options() ("suites", po::value< vector<string> >(), "test suites to run") ("nopreallocj", "disable journal prealloc") ; positional_options.add("suites", -1); cmdline_options.add(shell_options).add(hidden_options); po::variables_map params; int command_line_style = (((po::command_line_style::unix_style ^ po::command_line_style::allow_guessing) | po::command_line_style::allow_long_disguise) ^ po::command_line_style::allow_sticky); try { po::store(po::command_line_parser(argc, argv).options(cmdline_options). positional(positional_options). style(command_line_style).run(), params); po::notify(params); } catch (po::error &e) { cout << "ERROR: " << e.what() << endl << endl; show_help_text(argv[0], shell_options); return EXIT_BADOPTIONS; } if (params.count("help")) { show_help_text(argv[0], shell_options); return EXIT_CLEAN; } bool nodur = false; if( params.count("nodur") ) { nodur = true; cmdLine.dur = false; } if( params.count("dur") || cmdLine.dur ) { cmdLine.dur = true; } if( params.count("nopreallocj") ) { cmdLine.preallocj = false; } if (params.count("debug") || params.count("verbose") ) { logger::globalLogDomain()->setMinimumLoggedSeverity(logger::LogSeverity::Debug(1)); } if (params.count("list")) { std::vector<std::string> suiteNames = mongo::unittest::getAllSuiteNames(); for ( std::vector<std::string>::const_iterator i = suiteNames.begin(); i != suiteNames.end(); ++i ) { std::cout << *i << std::endl; } return 0; } boost::filesystem::path p(dbpathSpec); /* remove the contents of the test directory if it exists. */ if (boost::filesystem::exists(p)) { if (!boost::filesystem::is_directory(p)) { cout << "ERROR: path \"" << p.string() << "\" is not a directory" << endl << endl; show_help_text(argv[0], shell_options); return EXIT_BADOPTIONS; } boost::filesystem::directory_iterator end_iter; for (boost::filesystem::directory_iterator dir_iter(p); dir_iter != end_iter; ++dir_iter) { boost::filesystem::remove_all(*dir_iter); } } else { boost::filesystem::create_directory(p); } string dbpathString = p.string(); dbpath = dbpathString.c_str(); cmdLine.prealloc = false; // dbtest defaults to smallfiles cmdLine.smallfiles = true; if( params.count("bigfiles") ) { cmdLine.dur = true; } cmdLine.oplogSize = 10 * 1024 * 1024; Client::initThread("testsuite"); acquirePathLock(); srand( (unsigned) seed ); printGitVersion(); printSysInfo(); DEV log() << "_DEBUG build" << endl; if( sizeof(void*)==4 ) log() << "32bit" << endl; log() << "random seed: " << seed << endl; if( time(0) % 3 == 0 && !nodur ) { if( !cmdLine.dur ) { cmdLine.dur = true; log() << "****************" << endl; log() << "running with journaling enabled to test that. dbtests will do this occasionally even if --dur is not specified." << endl; log() << "****************" << endl; } } FileAllocator::get()->start(); vector<string> suites; if (params.count("suites")) { suites = params["suites"].as< vector<string> >(); } string filter = ""; if ( params.count( "filter" ) ) { filter = params["filter"].as<string>(); } dur::startup(); if( debug && cmdLine.dur ) { log() << "_DEBUG: automatically enabling cmdLine.durOptions=8 (DurParanoid)" << endl; // this was commented out. why too slow or something? : cmdLine.durOptions |= 8; } TestWatchDog twd; twd.go(); // set tlogLevel to -1 to suppress MONGO_TLOG(0) output in a test program tlogLevel = -1; int ret = ::mongo::unittest::Suite::run(suites,filter,runsPerTest); #if !defined(_WIN32) && !defined(__sunos__) flock( lockFile, LOCK_UN ); #endif cc().shutdown(); dbexit( (ExitCode)ret ); // so everything shuts down cleanly return ret; }
int Suite::run( int argc , char** argv , string default_dbpath ) { unsigned long long seed = time( 0 ); string dbpathSpec; po::options_description shell_options("options"); po::options_description hidden_options("Hidden options"); po::options_description cmdline_options("Command line options"); po::positional_options_description positional_options; shell_options.add_options() ("help,h", "show this usage information") ("dbpath", po::value<string>(&dbpathSpec)->default_value(default_dbpath), "db data path for this test run. NOTE: the contents of this " "directory will be overwritten if it already exists") ("debug", "run tests with verbose output") ("list,l", "list available test suites") ("verbose,v", "verbose") ("seed", po::value<unsigned long long>(&seed), "random number seed") ; hidden_options.add_options() ("suites", po::value< vector<string> >(), "test suites to run") ; positional_options.add("suites", -1); cmdline_options.add(shell_options).add(hidden_options); po::variables_map params; int command_line_style = (((po::command_line_style::unix_style ^ po::command_line_style::allow_guessing) | po::command_line_style::allow_long_disguise) ^ po::command_line_style::allow_sticky); try { po::store(po::command_line_parser(argc, argv).options(cmdline_options). positional(positional_options). style(command_line_style).run(), params); po::notify(params); } catch (po::error &e) { cout << "ERROR: " << e.what() << endl << endl; show_help_text(argv[0], shell_options); return EXIT_BADOPTIONS; } if (params.count("help")) { show_help_text(argv[0], shell_options); return EXIT_CLEAN; } if (params.count("debug") || params.count("verbose") ) { logLevel = 1; } if (params.count("list")) { for ( map<string,Suite*>::iterator i = _suites->begin() ; i != _suites->end(); i++ ) cout << i->first << endl; return 0; } boost::filesystem::path p(dbpathSpec); /* remove the contents of the test directory if it exists. */ if (boost::filesystem::exists(p)) { if (!boost::filesystem::is_directory(p)) { cout << "ERROR: path \"" << p.string() << "\" is not a directory" << endl << endl; show_help_text(argv[0], shell_options); return EXIT_BADOPTIONS; } boost::filesystem::directory_iterator end_iter; for (boost::filesystem::directory_iterator dir_iter(p); dir_iter != end_iter; ++dir_iter) { boost::filesystem::remove_all(*dir_iter); } } else { boost::filesystem::create_directory(p); } string dbpathString = p.native_directory_string(); dbpath = dbpathString.c_str(); cmdLine.prealloc = false; cmdLine.smallfiles = true; cmdLine.oplogSize = 10 * 1024 * 1024; Client::initThread("testsuite"); acquirePathLock(); srand( (unsigned) seed ); printGitVersion(); printSysInfo(); out() << "random seed: " << seed << endl; theFileAllocator().start(); vector<string> suites; if (params.count("suites")) { suites = params["suites"].as< vector<string> >(); } int ret = run(suites); #if !defined(_WIN32) && !defined(__sunos__) flock( lockFile, LOCK_UN ); #endif cc().shutdown(); dbexit( (ExitCode)ret ); // so everything shuts down cleanly return ret; }
void _initAndListen(int listenPort, const char *appserverLoc = NULL) { bool is32bit = sizeof(int*) == 4; { #if !defined(_WIN32) pid_t pid = getpid(); #else DWORD pid=GetCurrentProcessId(); #endif Nullstream& l = log(); l << "MongoDB starting : pid=" << pid << " port=" << cmdLine.port << " dbpath=" << dbpath; if( replSettings.master ) l << " master=" << replSettings.master; if( replSettings.slave ) l << " slave=" << (int) replSettings.slave; l << ( is32bit ? " 32" : " 64" ) << "-bit " << endl; } DEV log() << "_DEBUG build (which is slower)" << endl; show_warnings(); log() << mongodVersion() << endl; printGitVersion(); printSysInfo(); { stringstream ss; ss << "dbpath (" << dbpath << ") does not exist"; uassert( 10296 , ss.str().c_str(), boost::filesystem::exists( dbpath ) ); } { stringstream ss; ss << "repairpath (" << repairpath << ") does not exist"; uassert( 12590 , ss.str().c_str(), boost::filesystem::exists( repairpath ) ); } acquirePathLock(); remove_all( dbpath + "/_tmp/" ); theFileAllocator().start(); BOOST_CHECK_EXCEPTION( clearTmpFiles() ); Client::initThread("initandlisten"); _diaglog.init(); clearTmpCollections(); Module::initAll(); #if 0 { stringstream indexpath; indexpath << dbpath << "/indexes.dat"; RecCache::tempStore.init(indexpath.str().c_str(), BucketSize); } #endif if ( useJNI ) { ScriptEngine::setup(); globalScriptEngine->setCheckInterruptCallback( jsInterruptCallback ); } repairDatabases(); /* we didn't want to pre-open all fiels for the repair check above. for regular operation we do for read/write lock concurrency reasons. */ Database::_openAllFiles = true; if ( shouldRepairDatabases ) return; /* this is for security on certain platforms (nonce generation) */ srand((unsigned) (curTimeMicros() ^ startupSrandTimer.micros())); snapshotThread.go(); clientCursorMonitor.go(); if( !cmdLine._replSet.empty() ) { replSet = true; ReplSetCmdline *replSetCmdline = new ReplSetCmdline(cmdLine._replSet); boost::thread t( boost::bind( &startReplSets, replSetCmdline) ); } listen(listenPort); // listen() will return when exit code closes its socket. exitCleanly(EXIT_NET_ERROR); }
int Tool::main( int argc , char ** argv ){ static StaticObserver staticObserver; cmdLine.prealloc = false; boost::filesystem::path::default_name_check( boost::filesystem::no_check ); _name = argv[0]; /* using the same style as db.cpp */ int command_line_style = (((po::command_line_style::unix_style ^ po::command_line_style::allow_guessing) | po::command_line_style::allow_long_disguise) ^ po::command_line_style::allow_sticky); try { po::options_description all_options("all options"); all_options.add(*_options).add(*_hidden_options); po::store( po::command_line_parser( argc , argv ). options(all_options). positional( _positonalOptions ). style(command_line_style).run() , _params ); po::notify( _params ); } catch (po::error &e) { cerr << "ERROR: " << e.what() << endl << endl; printHelp(cerr); return EXIT_BADOPTIONS; } // hide password from ps output for (int i=0; i < (argc-1); ++i){ if (!strcmp(argv[i], "-p") || !strcmp(argv[i], "--password")){ char* arg = argv[i+1]; while (*arg){ *arg++ = 'x'; } } } if ( _params.count( "help" ) ){ printHelp(cout); return 0; } if ( _params.count( "verbose" ) ) { logLevel = 1; } for (string s = "vv"; s.length() <= 10; s.append("v")) { if (_params.count(s)) { logLevel = s.length(); } } preSetup(); bool useDirectClient = hasParam( "dbpath" ); if ( ! useDirectClient ) { _host = "127.0.0.1"; if ( _params.count( "host" ) ) _host = _params["host"].as<string>(); if ( _params.count( "port" ) ) _host += ':' + _params["port"].as<string>(); if ( _noconnection ){ // do nothing } else if ( _host.find( "," ) == string::npos ){ DBClientConnection * c = new DBClientConnection( _autoreconnect ); _conn = c; string errmsg; if ( ! c->connect( _host , errmsg ) ){ cerr << "couldn't connect to [" << _host << "] " << errmsg << endl; return -1; } } else { log(1) << "using pairing" << endl; DBClientPaired * c = new DBClientPaired(); _paired = true; _conn = c; if ( ! c->connect( _host ) ){ cerr << "couldn't connect to paired server: " << _host << endl; return -1; } } (_usesstdout ? cout : cerr ) << "connected to: " << _host << endl; } else { if ( _params.count( "directoryperdb" ) ) { directoryperdb = true; } assert( lastError.get( true ) ); Client::initThread("tools"); _conn = new DBDirectClient(); _host = "DIRECT"; static string myDbpath = getParam( "dbpath" ); dbpath = myDbpath.c_str(); try { acquirePathLock(); } catch ( DBException& e ){ cerr << endl << "If you are running a mongod on the same " "path you should connect to that instead of direct data " "file access" << endl << endl; dbexit( EXIT_CLEAN ); return -1; } theFileAllocator().start(); } if ( _params.count( "db" ) ) _db = _params["db"].as<string>(); if ( _params.count( "collection" ) ) _coll = _params["collection"].as<string>(); if ( _params.count( "username" ) ) _username = _params["username"].as<string>(); if ( _params.count( "password" ) && ( _password.empty() ) ) { _password = askPassword(); } if (_params.count("ipv6")) enableIPv6(); int ret = -1; try { ret = run(); } catch ( DBException& e ){ cerr << "assertion: " << e.toString() << endl; ret = -1; } if ( currentClient.get() ) currentClient->shutdown(); if ( useDirectClient ) dbexit( EXIT_CLEAN ); return ret; }
int runDbTests( int argc , char** argv , string default_dbpath ) { unsigned long long seed = time( 0 ); int runsPerTest = 1; string dbpathSpec; po::options_description shell_options("options"); po::options_description hidden_options("Hidden options"); po::options_description cmdline_options("Command line options"); po::positional_options_description positional_options; shell_options.add_options() ("help,h", "show this usage information") ("dbpath", po::value<string>(&dbpathSpec)->default_value(default_dbpath), "db data path for this test run. NOTE: the contents of this " "directory will be overwritten if it already exists") ("debug", "run tests with verbose output") ("list,l", "list available test suites") ("filter,f" , po::value<string>() , "string substring filter on test name" ) ("verbose,v", "be more verbose (include multiple times for more verbosity e.g. -vvvvv)") ("dur", "enable journaling (currently the default)") ("nodur", "disable journaling") ("seed", po::value<unsigned long long>(&seed), "random number seed") ("runs", po::value<int>(&runsPerTest), "number of times to run each test") ("perfHist", po::value<unsigned>(&perfHist), "number of back runs of perf stats to display") ; hidden_options.add_options() ("suites", po::value< vector<string> >(), "test suites to run") ; positional_options.add("suites", -1); /* support for -vv -vvvv etc. */ for (string s = "vv"; s.length() <= 10; s.append("v")) { hidden_options.add_options()(s.c_str(), "verbose"); } cmdline_options.add(shell_options).add(hidden_options); po::variables_map params; int command_line_style = (((po::command_line_style::unix_style ^ po::command_line_style::allow_guessing) | po::command_line_style::allow_long_disguise) ^ po::command_line_style::allow_sticky); try { po::store(po::command_line_parser(argc, argv).options(cmdline_options). positional(positional_options). style(command_line_style).run(), params); po::notify(params); } catch (po::error &e) { cout << "ERROR: " << e.what() << endl << endl; show_help_text(argv[0], shell_options); return EXIT_BADOPTIONS; } if (params.count("help")) { show_help_text(argv[0], shell_options); return EXIT_CLEAN; } if (params.count("debug") || params.count("verbose") ) { logLevel = 1; } for (string s = "vv"; s.length() <= 10; s.append("v")) { if (params.count(s)) { logLevel = s.length(); } } if (params.count("list")) { std::vector<std::string> suiteNames = mongo::unittest::getAllSuiteNames(); for ( std::vector<std::string>::const_iterator i = suiteNames.begin(); i != suiteNames.end(); ++i ) { std::cout << *i << std::endl; } return 0; } boost::filesystem::path p(dbpathSpec); /* remove the contents of the test directory if it exists. */ if (boost::filesystem::exists(p)) { if (!boost::filesystem::is_directory(p)) { cout << "ERROR: path \"" << p.string() << "\" is not a directory" << endl << endl; show_help_text(argv[0], shell_options); return EXIT_BADOPTIONS; } boost::filesystem::directory_iterator end_iter; for (boost::filesystem::directory_iterator dir_iter(p); dir_iter != end_iter; ++dir_iter) { boost::filesystem::remove_all(*dir_iter); } } else { boost::filesystem::create_directory(p); } string dbpathString = p.native_directory_string(); dbpath = dbpathString.c_str(); Client::initThread("testsuite"); acquirePathLock(); srand( (unsigned) seed ); printGitVersion(); printSysInfo(); DEV log() << "_DEBUG build" << endl; if( sizeof(void*)==4 ) log() << "32bit" << endl; log() << "random seed: " << seed << endl; vector<string> suites; if (params.count("suites")) { suites = params["suites"].as< vector<string> >(); } string filter = ""; if ( params.count( "filter" ) ) { filter = params["filter"].as<string>(); } mongo::setTxnCompleteHooks(&mongo::_txnCompleteHooks); storage::startup(); TestWatchDog twd; twd.go(); // set tlogLevel to -1 to suppress tlog() output in a test program tlogLevel = -1; int ret = ::mongo::unittest::Suite::run(suites,filter,runsPerTest); #if !defined(_WIN32) && !defined(__sunos__) flock( lockFile, LOCK_UN ); #endif cc().shutdown(); dbexit( (ExitCode)ret ); // so everything shuts down cleanly return ret; }
int Tool::main( int argc , char ** argv ) { static StaticObserver staticObserver; cmdLine.prealloc = false; // The default value may vary depending on compile options, but for tools // we want durability to be disabled. cmdLine.dur = false; #if( BOOST_VERSION >= 104500 ) boost::filesystem::path::default_name_check( boost::filesystem2::no_check ); #else boost::filesystem::path::default_name_check( boost::filesystem::no_check ); #endif _name = argv[0]; /* using the same style as db.cpp */ int command_line_style = (((po::command_line_style::unix_style ^ po::command_line_style::allow_guessing) | po::command_line_style::allow_long_disguise) ^ po::command_line_style::allow_sticky); try { po::options_description all_options("all options"); all_options.add(*_options).add(*_hidden_options); po::store( po::command_line_parser( argc , argv ). options(all_options). positional( _positonalOptions ). style(command_line_style).run() , _params ); po::notify( _params ); } catch (po::error &e) { cerr << "ERROR: " << e.what() << endl << endl; printHelp(cerr); ::_exit(EXIT_BADOPTIONS); } // hide password from ps output for (int i=0; i < (argc-1); ++i) { if (!strcmp(argv[i], "-p") || !strcmp(argv[i], "--password")) { char* arg = argv[i+1]; while (*arg) { *arg++ = 'x'; } } } if ( _params.count( "help" ) ) { printHelp(cout); ::_exit(0); } if ( _params.count( "version" ) ) { printVersion(cout); ::_exit(0); } if ( _params.count( "verbose" ) ) { logLevel = 1; } for (string s = "vv"; s.length() <= 10; s.append("v")) { if (_params.count(s)) { logLevel = s.length(); } } #ifdef MONGO_SSL if (_params.count("ssl")) { mongo::cmdLine.sslOnNormalPorts = true; } #endif preSetup(); bool useDirectClient = hasParam( "dbpath" ); if ( ! useDirectClient ) { _host = "127.0.0.1"; if ( _params.count( "host" ) ) _host = _params["host"].as<string>(); if ( _params.count( "port" ) ) _host += ':' + _params["port"].as<string>(); if ( _noconnection ) { // do nothing } else { string errmsg; ConnectionString cs = ConnectionString::parse( _host , errmsg ); if ( ! cs.isValid() ) { cerr << "invalid hostname [" << _host << "] " << errmsg << endl; ::_exit(-1); } _conn = cs.connect( errmsg ); if ( ! _conn ) { cerr << "couldn't connect to [" << _host << "] " << errmsg << endl; ::_exit(-1); } (_usesstdout ? cout : cerr ) << "connected to: " << _host << endl; } } else { if ( _params.count( "directoryperdb" ) ) { directoryperdb = true; } verify( lastError.get( true ) ); if (_params.count("journal")){ cmdLine.dur = true; } Client::initThread("tools"); _conn = new DBDirectClient(); _host = "DIRECT"; static string myDbpath = getParam( "dbpath" ); dbpath = myDbpath.c_str(); try { acquirePathLock(); } catch ( DBException& ) { cerr << endl << "If you are running a mongod on the same " "path you should connect to that instead of direct data " "file access" << endl << endl; dbexit( EXIT_CLEAN ); ::_exit(-1); } FileAllocator::get()->start(); dur::startup(); } if ( _params.count( "db" ) ) _db = _params["db"].as<string>(); if ( _params.count( "collection" ) ) _coll = _params["collection"].as<string>(); if ( _params.count( "username" ) ) _username = _params["username"].as<string>(); if ( _params.count( "password" ) && ( _password.empty() ) ) { _password = askPassword(); } if (_params.count("ipv6")) enableIPv6(); int ret = -1; try { ret = run(); } catch ( DBException& e ) { cerr << "assertion: " << e.toString() << endl; ret = -1; } catch(const boost::filesystem::filesystem_error &fse) { /* https://jira.mongodb.org/browse/SERVER-2904 Simple tools that don't access the database, such as bsondump, aren't throwing DBExceptions, but are throwing boost exceptions. The currently available set of error codes don't seem to match boost documentation. boost::filesystem::not_found_error (from http://www.boost.org/doc/libs/1_31_0/libs/filesystem/doc/exception.htm) doesn't seem to exist in our headers. Also, fse.code() isn't boost::system::errc::no_such_file_or_directory when this happens, as you would expect. And, determined from experimentation that the command-line argument gets turned into "\\?" instead of "/?" !!! */ #if defined(_WIN32) if (/*(fse.code() == boost::system::errc::no_such_file_or_directory) &&*/ (fse.path1() == "\\?")) printHelp(cerr); else #endif // _WIN32 cerr << "error: " << fse.what() << endl; ret = -1; } if ( currentClient.get() ) currentClient.get()->shutdown(); if ( useDirectClient ) dbexit( EXIT_CLEAN ); ::_exit(ret); }