From f2c0ed475e0580af9f005cff9dd6d7850956e537 Mon Sep 17 00:00:00 2001 From: Frederik Gladhorn Date: Fri, 11 Jan 2013 10:27:41 +0100 Subject: Warn about recursive calls Calling qdbus took a long time and 100% cpu since I had a broken setup. Instead of doing that, warn that the user callls a symlink to qtchooser itself. Change-Id: I968a6d637f51bf8138e196207b7f3bbae17883f5 Reviewed-by: Thiago Macieira --- src/qtchooser/main.cpp | 50 ++++++++++++++++++++++++++++++++++++-------------- 1 file changed, 36 insertions(+), 14 deletions(-) diff --git a/src/qtchooser/main.cpp b/src/qtchooser/main.cpp index 9c67b18..fb5eaa9 100644 --- a/src/qtchooser/main.cpp +++ b/src/qtchooser/main.cpp @@ -169,6 +169,37 @@ static string userHome() #endif } +static inline bool beginsWith(const char *haystack, const char *needle) +{ + return strncmp(haystack, needle, strlen(needle)) == 0; +} + +static inline bool endsWith(const char *haystack, const char *needle) +{ + size_t haystackLen = strlen(haystack); + size_t needleLen = strlen(needle); + if (needleLen > haystackLen) + return false; + return strcmp(haystack + haystackLen - needleLen, needle) == 0; +} + +bool linksBackToSelf(const char *link, const char *target) +{ +#if !defined(_WIN32) && !defined(__WIN32__) + char buf[512]; + int count = readlink(link, buf, sizeof(buf)); + if (count >= 0) { + buf[count] = '\0'; + if (endsWith(buf, target) == 0) { + fprintf(stderr, "%s: could not exec '%s' since it links to %s itself. Check your installation.\n", + target, link, target); + return true; + } + } +#endif + return false; +} + int ToolWrapper::runTool(const string &targetSdk, const string &targetTool, char **argv) { Sdk sdk = selectSdk(targetSdk); @@ -178,6 +209,11 @@ int ToolWrapper::runTool(const string &targetSdk, const string &targetTool, char string tool = sdk.toolsPath + PATH_SEP + targetTool; if (tool[0] == '~') tool = userHome() + tool.substr(1); + + // check if the tool is a symlink to ourselves + if (linksBackToSelf(tool.c_str(), argv0)) + return 1; + argv[0] = &tool[0]; #ifdef QTCHOOSER_TEST_MODE while (*argv) @@ -331,20 +367,6 @@ bool ToolWrapper::matchSdk(const string &targetSdk, Sdk &sdk) return false; } -static inline bool beginsWith(const char *haystack, const char *needle) -{ - return strncmp(haystack, needle, strlen(needle)) == 0; -} - -static inline bool endsWith(const char *haystack, const char *needle) -{ - size_t haystackLen = strlen(haystack); - size_t needleLen = strlen(needle); - if (needleLen > haystackLen) - return false; - return strcmp(haystack + haystackLen - needleLen, needle) == 0; -} - int main(int argc, char **argv) { // search the environment for defaults -- cgit v1.2.3