Expose new --mmap switch (mmap_memory: true in NodeJS), and run test suite in this mode, as well as shared memory mode.
				
					
				
			This commit is contained in:
		
							parent
							
								
									2f9cb44368
								
							
						
					
					
						commit
						b7e7d32361
					
				@ -1,5 +1,8 @@
 | 
			
		||||
# UNRELEASED
 | 
			
		||||
  - Changes from 5.19.0:
 | 
			
		||||
    - Features:
 | 
			
		||||
      - ADDED: direct mmapping of datafiles is now supported via the `-mmap` switch. [#5242](https://github.com/Project-OSRM/osrm-backend/pull/5242)
 | 
			
		||||
      - REMOVED: the previous `--memory_file` switch is now deprecated and will fallback to `--mmap` [#5242](https://github.com/Project-OSRM/osrm-backend/pull/5242)
 | 
			
		||||
 | 
			
		||||
# 5.19.0
 | 
			
		||||
  - Changes from 5.18.0:
 | 
			
		||||
 | 
			
		||||
@ -84,7 +84,47 @@ class OSRMDirectLoader extends OSRMBaseLoader {
 | 
			
		||||
                throw new Error(util.format('osrm-routed %s: %s', errorReason(err), err.cmd));
 | 
			
		||||
            }
 | 
			
		||||
        });
 | 
			
		||||
        callback();
 | 
			
		||||
 | 
			
		||||
        this.child.readyFunc = (data) => {
 | 
			
		||||
            if (/running and waiting for requests/.test(data)) {
 | 
			
		||||
              this.child.stdout.removeListener('data', this.child.readyFunc);
 | 
			
		||||
              callback();
 | 
			
		||||
            }
 | 
			
		||||
        };
 | 
			
		||||
        this.child.stdout.on('data',this.child.readyFunc);
 | 
			
		||||
    }
 | 
			
		||||
};
 | 
			
		||||
 | 
			
		||||
class OSRMmmapLoader extends OSRMBaseLoader {
 | 
			
		||||
    constructor (scope) {
 | 
			
		||||
        super(scope);
 | 
			
		||||
    }
 | 
			
		||||
 | 
			
		||||
    load (inputFile, callback) {
 | 
			
		||||
        this.inputFile = inputFile;
 | 
			
		||||
        this.shutdown(() => {
 | 
			
		||||
            this.launch(callback);
 | 
			
		||||
        });
 | 
			
		||||
    }
 | 
			
		||||
 | 
			
		||||
    osrmUp (callback) {
 | 
			
		||||
        if (this.osrmIsRunning()) return callback(new Error("osrm-routed already running!"));
 | 
			
		||||
 | 
			
		||||
        const command_arguments = util.format('%s -p %d -i %s -a %s --mmap', this.inputFile, this.scope.OSRM_PORT, this.scope.OSRM_IP, this.scope.ROUTING_ALGORITHM);
 | 
			
		||||
        this.child = this.scope.runBin('osrm-routed', command_arguments, this.scope.environment, (err) => {
 | 
			
		||||
            if (err && err.signal !== 'SIGINT') {
 | 
			
		||||
                this.child = null;
 | 
			
		||||
                throw new Error(util.format('osrm-routed %s: %s', errorReason(err), err.cmd));
 | 
			
		||||
            }
 | 
			
		||||
        });
 | 
			
		||||
 | 
			
		||||
        this.child.readyFunc = (data) => {
 | 
			
		||||
          if (/running and waiting for requests/.test(data)) {
 | 
			
		||||
            this.child.stdout.removeListener('data', this.child.readyFunc);
 | 
			
		||||
            callback();
 | 
			
		||||
          }
 | 
			
		||||
        };
 | 
			
		||||
        this.child.stdout.on('data',this.child.readyFunc);
 | 
			
		||||
    }
 | 
			
		||||
};
 | 
			
		||||
 | 
			
		||||
