From 9d46ff9edad48c0fca96c419e9325414b17e7e88 Mon Sep 17 00:00:00 2001 From: Florian Lindner Date: Sun, 11 Jun 2023 03:43:15 +0200 Subject: [PATCH] odbcBackend: bugfixes, restrict namespaces - fix bug where string for quoted identifiers is not ended with '\0' - fix checking for valid `timeout` arguemnts - Only allow user- and system-namespaces for ODBC mountpoints --- src/plugins/backend_odbc/backend_odbc_get.c | 2 +- src/tools/kdb/mountOdbc.cpp | 45 +++++++++++++++++++-- 2 files changed, 42 insertions(+), 5 deletions(-) diff --git a/src/plugins/backend_odbc/backend_odbc_get.c b/src/plugins/backend_odbc/backend_odbc_get.c index 6482f1920d5..9b9b6e75448 100644 --- a/src/plugins/backend_odbc/backend_odbc_get.c +++ b/src/plugins/backend_odbc/backend_odbc_get.c @@ -194,7 +194,7 @@ static SQLHSTMT prepareSelectStmt (SQLHDBC sqlConnection, struct dataSourceConfi /* Get driver specific identifier quote character * (see: https://learn.microsoft.com/en-us/sql/odbc/reference/develop-app/quoted-identifiers) for more information */ - char identifierQuoteChar[2]; + char identifierQuoteChar[2] = { 0, 0 }; SQLSMALLINT quoteCharLen = 0; ret = SQLGetInfo (sqlConnection, SQL_IDENTIFIER_QUOTE_CHAR, identifierQuoteChar, 2, "eCharLen); diff --git a/src/tools/kdb/mountOdbc.cpp b/src/tools/kdb/mountOdbc.cpp index e4ff9f02888..14515356e29 100644 --- a/src/tools/kdb/mountOdbc.cpp +++ b/src/tools/kdb/mountOdbc.cpp @@ -37,10 +37,38 @@ void replaceSubstrings (std::string & str, std::string oldSubStr, std::string ne bool strContainsUnsignedChar (std::string & toCheck) { + for (char c : toCheck) + { + if (!isdigit (c)) + { + return false; + } + } + std::istringstream inputStringStream (toCheck); - unsigned char uCharVal; - inputStringStream >> uCharVal; - return !inputStringStream.fail () && inputStringStream.eof (); + unsigned long lngVal; + inputStringStream >> lngVal; + + if (lngVal > UCHAR_MAX) + { + return false; + } + + return !inputStringStream.fail (); +} + +bool checkNameSpace (std::string toCheck) +{ + std::string userNs = "user:/"; + std::string systemNs = "system:/"; + + + if (toCheck.compare (0, userNs.length (), userNs) == 0 || toCheck.compare (0, systemNs.length (), systemNs) == 0) + { + return true; + } + + return false; } int MountOdbcCommand::execute (Cmdline const & cl) @@ -77,6 +105,14 @@ int MountOdbcCommand::execute (Cmdline const & cl) std::string mp = keyMpPath.getName (); + if (!checkNameSpace (mp)) + { + throw std::invalid_argument ( + "Only mountpoints for the user- and system-namespaces are supported by the ODBC backend!\n" + "Therefore, the given mountpoint must start with 'user:/' or 'system:/', but '" + + mp + "' was given."); + } + /* escape slashes in the mountpoint path */ std::string mpOriginal (mp); replaceSubstrings (mp, "/", "\\/"); @@ -105,7 +141,8 @@ int MountOdbcCommand::execute (Cmdline const & cl) { throw std::invalid_argument ( "If you specify a timeout, it must fit into an unsigned char.\n" - "The maximum allowed value on this system is " ELEKTRA_STRINGIFY (UCHAR_MAX)); + "The maximum allowed value on this system is " + + std::to_string (UCHAR_MAX) + " but you passed " + timeout); }