Commit 1fbdb6bc authored by Michael Meskes's avatar Michael Meskes

Fixed segfault in connect when specifying no database name.

parent c3d583dd
/* $PostgreSQL: pgsql/src/interfaces/ecpg/ecpglib/connect.c,v 1.23 2004/08/29 05:06:59 momjian Exp $ */ /* $PostgreSQL: pgsql/src/interfaces/ecpg/ecpglib/connect.c,v 1.24 2004/12/30 09:36:37 meskes Exp $ */
#define POSTGRES_ECPG_INTERNAL #define POSTGRES_ECPG_INTERNAL
#include "postgres_fe.h" #include "postgres_fe.h"
...@@ -242,7 +242,7 @@ ECPGconnect(int lineno, int c, const char *name, const char *user, const char *p ...@@ -242,7 +242,7 @@ ECPGconnect(int lineno, int c, const char *name, const char *user, const char *p
struct sqlca_t *sqlca = ECPGget_sqlca(); struct sqlca_t *sqlca = ECPGget_sqlca();
enum COMPAT_MODE compat = c; enum COMPAT_MODE compat = c;
struct connection *this; struct connection *this;
char *dbname = strdup(name), char *dbname = name ? strdup(name) : NULL,
*host = NULL, *host = NULL,
*tmp, *tmp,
*port = NULL, *port = NULL,
...@@ -275,75 +275,100 @@ ECPGconnect(int lineno, int c, const char *name, const char *user, const char *p ...@@ -275,75 +275,100 @@ ECPGconnect(int lineno, int c, const char *name, const char *user, const char *p
if (dbname == NULL && connection_name == NULL) if (dbname == NULL && connection_name == NULL)
connection_name = "DEFAULT"; connection_name = "DEFAULT";
/* get the detail information out of dbname */ if (dbname != NULL)
if (strchr(dbname, '@') != NULL) {
{ /* get the detail information out of dbname */
/* old style: dbname[@server][:port] */ if (strchr(dbname, '@') != NULL)
tmp = strrchr(dbname, ':');
if (tmp != NULL) /* port number given */
{
port = strdup(tmp + 1);
*tmp = '\0';
}
tmp = strrchr(dbname, '@');
if (tmp != NULL) /* host name given */
{
host = strdup(tmp + 1);
*tmp = '\0';
}
realname = strdup(dbname);
}
else if (strncmp(dbname, "tcp:", 4) == 0 || strncmp(dbname, "unix:", 5) == 0)
{
int offset = 0;
/*
* only allow protocols tcp and unix
*/
if (strncmp(dbname, "tcp:", 4) == 0)
offset = 4;
else if (strncmp(dbname, "unix:", 5) == 0)
offset = 5;
if (strncmp(dbname + offset, "postgresql://", strlen("postgresql://")) == 0)
{ {
/* old style: dbname[@server][:port] */
/*------ tmp = strrchr(dbname, ':');
* new style: if (tmp != NULL) /* port number given */
* <tcp|unix>:postgresql://server[:port|:/unixsocket/path:]
* [/db name][?options]
*------
*/
offset += strlen("postgresql://");
tmp = strrchr(dbname + offset, '?');
if (tmp != NULL) /* options given */
{ {
options = strdup(tmp + 1); port = strdup(tmp + 1);
*tmp = '\0'; *tmp = '\0';
} }
tmp = last_dir_separator(dbname + offset); tmp = strrchr(dbname, '@');
if (tmp != NULL) /* database name given */ if (tmp != NULL) /* host name given */
{ {
realname = strdup(tmp + 1); host = strdup(tmp + 1);
*tmp = '\0'; *tmp = '\0';
} }
realname = strdup(dbname);
}
else if (strncmp(dbname, "tcp:", 4) == 0 || strncmp(dbname, "unix:", 5) == 0)
{
int offset = 0;
/*
* only allow protocols tcp and unix
*/
if (strncmp(dbname, "tcp:", 4) == 0)
offset = 4;
else if (strncmp(dbname, "unix:", 5) == 0)
offset = 5;
tmp = strrchr(dbname + offset, ':'); if (strncmp(dbname + offset, "postgresql://", strlen("postgresql://")) == 0)
if (tmp != NULL) /* port number or Unix socket path given */
{ {
char *tmp2;
*tmp = '\0'; /*------
if ((tmp2 = strchr(tmp + 1, ':')) != NULL) * new style:
* <tcp|unix>:postgresql://server[:port|:/unixsocket/path:]
* [/db name][?options]
*------
*/
offset += strlen("postgresql://");
tmp = strrchr(dbname + offset, '?');
if (tmp != NULL) /* options given */
{
options = strdup(tmp + 1);
*tmp = '\0';
}
tmp = last_dir_separator(dbname + offset);
if (tmp != NULL) /* database name given */
{ {
*tmp2 = '\0'; realname = strdup(tmp + 1);
host = strdup(tmp + 1); *tmp = '\0';
if (strncmp(dbname, "unix:", 5) != 0) }
tmp = strrchr(dbname + offset, ':');
if (tmp != NULL) /* port number or Unix socket path given */
{
char *tmp2;
*tmp = '\0';
if ((tmp2 = strchr(tmp + 1, ':')) != NULL)
{ {
ECPGlog("connect: socketname %s given for TCP connection in line %d\n", host, lineno); *tmp2 = '\0';
host = strdup(tmp + 1);
if (strncmp(dbname, "unix:", 5) != 0)
{
ECPGlog("connect: socketname %s given for TCP connection in line %d\n", host, lineno);
ECPGraise(lineno, ECPG_CONNECT, ECPG_SQLSTATE_SQLCLIENT_UNABLE_TO_ESTABLISH_SQLCONNECTION, realname ? realname : "<DEFAULT>");
if (host)
ECPGfree(host);
if (port)
ECPGfree(port);
if (options)
ECPGfree(options);
if (realname)
ECPGfree(realname);
if (dbname)
ECPGfree(dbname);
return false;
}
}
else
port = strdup(tmp + 1);
}
if (strncmp(dbname, "unix:", 5) == 0)
{
if (strcmp(dbname + offset, "localhost") != 0 && strcmp(dbname + offset, "127.0.0.1") != 0)
{
ECPGlog("connect: non-localhost access via sockets in line %d\n", lineno);
ECPGraise(lineno, ECPG_CONNECT, ECPG_SQLSTATE_SQLCLIENT_UNABLE_TO_ESTABLISH_SQLCONNECTION, realname ? realname : "<DEFAULT>"); ECPGraise(lineno, ECPG_CONNECT, ECPG_SQLSTATE_SQLCLIENT_UNABLE_TO_ESTABLISH_SQLCONNECTION, realname ? realname : "<DEFAULT>");
if (host) if (host)
ECPGfree(host); ECPGfree(host);
...@@ -359,37 +384,17 @@ ECPGconnect(int lineno, int c, const char *name, const char *user, const char *p ...@@ -359,37 +384,17 @@ ECPGconnect(int lineno, int c, const char *name, const char *user, const char *p
} }
} }
else else
port = strdup(tmp + 1); host = strdup(dbname + offset);
}
if (strncmp(dbname, "unix:", 5) == 0)
{
if (strcmp(dbname + offset, "localhost") != 0 && strcmp(dbname + offset, "127.0.0.1") != 0)
{
ECPGlog("connect: non-localhost access via sockets in line %d\n", lineno);
ECPGraise(lineno, ECPG_CONNECT, ECPG_SQLSTATE_SQLCLIENT_UNABLE_TO_ESTABLISH_SQLCONNECTION, realname ? realname : "<DEFAULT>");
if (host)
ECPGfree(host);
if (port)
ECPGfree(port);
if (options)
ECPGfree(options);
if (realname)
ECPGfree(realname);
if (dbname)
ECPGfree(dbname);
return false;
}
} }
else else
host = strdup(dbname + offset); realname = strdup(dbname);
} }
else else
realname = strdup(dbname); realname = strdup(dbname);
} }
else else
realname = strdup(dbname); realname = NULL;
/* add connection to our list */ /* add connection to our list */
#ifdef ENABLE_THREAD_SAFETY #ifdef ENABLE_THREAD_SAFETY
......
/* $PostgreSQL: pgsql/src/interfaces/ecpg/ecpglib/memory.c,v 1.5 2003/11/29 19:52:08 pgsql Exp $ */ /* $PostgreSQL: pgsql/src/interfaces/ecpg/ecpglib/memory.c,v 1.6 2004/12/30 09:36:37 meskes Exp $ */
#define POSTGRES_ECPG_INTERNAL #define POSTGRES_ECPG_INTERNAL
#include "postgres_fe.h" #include "postgres_fe.h"
...@@ -46,8 +46,12 @@ ECPGrealloc(void *ptr, long size, int lineno) ...@@ -46,8 +46,12 @@ ECPGrealloc(void *ptr, long size, int lineno)
char * char *
ECPGstrdup(const char *string, int lineno) ECPGstrdup(const char *string, int lineno)
{ {
char *new = strdup(string); char *new;
if (string == NULL)
return NULL;
new = strdup(string);
if (!new) if (!new)
{ {
ECPGraise(lineno, ECPG_OUT_OF_MEMORY, ECPG_SQLSTATE_ECPG_OUT_OF_MEMORY, NULL); ECPGraise(lineno, ECPG_OUT_OF_MEMORY, ECPG_SQLSTATE_ECPG_OUT_OF_MEMORY, NULL);
......
Markdown is supported
0% or
You are about to add 0 people to the discussion. Proceed with caution.
Finish editing this message first!
Please register or to comment