@ -135,22 +175,32 @@ class OSRMLoader {
 | 
			
		||||
        this.scope = scope;
 | 
			
		||||
        this.sharedLoader = new OSRMDatastoreLoader(this.scope);
 | 
			
		||||
        this.directLoader = new OSRMDirectLoader(this.scope);
 | 
			
		||||
        this.mmapLoader = new OSRMmmapLoader(this.scope);
 | 
			
		||||
        this.method = scope.DEFAULT_LOAD_METHOD;
 | 
			
		||||
    }
 | 
			
		||||
 | 
			
		||||
    load (inputFile, callback) {
 | 
			
		||||
        if (!this.loader) {
 | 
			
		||||
            this.loader = {shutdown: (cb) => cb() };
 | 
			
		||||
        }
 | 
			
		||||
        if (this.method === 'datastore') {
 | 
			
		||||
            this.directLoader.shutdown((err) => {
 | 
			
		||||
            this.loader.shutdown((err) => {
 | 
			
		||||
              if (err) return callback(err);
 | 
			
		||||
              this.loader = this.sharedLoader;
 | 
			
		||||
              this.sharedLoader.load(inputFile, callback);
 | 
			
		||||
            });
 | 
			
		||||
        } else if (this.method === 'directly') {
 | 
			
		||||
            this.sharedLoader.shutdown((err) => {
 | 
			
		||||
            this.loader.shutdown((err) => {
 | 
			
		||||
              if (err) return callback(err);
 | 
			
		||||
              this.loader = this.directLoader;
 | 
			
		||||
              this.directLoader.load(inputFile, callback);
 | 
			
		||||
            });
 | 
			
		||||
        } else if (this.method === 'mmap') {
 | 
			
		||||
            this.loader.shutdown((err) => {
 | 
			
		||||
              if (err) return callback(err);
 | 
			
		||||
              this.loader = this.mmapLoader;
 | 
			
		||||
              this.mmapLoader.load(inputFile, callback);
 | 
			
		||||
            });
 | 
			
		||||
        } else {
 | 
			
		||||
            callback(new Error('*** Unknown load method ' + method));
 | 
			
		||||
        }
 | 
			
		||||
 | 
			
		||||
@ -32,7 +32,7 @@ module.exports = function () {
 | 
			
		||||
        this.DEFAULT_ENVIRONMENT = Object.assign({STXXLCFG: stxxl_config}, process.env);
 | 
			
		||||
        this.DEFAULT_PROFILE = 'bicycle';
 | 
			
		||||
        this.DEFAULT_INPUT_FORMAT = 'osm';
 | 
			
		||||
        this.DEFAULT_LOAD_METHOD = 'datastore';
 | 
			
		||||
        this.DEFAULT_LOAD_METHOD = process.argv[process.argv.indexOf('-m') +1].match('mmap') ? 'mmap' : 'datastore';
 | 
			
		||||
        this.DEFAULT_ORIGIN = [1,1];
 | 
			
		||||
        this.OSM_USER = 'osrm';
 | 
			
		||||
        this.OSM_UID = 1;
 | 
			
		||||
 | 
			
		||||
@ -63,12 +63,16 @@ template <typename Algorithm> class Engine final : public EngineInterface
 | 
			
		||||
                                << "\" with algorithm " << routing_algorithms::name<Algorithm>();
 | 
			
		||||
            facade_provider = std::make_unique<WatchingProvider<Algorithm>>(config.dataset_name);
 | 
			
		||||
        }
 | 
			
		||||
        else if (!config.memory_file.empty())
 | 
			
		||||
        else if (!config.memory_file.empty() || config.use_mmap)
 | 
			
		||||
        {
 | 
			
		||||
            util::Log(logDEBUG) << "Using memory mapped filed at " << config.memory_file
 | 
			
		||||
                                << " with algorithm " << routing_algorithms::name<Algorithm>();
 | 
			
		||||
            facade_provider = std::make_unique<ExternalProvider<Algorithm>>(config.storage_config,
 | 
			
		||||
                                                                            config.memory_file);
 | 
			
		||||
            if (!config.memory_file.empty())
 | 
			
		||||
            {
 | 
			
		||||
                util::Log(logWARNING)
 | 
			
		||||
                    << "The 'memory_file' option is DEPRECATED - using direct mmaping instead";
 | 
			
		||||
            }
 | 
			
		||||
            util::Log(logDEBUG) << "Using direct memory mapping with algorithm "
 | 
			
		||||
                                << routing_algorithms::name<Algorithm>();
 | 
			
		||||
            facade_provider = std::make_unique<ExternalProvider<Algorithm>>(config.storage_config);
 | 
			
		||||
        }
 | 
			
		||||
        else
 | 
			
		||||
        {
 | 
			
		||||
 | 
			
		||||
@ -89,6 +89,7 @@ struct EngineConfig final
 | 
			
		||||
    int max_alternatives = 3; // set an arbitrary upper bound; can be adjusted by user
 | 
			
		||||
    bool use_shared_memory = true;
 | 
			
		||||
    boost::filesystem::path memory_file;
 | 
			
		||||
    bool use_mmap = true;
 | 
			
		||||
    Algorithm algorithm = Algorithm::CH;
 | 
			
		||||
    std::string verbosity;
 | 
			
		||||
    std::string dataset_name;
 | 
			
		||||
 | 
			
		||||
@ -142,6 +142,10 @@ inline engine_config_ptr argumentsToEngineConfig(const Nan::FunctionCallbackInfo
 | 
			
		||||
    if (shared_memory.IsEmpty())
 | 
			
		||||
        return engine_config_ptr();
 | 
			
		||||
 | 
			
		||||
    auto mmap_memory = params->Get(Nan::New("mmap_memory").ToLocalChecked());
 | 
			
		||||
    if (mmap_memory.IsEmpty())
 | 
			
		||||
        return engine_config_ptr();
 | 
			
		||||
 | 
			
		||||
    if (!memory_file->IsUndefined())
 | 
			
		||||
    {
 | 
			
		||||
        if (path->IsUndefined())
 | 
			
		||||
@ -190,6 +194,18 @@ inline engine_config_ptr argumentsToEngineConfig(const Nan::FunctionCallbackInfo
 | 
			
		||||
            return engine_config_ptr();
 | 
			
		||||
        }
 | 
			
		||||
    }
 | 
			
		||||
    if (!mmap_memory->IsUndefined())
 | 
			
		||||
    {
 | 
			
		||||
        if (mmap_memory->IsBoolean())
 | 
			
		||||
        {
 | 
			
		||||
            engine_config->use_mmap = Nan::To<bool>(mmap_memory).FromJust();
 | 
			
		||||
        }
 | 
			
		||||
        else
 | 
			
		||||
        {
 | 
			
		||||
            Nan::ThrowError("mmap_memory option must be a boolean");
 | 
			
		||||
            return engine_config_ptr();
 | 
			
		||||
        }
 | 
			
		||||
    }
 | 
			
		||||
 | 
			
		||||
    if (path->IsUndefined() && !engine_config->use_shared_memory)
 | 
			
		||||
    {
 | 
			
		||||
 | 
			
		||||
@ -18,7 +18,7 @@
 | 
			
		||||
  },
 | 
			
		||||
  "scripts": {
 | 
			
		||||
    "lint": "node ./node_modules/eslint/bin/eslint.js -c ./.eslintrc features/step_definitions/ features/support/",
 | 
			
		||||
    "test": "npm run lint && node ./node_modules/cucumber/bin/cucumber.js features/ -p verify && node ./node_modules/cucumber/bin/cucumber.js features/ -p mld",
 | 
			
		||||
    "test": "npm run lint && node ./node_modules/cucumber/bin/cucumber.js features/ -p verify && node ./node_modules/cucumber/bin/cucumber.js features/ -p verify -m mmap && node ./node_modules/cucumber/bin/cucumber.js features/ -p mld && node ./node_modules/cucumber/bin/cucumber.js features/ -p mld -m mmap",
 | 
			
		||||
    "clean": "rm -rf test/cache",
 | 
			
		||||
    "docs": "./scripts/build_api_docs.sh",
 | 
			
		||||
    "install": "node-pre-gyp install --fallback-to-build=false || ./scripts/node_install.sh",
 | 
			
		||||
 | 
			
		||||
@ -23,7 +23,9 @@ bool EngineConfig::IsValid() const
 | 
			
		||||
                              unlimited_or_more_than(max_results_nearest, 0) &&
 | 
			
		||||
                              max_alternatives >= 0;
 | 
			
		||||
 | 
			
		||||
    return ((use_shared_memory && all_path_are_empty) || storage_config.IsValid()) && limits_valid;
 | 
			
		||||
    return ((use_shared_memory && all_path_are_empty) || (use_mmap && storage_config.IsValid()) ||
 | 
			
		||||
            storage_config.IsValid()) &&
 | 
			
		||||
           limits_valid;
 | 
			
		||||
}
 | 
			
		||||
}
 | 
			
		||||
}
 | 
			
		||||
 | 
			
		||||
@ -119,7 +119,10 @@ inline unsigned generateServerProgramOptions(const int argc,
 | 
			
		||||
         "Load data from shared memory") //
 | 
			
		||||
        ("memory_file",
 | 
			
		||||
         value<boost::filesystem::path>(&config.memory_file),
 | 
			
		||||
         "Store data in a memory mapped file rather than in process memory.") //
 | 
			
		||||
         "DEPRECATED: Will behave the same as --mmap.")(
 | 
			
		||||
            "mmap,m",
 | 
			
		||||
            value<bool>(&config.use_mmap)->implicit_value(true)->default_value(false),
 | 
			
		||||
            "Map datafiles directly, do not use any additional memory.") //
 | 
			
		||||
        ("dataset-name",
 | 
			
		||||
         value<std::string>(&config.dataset_name),
 | 
			
		||||
         "Name of the shared memory dataset to connect to.") //
 | 
			
		||||
 | 
			
		||||
		Loading…
	
		Reference in New Issue
	
	Block a user