Changeset: 230778a77ea1 for MonetDB
URL: https://dev.monetdb.org/hg/MonetDB/rev/230778a77ea1
Modified Files:
clients/odbc/samples/odbcconnect.c
Branch: Aug2024
Log Message:
Add list drivers and list dns's to odbcconnect
Fix a small memory leak in the process
diffs (204 lines):
diff --git a/clients/odbc/samples/odbcconnect.c
b/clients/odbc/samples/odbcconnect.c
--- a/clients/odbc/samples/odbcconnect.c
+++ b/clients/odbc/samples/odbcconnect.c
@@ -15,6 +15,8 @@
#include <WTypes.h>
#endif
+
+#include <assert.h>
#include <stdio.h>
#include <stdlib.h>
#include <stdint.h>
@@ -29,14 +31,22 @@ static const char *USAGE =
" -d Target is DSN, call SQLConnect()\n"
" -c Target is connection string, call
SQLDriverConnect()\n"
" -b Target is connection string, call
SQLBrowseConnect()\n"
+ " -l List registered drivers and data sources\n"
" -u USER\n"
" -p PASSWORD\n"
" -v Be verbose\n"
" TARGET Connection String or DSN\n";
-static int do_sqlconnect(SQLCHAR *target);
-static int do_sqldriverconnect(SQLCHAR *target);
-static int do_sqlbrowseconnect(SQLCHAR *target);
+typedef int (action_t)(SQLCHAR *);
+
+static int do_actions(action_t action, int ntargets, SQLCHAR **targets);
+
+static action_t do_sqlconnect;
+static action_t do_sqldriverconnect;
+static action_t do_sqlbrowseconnect;
+
+static int do_listdrivers(void);
+static int do_listdsns(const char *prefix, SQLSMALLINT dir);
static void ensure_ok(SQLSMALLINT type, SQLHANDLE handle, const char *message,
SQLRETURN ret);
@@ -49,6 +59,7 @@ SQLHANDLE env = NULL;
SQLHANDLE conn = NULL;
SQLCHAR outbuf[4096];
+SQLCHAR attrbuf[4096];
static void
cleanup(void)
@@ -68,7 +79,7 @@ main(int argc, char **argv)
action = do_sqlconnect;
SQLCHAR **targets = calloc(argc, sizeof(argv[0]));
int ntargets = 0;
- int ret = 0;
+ int ret;
for (int i = 1; i < argc; i++) {
char *arg = argv[i];
@@ -78,6 +89,8 @@ main(int argc, char **argv)
action = do_sqldriverconnect;
else if (strcmp(arg, "-b") == 0)
action = do_sqlbrowseconnect;
+ else if (strcmp(arg, "-l") == 0)
+ action = NULL;
else if (strcmp(arg, "-u") == 0 && i + 1 < argc)
user = (SQLCHAR*)argv[++i];
else if (strcmp(arg, "-p") == 0 && i + 1 < argc)
@@ -88,15 +101,11 @@ main(int argc, char **argv)
targets[ntargets++] = (SQLCHAR*)arg;
else {
fprintf(stderr, "\nERROR: invalid argument: %s\n%s",
arg, USAGE);
- return 1;
+ ret = 1;
+ goto end;
}
}
- if (ntargets == 0) {
- fprintf(stderr, "\nERROR: pass at least one target\n%s", USAGE);
- return 1;
- }
-
ensure_ok(
SQL_HANDLE_ENV, NULL, "allocate env handle",
SQLAllocHandle(SQL_HANDLE_ENV, NULL, &env));
@@ -105,20 +114,25 @@ main(int argc, char **argv)
SQL_HANDLE_ENV, env, "set odbc version",
SQLSetEnvAttr(env, SQL_ATTR_ODBC_VERSION,
(SQLPOINTER)SQL_OV_ODBC3, 0));
- ensure_ok(
- SQL_HANDLE_ENV, env, "allocate conn handle",
- SQLAllocHandle(SQL_HANDLE_DBC, env, &conn));
-
- for (int i = 0; i < ntargets; i++) {
- SQLCHAR *t = targets[i];
- if (verbose)
- printf("\nTarget: %s\n", t);
- outbuf[0] = '\0';
- int ret = action(t);
- if (ret)
- break;
+ if (action) {
+ if (ntargets == 0) {
+ fprintf(stderr, "\nERROR: pass at least one
target\n%s", USAGE);
+ ret = 1;
+ goto end;
+ }
+ ret = do_actions(action, ntargets, targets);
+ } else {
+ if (ntargets != 0) {
+ fprintf(stderr, "\nERROR: -l does not take
arguments\n%s", USAGE);
+ ret = 1;
+ goto end;
+ }
+ ret = do_listdrivers();
+ ret |= do_listdsns("SYSTEM", SQL_FETCH_FIRST_SYSTEM);
+ ret |= do_listdsns("SYSTEM", SQL_FETCH_FIRST_USER);
}
+end:
free(targets);
cleanup();
@@ -174,6 +188,26 @@ ensure_ok(SQLSMALLINT type, SQLHANDLE ha
static int
+do_actions(action_t action, int ntargets, SQLCHAR **targets)
+{
+ ensure_ok(
+ SQL_HANDLE_ENV, env, "allocate conn handle",
+ SQLAllocHandle(SQL_HANDLE_DBC, env, &conn));
+
+ for (int i = 0; i < ntargets; i++) {
+ SQLCHAR *t = targets[i];
+ if (verbose)
+ printf("\nTarget: %s\n", t);
+ outbuf[0] = '\0';
+ int ret = action(t);
+ if (ret)
+ return ret;
+ }
+
+ return 0;
+}
+
+static int
do_sqlconnect(SQLCHAR *target)
{
ensure_ok(
@@ -218,3 +252,56 @@ do_sqlbrowseconnect(SQLCHAR *target)
return 0;
}
+static int
+do_listdrivers(void)
+{
+ SQLSMALLINT dir = SQL_FETCH_FIRST;
+ SQLSMALLINT len1, len2;
+ int count = 0;
+
+ while (1) {
+ outbuf[0] = attrbuf[0] = '\0';
+ SQLRETURN ret = SQLDrivers(
+ env, dir,
+ outbuf, sizeof(outbuf), &len1,
+ attrbuf, sizeof(attrbuf), &len2
+ );
+ if (ret == SQL_NO_DATA)
+ break;
+ ensure_ok(SQL_HANDLE_ENV, env, "SQLDrivers", ret);
+ dir = SQL_FETCH_NEXT;
+ count += 1;
+ printf("DRIVER={%s}\n", outbuf);
+ for (char *p = (char*)attrbuf; *p; p += strlen(p) + 1) {
+ printf(" %s\n", (char*)p);
+ }
+ }
+
+ if (count == 0)
+ printf("no drivers.\n");
+
+ return 0;
+}
+
+static int
+do_listdsns(const char *prefix, SQLSMALLINT dir)
+{
+ SQLSMALLINT len1, len2;
+
+ while (1) {
+ outbuf[0] = attrbuf[0] = '\0';
+ SQLRETURN ret = SQLDataSources(
+ env, dir,
+ outbuf, sizeof(outbuf), &len1,
+ attrbuf, sizeof(attrbuf), &len2
+ );
+ if (ret == SQL_NO_DATA)
+ break;
+ ensure_ok(SQL_HANDLE_ENV, env, "SQLDataSources", ret);
+ dir = SQL_FETCH_NEXT;
+ printf("%s DSN=%s\n Driver=%s\n", prefix, outbuf, attrbuf);
+ }
+
+ return 0;
+}
+
_______________________________________________
checkin-list mailing list -- [email protected]
To unsubscribe send an email to [email protected]