diff --git a/Options.cpp b/Options.cpp index 42b37581..1a4434f8 100644 --- a/Options.cpp +++ b/Options.cpp @@ -40,7 +40,6 @@ #include #else #include -#include #include #endif @@ -554,9 +553,12 @@ void Options::InitOptFile() int p = 0; while (const char* szFilename = PossibleConfigLocations[p++]) { - // substitute HOME-variable using SetOption - SetOption("$CONFIGFILENAME", szFilename); - szFilename = GetOption("$CONFIGFILENAME"); + // substitute HOME-variable + char szExpandedFilename[1024]; + if (Util::ExpandHomePath(szFilename, szExpandedFilename, sizeof(szExpandedFilename))) + { + szFilename = szExpandedFilename; + } if (Util::FileExists(szFilename)) { @@ -1114,35 +1116,14 @@ void Options::SetOption(const char* optname, const char* value) char* curvalue = NULL; #ifndef WIN32 - if ((value) && (value[0] == '~') && (value[1] == '/')) + if (value && (value[0] == '~') && (value[1] == '/')) { - // expand home-dir - - char* home = getenv("HOME"); - if (!home) - { - struct passwd *pw = getpwuid(getuid()); - if (pw) - home = pw->pw_dir; - } - - if (!home) + char szExpandedPath[1024]; + if (!Util::ExpandHomePath(value, szExpandedPath, sizeof(szExpandedPath))) { abort("FATAL ERROR: Unable to determine home-directory, option \"%s\"\n", optname); } - - char* newvalue = (char*) malloc(strlen(value) + strlen(home) + 10); - - if (home[strlen(home)-1] == '/') - { - sprintf(newvalue, "%s%s", home, value + 2); - } - else - { - sprintf(newvalue, "%s/%s", home, value + 2); - } - - curvalue = newvalue; + curvalue = strdup(szExpandedPath); } else #endif @@ -1681,3 +1662,14 @@ void Options::ParseFileIDList(int argc, char* argv[], int optind) m_pEditQueueIDList[i] = IDs[i]; } } + +Options::OptEntries* Options::LockOptEntries() +{ + m_mutexOptEntries.Lock(); + return &m_OptEntries; +} + +void Options::UnlockOptEntries() +{ + m_mutexOptEntries.Unlock(); +} diff --git a/Options.h b/Options.h index 0286903d..17d0b7fc 100644 --- a/Options.h +++ b/Options.h @@ -28,6 +28,7 @@ #define OPTIONS_H #include +#include "Thread.h" class Options { @@ -78,26 +79,30 @@ public: slDebug }; -private: class OptEntry { private: char* m_szName; char* m_szValue; + void SetName(const char* szName); + void SetValue(const char* szValue); + + friend class Options; + public: OptEntry(); ~OptEntry(); const char* GetName() { return m_szName; } - void SetName(const char* szName); const char* GetValue() { return m_szValue; } - void SetValue(const char* szValue); }; typedef std::vector OptEntries; +private: OptEntries m_OptEntries; bool m_bConfigInitialized; + Mutex m_mutexOptEntries; // Options char* m_szConfigFilename; @@ -218,6 +223,8 @@ public: ~Options(); // Options + OptEntries* LockOptEntries(); + void UnlockOptEntries(); const char* GetDestDir() { return m_szDestDir; } const char* GetTempDir() { return m_szTempDir; } const char* GetQueueDir() { return m_szQueueDir; } diff --git a/ScriptController.cpp b/ScriptController.cpp index 7fb425ca..b0fed028 100644 --- a/ScriptController.cpp +++ b/ScriptController.cpp @@ -199,8 +199,29 @@ void ScriptController::SetEnvVar(const char* szName, const char* szValue) void ScriptController::PrepareEnvironmentStrings() { - //TODO: add program options + Options::OptEntries* pOptEntries = g_pOptions->LockOptEntries(); + for (Options::OptEntries::iterator it = pOptEntries->begin(); it != pOptEntries->end(); it++) + { + Options::OptEntry* pOptEntry = *it; + char szVarname[1024]; + snprintf(szVarname, sizeof(szVarname), "NZBOP_%s", pOptEntry->GetName()); + + // convert to upper case; replace "." with "_". + for (char* szPtr = szVarname; *szPtr; szPtr++) + { + if (*szPtr == '.') + { + *szPtr = '_'; + } + *szPtr = toupper(*szPtr); + } + + szVarname[1024-1] = '\0'; + SetEnvVar(szVarname, pOptEntry->GetValue()); + } + + g_pOptions->UnlockOptEntries(); } int ScriptController::Execute() diff --git a/Util.cpp b/Util.cpp index 946307b6..3112e56d 100644 --- a/Util.cpp +++ b/Util.cpp @@ -41,6 +41,7 @@ #else #include #include +#include #endif #include "nzbget.h" @@ -1069,3 +1070,39 @@ bool Util::RenameBak(const char* szFilename, const char* szBakPart, bool bRemove return bOK; } +#ifndef WIN32 +bool Util::ExpandHomePath(const char* szFilename, char* szBuffer, int iBufSize) +{ + if (szFilename && (szFilename[0] == '~') && (szFilename[1] == '/')) + { + // expand home-dir + + char* home = getenv("HOME"); + if (!home) + { + struct passwd *pw = getpwuid(getuid()); + if (pw) + { + home = pw->pw_dir; + } + } + + if (!home) + { + return false; + } + + if (home[strlen(home)-1] == '/') + { + snprintf(szBuffer, iBufSize, "%s%s", home, szFilename + 2); + } + else + { + snprintf(szBuffer, iBufSize, "%s/%s", home, szFilename + 2); + } + szBuffer[iBufSize - 1] = '\0'; + } + + return true; +} +#endif diff --git a/Util.h b/Util.h index 46b43e7c..d0b7c4fa 100644 --- a/Util.h +++ b/Util.h @@ -76,6 +76,9 @@ public: static long long FreeDiskSize(const char* szPath); static bool DirEmpty(const char* szDirFilename); static bool RenameBak(const char* szFilename, const char* szBakPart, bool bRemoveOldExtension, char* szNewNameBuf, int iNewNameBufSize); +#ifndef WIN32 + static bool ExpandHomePath(const char* szFilename, char* szBuffer, int iBufSize); +#endif static long long JoinInt64(unsigned long Hi, unsigned long Lo); static void SplitInt64(long long Int64, unsigned long* Hi, unsigned long* Lo);