Change default location for configuration file
– under Linux and macOS, use the “dynare” subdirectory of the configuration directory specified by the XDG specification – under Windows, use the “dynare” subdirectory of the Application Data folder The old location is kept for backward compatibility, with a warning.master
parent
7c83b81623
commit
328e8eef78
|
@ -21,7 +21,12 @@
|
||||||
#include <iostream>
|
#include <iostream>
|
||||||
#include <utility>
|
#include <utility>
|
||||||
|
|
||||||
|
#ifdef _WIN32
|
||||||
|
# include <shlobj.h>
|
||||||
|
#endif
|
||||||
|
|
||||||
#include "Configuration.hh"
|
#include "Configuration.hh"
|
||||||
|
#include "DataTree.hh" // For strsplit()
|
||||||
|
|
||||||
#pragma GCC diagnostic push
|
#pragma GCC diagnostic push
|
||||||
#pragma GCC diagnostic ignored "-Wold-style-cast"
|
#pragma GCC diagnostic ignored "-Wold-style-cast"
|
||||||
|
@ -109,64 +114,59 @@ Configuration::Configuration(bool parallel_arg, bool parallel_test_arg,
|
||||||
}
|
}
|
||||||
|
|
||||||
void
|
void
|
||||||
Configuration::getConfigFileInfo(const filesystem::path& conffile_option)
|
Configuration::getConfigFileInfo(const filesystem::path& conffile_option,
|
||||||
|
WarningConsolidation& warnings)
|
||||||
{
|
{
|
||||||
using namespace boost;
|
using namespace boost;
|
||||||
ifstream configFile;
|
|
||||||
|
|
||||||
if (conffile_option.empty())
|
filesystem::path config_file {conffile_option};
|
||||||
|
|
||||||
|
if (config_file.empty())
|
||||||
{
|
{
|
||||||
filesystem::path defaultConfigFile;
|
config_file = findConfigFile("dynare.ini");
|
||||||
// Test OS and try to open default file
|
|
||||||
#if defined(_WIN32) || defined(__CYGWIN32__)
|
|
||||||
if (auto appdata = getenv("APPDATA"); appdata)
|
|
||||||
defaultConfigFile = filesystem::path {appdata} / "dynare.ini";
|
|
||||||
else
|
|
||||||
{
|
|
||||||
if (parallel || parallel_test)
|
|
||||||
cerr << "ERROR: ";
|
|
||||||
else
|
|
||||||
cerr << "WARNING: ";
|
|
||||||
cerr << "APPDATA environment variable not found." << endl;
|
|
||||||
|
|
||||||
if (parallel || parallel_test)
|
if (config_file.empty()) // Try old default location (Dynare ⩽ 5) for backward compatibility
|
||||||
exit(EXIT_FAILURE);
|
{
|
||||||
}
|
filesystem::path old_default_config_file;
|
||||||
|
#ifdef _WIN32
|
||||||
|
array<wchar_t, MAX_PATH + 1> appdata;
|
||||||
|
if (SHGetFolderPathW(nullptr, CSIDL_APPDATA | CSIDL_FLAG_DONT_VERIFY, nullptr,
|
||||||
|
SHGFP_TYPE_CURRENT, appdata.data())
|
||||||
|
== S_OK)
|
||||||
|
old_default_config_file = filesystem::path {appdata.data()} / "dynare.ini";
|
||||||
#else
|
#else
|
||||||
if (auto home = getenv("HOME"); home)
|
if (auto home = getenv("HOME"); home)
|
||||||
defaultConfigFile = filesystem::path {home} / ".dynare";
|
old_default_config_file = filesystem::path {home} / ".dynare";
|
||||||
else
|
|
||||||
{
|
|
||||||
if (parallel || parallel_test)
|
|
||||||
cerr << "ERROR: ";
|
|
||||||
else
|
|
||||||
cerr << "WARNING: ";
|
|
||||||
cerr << "HOME environment variable not found." << endl;
|
|
||||||
if (parallel || parallel_test)
|
|
||||||
exit(EXIT_FAILURE);
|
|
||||||
}
|
|
||||||
#endif
|
#endif
|
||||||
configFile.open(defaultConfigFile, fstream::in);
|
if (!old_default_config_file.empty() && exists(old_default_config_file))
|
||||||
if (!configFile.is_open())
|
|
||||||
{
|
|
||||||
if (parallel || parallel_test)
|
|
||||||
{
|
{
|
||||||
cerr << "ERROR: Could not open the default config file ("
|
warnings << "WARNING: the location " << old_default_config_file.string()
|
||||||
<< defaultConfigFile.string() << ")" << endl;
|
<< " for the configuration file is obsolete; please see the reference"
|
||||||
exit(EXIT_FAILURE);
|
<< " manual for the new location." << endl;
|
||||||
|
config_file = old_default_config_file;
|
||||||
}
|
}
|
||||||
else
|
|
||||||
return;
|
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
else
|
|
||||||
|
if (config_file.empty())
|
||||||
{
|
{
|
||||||
configFile.open(conffile_option, fstream::in);
|
if (parallel || parallel_test)
|
||||||
if (!configFile.is_open())
|
|
||||||
{
|
{
|
||||||
cerr << "ERROR: Couldn't open file " << conffile_option.string() << endl;
|
cerr << "ERROR: the parallel or parallel_test option was passed but no configuration "
|
||||||
|
<< "file was found" << endl;
|
||||||
exit(EXIT_FAILURE);
|
exit(EXIT_FAILURE);
|
||||||
}
|
}
|
||||||
|
else
|
||||||
|
return;
|
||||||
|
}
|
||||||
|
|
||||||
|
ifstream configFile;
|
||||||
|
configFile.open(config_file, fstream::in);
|
||||||
|
|
||||||
|
if (!configFile.is_open())
|
||||||
|
{
|
||||||
|
cerr << "ERROR: Couldn't open configuration file " << config_file.string() << endl;
|
||||||
|
exit(EXIT_FAILURE);
|
||||||
}
|
}
|
||||||
|
|
||||||
string name, computerName, port, userName, password, remoteDrive, remoteDirectory, programPath,
|
string name, computerName, port, userName, password, remoteDrive, remoteDirectory, programPath,
|
||||||
|
@ -812,3 +812,46 @@ Configuration::writeEndParallel(ostream& output) const
|
||||||
<< " closeSlave(options_.parallel,options_.parallel_info.RemoteTmpFolder);" << endl
|
<< " closeSlave(options_.parallel,options_.parallel_info.RemoteTmpFolder);" << endl
|
||||||
<< "end" << endl;
|
<< "end" << endl;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
filesystem::path
|
||||||
|
Configuration::findConfigFile(const string& filename)
|
||||||
|
{
|
||||||
|
#ifdef _WIN32
|
||||||
|
array<wchar_t, MAX_PATH + 1> appdata;
|
||||||
|
if (SHGetFolderPathW(nullptr, CSIDL_APPDATA | CSIDL_FLAG_DONT_VERIFY, nullptr, SHGFP_TYPE_CURRENT,
|
||||||
|
appdata.data())
|
||||||
|
== S_OK)
|
||||||
|
{
|
||||||
|
filesystem::path candidate {filesystem::path {appdata.data()} / "dynare" / filename};
|
||||||
|
if (exists(candidate))
|
||||||
|
return candidate;
|
||||||
|
}
|
||||||
|
#else
|
||||||
|
filesystem::path xdg_config_home;
|
||||||
|
if (auto xdg_config_home_env = getenv("XDG_CONFIG_HOME"); xdg_config_home_env)
|
||||||
|
xdg_config_home = xdg_config_home_env;
|
||||||
|
if (auto home = getenv("HOME"); xdg_config_home.empty() && home)
|
||||||
|
xdg_config_home = filesystem::path {home} / ".config";
|
||||||
|
|
||||||
|
if (!xdg_config_home.empty())
|
||||||
|
{
|
||||||
|
filesystem::path candidate {xdg_config_home / "dynare" / filename};
|
||||||
|
if (exists(candidate))
|
||||||
|
return candidate;
|
||||||
|
}
|
||||||
|
|
||||||
|
string xdg_config_dirs;
|
||||||
|
if (auto xdg_config_dirs_env = getenv("XDG_CONFIG_DIRS"); xdg_config_dirs_env)
|
||||||
|
xdg_config_dirs = xdg_config_dirs_env;
|
||||||
|
if (xdg_config_dirs.empty())
|
||||||
|
xdg_config_dirs = "/etc/xdg";
|
||||||
|
for (const auto& dir : DataTree::strsplit(xdg_config_dirs, ':'))
|
||||||
|
{
|
||||||
|
filesystem::path candidate {filesystem::path {dir} / "dynare" / filename};
|
||||||
|
if (exists(candidate))
|
||||||
|
return candidate;
|
||||||
|
}
|
||||||
|
#endif
|
||||||
|
|
||||||
|
return {};
|
||||||
|
}
|
||||||
|
|
|
@ -114,10 +114,17 @@ private:
|
||||||
const string& programPath, const string& programConfig,
|
const string& programPath, const string& programConfig,
|
||||||
const string& matlabOctavePath, bool singleCompThread,
|
const string& matlabOctavePath, bool singleCompThread,
|
||||||
int numberOfThreadsPerJob, const string& operatingSystem);
|
int numberOfThreadsPerJob, const string& operatingSystem);
|
||||||
|
/* Given a filename (e.g. dynare.ini), looks for it in the configuration directory:
|
||||||
|
– if under Linux or macOS, look into the “dynare” subdirectory of the XDG
|
||||||
|
configuration directories (following the default values and the precedence order specified in
|
||||||
|
the XDG specification)
|
||||||
|
– if under Windows, look into %APPDATA%\dynare\
|
||||||
|
The returned path will be empty if the file is not found. */
|
||||||
|
[[nodiscard]] static filesystem::path findConfigFile(const string& filename);
|
||||||
|
|
||||||
public:
|
public:
|
||||||
//! Parse config file
|
//! Parse config file
|
||||||
void getConfigFileInfo(const filesystem::path& conffile_option);
|
void getConfigFileInfo(const filesystem::path& conffile_option, WarningConsolidation& warnings);
|
||||||
//! Check Pass
|
//! Check Pass
|
||||||
void checkPass(WarningConsolidation& warnings) const;
|
void checkPass(WarningConsolidation& warnings) const;
|
||||||
//! Check Pass
|
//! Check Pass
|
||||||
|
|
|
@ -463,7 +463,7 @@ main(int argc, char** argv)
|
||||||
// Process config file
|
// Process config file
|
||||||
Configuration config {parallel, parallel_test, parallel_follower_open_mode, parallel_use_psexec,
|
Configuration config {parallel, parallel_test, parallel_follower_open_mode, parallel_use_psexec,
|
||||||
cluster_name};
|
cluster_name};
|
||||||
config.getConfigFileInfo(conffile);
|
config.getConfigFileInfo(conffile, warnings);
|
||||||
config.checkPass(warnings);
|
config.checkPass(warnings);
|
||||||
config.transformPass();
|
config.transformPass();
|
||||||
|
|
||||||
|
|
Loading…
Reference in New Issue