/*!
@file MaxDB.xs
@author MarcoP
@ingroup dbd::MaxDB
@brief
\if EMIT_LICENCE
========== licence begin PERL_STANDARD
Copyright (c) 2001-2004 SAP AG
This program is free software; you can redistribute it and/or
modify it under the terms of either the Artistic License, as
specified in the Perl README file or the GNU General Public License
as published by the Free Software Foundation; either version 2
of the License, or (at your option) any later version.
This program is distributed in the hope that it will be useful,
but WITHOUT ANY WARRANTY; without even the implied warranty of
MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
GNU General Public License for more details.
You should have received a copy of the GNU General Public License
along with this program; if not, write to the Free Software
Foundation, Inc., 59 Temple Place - Suite 330, Boston, MA 02111-1307, USA.
========== licence end
\endif
*/
#include "dbdimp.h"
#ifndef WIN32
#define UNIX UNIX
#endif
#ifdef __hpux
#define DONT_DECLARE_STD
#endif
/*
* instinfo.c
*/
#ifdef UNIX
#include <pwd.h>
#include <unistd.h>
#include <fcntl.h>
#include <sys/stat.h>
#include <sys/types.h>
#include <grp.h>
#include <pwd.h>
#endif
struct info {
char *key;
char *val;
struct info *next;
};
typedef struct info info_t;
static info_t *
infofree (info_t *ptr) {
info_t *next;
for (;;) {
if (ptr == 0)
break;
next = ptr->next;
if (strcmp (ptr->key, "db") == 0) {
if (ptr->val != 0)
infofree ((info_t *)(ptr->val));
} else {
if (ptr->val != 0)
Safefree (ptr->val);
}
if (ptr->key != 0)
Safefree (ptr->key);
Safefree (ptr);
ptr = next;
}
return 0;
}
static info_t *
infoadd (info_t *their, const char *key, char *val) {
info_t *our;
info_t *curr;
Newz(101, our, 1, info_t);
if (our == 0) {
infofree (their);
return 0;
}
New(101, our->key, strlen (key) + 1, char);
if (our->key == 0) {
Safefree (our);
infofree (their);
return 0;
}
strcpy (our->key, key);
our->val = val;
if (their == 0)
return (our);
for (curr = their; curr->next != 0; curr = curr->next);
curr->next = our;
return (their);
}
#ifdef UNIX
static const char sapdb_keyname[] = "/usr/spool/sql";
static const char sapdb_ininame[] = "ini/SAP_DBTech.ini";
static const char sapdb_globals_filename[] = "/etc/opt/sdb";
static const char sapdb_databases_filename[] = "config/Databases.ini";
static char *
readline (int fd) {
char *buff;
int len;
int want;
int got;
int pos;
char *ptr;
int buffsize;
int offset;
offset = 0;
buffsize = 80;
New (101, buff, buffsize+1, char);
if (buff == 0)
return 0;
pos = lseek (fd, 0, SEEK_CUR);
buff[0] = '\0';
for (;;) {
want = buffsize - offset;
got = read (fd, buff + offset, want);
if (got == 0 && buff[0] == '\0') {
Safefree (buff);
return 0;
}
if (got == 0)
break;
ptr = strchr (buff, '\n');
if (ptr != 0) {
*(ptr + 1) = '\0';
pos += ptr - buff + 1;
lseek (fd, pos, SEEK_SET);
break;
}
offset = buffsize;
buffsize += 80;
buff = (char *) realloc (buff, buffsize + 1);
if (buff == 0)
break;
}
if (buff == 0)
return 0;
len = strlen (buff);
if (len >= 1 && buff[len - 1] == '\n')
buff[len - 1] = '\0';
len = strlen (buff);
if (len >= 1 && buff[len - 1] == '\r')
buff[len - 1] = '\0';
return (buff);
}
static int
enum_db (int fd, const char *section, char **pkey, char **pval, int idx) {
char *line;
int is_in_section;
int len;
int i;
lseek (fd, 0, SEEK_SET);
i = 0;
is_in_section = 0;
for (;;) {
line = readline (fd);
if (line == 0)
break;
if (line[0] == '\0') {
Safefree (line);
continue;
}
if (
is_in_section == 0 &&
line[0] == '[' &&
(len = strlen (section)) != 0 &&
memcmp (&line[1], section, len) == 0 &&
line[len + 1] == ']') {
is_in_section = 1;
Safefree (line);
continue;
}
if (
is_in_section != 0 &&
line[0] == '[') {
Safefree (line);
return 0;
}
if (is_in_section != 0) {
char *ptr;
char *key;
char *val;
int keysize;
int valsize;
ptr = strchr (line, '=');
if (ptr == 0) {
Safefree (line);
continue;
}
if (line[0] == '.' || line[0] == '_') {
Safefree (line);
continue;
}
if (i < idx) {
i++;
Safefree (line);
continue;
}
valsize = strlen (ptr + 1);
New(101, val, valsize + 1, char);
if (val == 0) {
Safefree (line);
return 0;
}
keysize = ptr - line;
New(101, key, keysize + 1, char);
if (key == 0) {
Safefree (val);
Safefree (line);
return 0;
}
strcpy (val, ptr + 1);
memcpy (key, line, keysize);
key[keysize] = '\0';
Safefree (line);
if (pkey != 0)
*pkey = key;
if (pval != 0)
*pval = val;
return 1;
}
Safefree (line);
}
return 0;
}
static char *
get_value (int fd, const char *section, const char *key) {
char *line;
int is_in_section;
int len;
lseek (fd, 0, SEEK_SET);
is_in_section = 0;
for (;;) {
line = readline (fd);
if (line == 0)
break;
if (line[0] == '\0') {
Safefree (line);
continue;
}
if (
is_in_section == 0 &&
line[0] == '[' &&
(len = strlen (section)) != 0 &&
memcmp (&line[1], section, len) == 0 &&
line[len + 1] == ']') {
is_in_section = 1;
Safefree (line);
continue;
}
if (
is_in_section != 0 &&
(len = strlen (key)) != 0 &&
memcmp (line, key, len) == 0 &&
line[len] == '=') {
char *value;
int valuesize;
valuesize = strlen (&line[len + 1]);
if (valuesize == 0) {
Safefree (line);
return 0;
}
New(101, value, valuesize + 1, char);
if (value == 0) {
Safefree (line);
return 0;
}
strcpy (value, &line[len + 1]);
Safefree (line);
return (value);
}
Safefree (line);
}
return 0;
}
static char *
get_paramfile (char *datadir, char *dbname) {
char subdirname[] = "config";
char *filename;
Stat_t statbuff[1];
int rc;
filename = 0;
/* first look in <sapdbdata>/config if <sapdbdata> is known */
if (datadir != 0 && datadir[0] != '\0') {
New(101, filename, strlen (datadir) + 1 +
strlen (subdirname) + 1 + strlen (dbname) + 1, char);
if (filename == 0)
return 0;
strcpy (filename, datadir);
strcat (filename, "/");
strcat (filename, subdirname);
strcat (filename, "/");
strcat (filename, dbname);
rc = stat (filename, statbuff);
}
if (rc == 0)
return (filename);
if (filename != 0) {
Safefree (filename);
filename = 0;
}
/* look in /usr/spool/sql/config, maybe DBROOT installation */
if (rc != 0 && errno == ENOENT) {
New(101,filename, strlen (sapdb_keyname) + 1 +
strlen (subdirname) + 1 + strlen (dbname) + 1, char);
if (filename == 0)
return 0;
strcpy (filename, sapdb_keyname);
strcat (filename, "/");
strcat (filename, subdirname);
strcat (filename, "/");
strcat (filename, dbname);
rc = stat (filename, statbuff);
}
if (rc == 0)
return (filename);
if (filename != 0)
Safefree (filename);
return 0;
}
static char *
get_dbowner (char *datadir, char *dbname) {
char subdirname[] = "config";
char extention[] = "upc";
char *upcfilename;
char *dbowner;
Stat_t statbuff[1];
struct passwd *pwd;
int rc;
/* no file found yet */
rc = -1;
/* first look in <sapdbdata>/config if <sapdbdata> is known */
if (datadir != 0 && datadir[0] != '\0') {
New(101, upcfilename, strlen (datadir) + 1 +
strlen (subdirname) + 1 + strlen (dbname) + 1 +
strlen (extention) + 1, char);
if (upcfilename == 0)
return 0;
strcpy (upcfilename, datadir);
strcat (upcfilename, "/");
strcat (upcfilename, subdirname);
strcat (upcfilename, "/");
strcat (upcfilename, dbname);
strcat (upcfilename, ".");
strcat (upcfilename, extention);
rc = stat (upcfilename, statbuff);
Safefree (upcfilename);
}
/* look in /usr/spool/sql/config, maybe DBROOT installation */
if (rc != 0 && errno == ENOENT) {
New(101, upcfilename, strlen (sapdb_keyname) + 1 +
strlen (subdirname) + 1 + strlen (dbname) + 1 +
strlen (extention) + 1,char);
if (upcfilename == 0)
return 0;
strcpy (upcfilename, sapdb_keyname);
strcat (upcfilename, "/");
strcat (upcfilename, subdirname);
strcat (upcfilename, "/");
strcat (upcfilename, dbname);
strcat (upcfilename, ".");
strcat (upcfilename, extention);
rc = stat (upcfilename, statbuff);
Safefree (upcfilename);
}
if (rc != 0)
return 0;
pwd = getpwuid (statbuff->st_uid);
if (pwd == 0)
return 0;
New (101, dbowner, strlen (pwd->pw_name) + 1, char);
if (dbowner == 0)
return 0;
strcpy (dbowner, pwd->pw_name);
return (dbowner);
}
static info_t *
get_instinfo (char *dbname) {
int fd;
struct stat sb[1];
char *filename;
char *datadir;
info_t *info;
info_t *curr;
char *val;
/*
* first try to find 75 style globals
*/
New (101, filename, strlen (sapdb_globals_filename) + 1,char);
if (filename == 0)
return 0;
strcpy (filename, sapdb_globals_filename);
if (stat (filename, sb) != 0) {
/*
* then try 72, 73 and 74 style globals
*/
Safefree (filename);
New (101, filename, strlen (sapdb_keyname) + 1 + strlen (sapdb_ininame) + 1,char);
if (filename == 0)
return 0;
strcpy (filename, sapdb_keyname);
strcat (filename, "/");
strcat (filename, sapdb_ininame);
}
info = 0;
fd = open (filename , O_RDONLY);
Safefree (filename);
if (fd < 0)
return 0;
datadir = get_value (fd, "Globals", "IndepData");
info = infoadd (info, "datadir", datadir);
info =
infoadd (info, "progdir", get_value (fd, "Globals", "IndepPrograms"));
val = get_value (fd, "Globals", "SdbOwner");
if (val != 0)
infoadd (info, "user", val);
val = get_value (fd, "Globals", "SdbGroup");
if (val != 0)
infoadd (info, "group", val);
close (fd);
/*
* look for databases
*/
if (dbname != 0) {
char *mydbname;
char *myparamfile;
char *mydbswdir;
/*
* 75 style Databases.ini file
*/
New (101, filename, strlen (datadir) + 1 + strlen (sapdb_databases_filename) + 1,char);
if (filename == 0) {
infofree (info);
return 0;
}
strcpy (filename, datadir);
strcat (filename, "/");
strcat (filename, sapdb_databases_filename);
mydbswdir = 0;
fd = open (filename , O_RDONLY);
Safefree (filename);
if (fd >= 0) {
mydbswdir = get_value (fd, "Databases", dbname);
close (fd);
}
if (mydbswdir == 0) {
/*
* then try 72, 73, 74 style Databases section in SAP_DBTech.ini
*/
New (101, filename, strlen (sapdb_keyname) + 1 + strlen (sapdb_ininame) + 1, char);
if (filename == 0) {
infofree (info);
return 0;
}
strcpy (filename, sapdb_keyname);
strcat (filename, "/");
strcat (filename, sapdb_ininame);
fd = open (filename , O_RDONLY);
Safefree (filename);
if (fd >= 0) {
mydbswdir = get_value (fd, "Databases", dbname);
close (fd);
}
}
New (101, mydbname, strlen (dbname) + 1, char);
if (mydbname == 0) {
infofree (info);
return 0;
}
strcpy (mydbname, dbname);
myparamfile = get_paramfile (datadir, mydbname);
curr = 0;
if (mydbname != 0 && myparamfile != 0 && mydbswdir != 0) {
curr = infoadd (curr, "dbname", mydbname);
curr = infoadd (curr, "dbswdir", mydbswdir);
curr = infoadd (curr, "paramfile", myparamfile);
curr = infoadd (curr, "dbowner",
get_dbowner (datadir, dbname));
}
if (curr != 0)
info = infoadd (info, "db", (char *) curr);
} else {
int i;
char *dbswdir;
char *mydbname;
char *myparamfile;
/*
* first try 75 style Databases.ini file
*/
New (101, filename, strlen (datadir) + 1 + strlen (sapdb_databases_filename) + 1, char);
if (filename == 0) {
infofree (info);
return 0;
}
strcpy (filename, datadir);
strcat (filename, "/");
strcat (filename, sapdb_databases_filename);
fd = open (filename , O_RDONLY);
Safefree (filename);
if (fd >= 0) {
for (i = 0;; i++) {
if (enum_db (fd, "Databases", &mydbname, &dbswdir, i) == 0)
break;
myparamfile = get_paramfile (datadir, mydbname);
curr = 0;
if (mydbname != 0 && myparamfile != 0) {
curr = infoadd (curr, "dbname", mydbname);
curr = infoadd (curr, "dbswdir", dbswdir);
curr = infoadd (curr, "paramfile", myparamfile);
curr = infoadd (curr, "dbowner",
get_dbowner (datadir, mydbname));
}
if (curr != 0)
info = infoadd (info, "db", (char *) curr);
}
close (fd);
}
/*
* then try 72, 73, 74 style Databases section in SAP_DBTech.ini
*/
New (101, filename, strlen (sapdb_keyname) + 1 + strlen (sapdb_ininame) + 1, char);
if (filename == 0) {
infofree (info);
return 0;
}
strcpy (filename, sapdb_keyname);
strcat (filename, "/");
strcat (filename, sapdb_ininame);
fd = open (filename , O_RDONLY);
Safefree (filename);
if (fd >= 0) {
for (i = 0;; i++) {
if (enum_db (fd, "Databases", &mydbname, &dbswdir, i) == 0)
break;
myparamfile = get_paramfile (datadir, mydbname);
curr = 0;
if (mydbname != 0 && myparamfile != 0) {
curr = infoadd (curr, "dbname", mydbname);
curr = infoadd (curr, "dbswdir", dbswdir);
curr = infoadd (curr, "paramfile", myparamfile);
curr = infoadd (curr, "dbowner",
get_dbowner (datadir, mydbname));
}
if (curr != 0)
info = infoadd (info, "db", (char *) curr);
}
close (fd);
}
}
return (info);
}
#endif
#ifdef WIN32
static const char sapdb_key[] = "SOFTWARE\\SAP\\SAP DBTech";
static const char services_key[] ="SYSTEM\\CurrentControlSet\\Services";
static const char key_prefix[] = "SAP DBTech-";
static int
enum_db (const HKEY their, const char *section, char **pkey, int idx) {
FILETIME ft[1];
HKEY our;
DWORD len;
char *key;
int prefix_len;
int i;
int j;
char buff[1024];
prefix_len = strlen (key_prefix);
if (RegOpenKeyEx (their, section, 0, KEY_ENUMERATE_SUB_KEYS, &our) != ERROR_SUCCESS)
return 0;
i = 0;
for (j = 0;; j++) {
if (i > idx)
break;
len = sizeof (buff);
if (RegEnumKeyEx (our, j, buff, &len, 0, 0, 0, ft) != ERROR_SUCCESS) {
RegCloseKey (our);
return 0;
}
if (memcmp (buff, key_prefix, prefix_len) != 0)
continue;
if (buff[prefix_len] == '.')
continue;
if (buff[prefix_len] == '_')
continue;
i++;
}
RegCloseKey (our);
New (101, key, strlen (buff) + 1 - prefix_len, char);
if (key == 0)
return 0;
strcpy (key, &buff[prefix_len]);
*pkey = key;
return 1;
}
static char *
get_value (const HKEY their, const char *section, const char *key) {
HKEY our;
DWORD type;
DWORD len;
char *value;
char buffer[32 * 1024];
if (RegOpenKeyEx (their, section, 0, KEY_QUERY_VALUE, &our) != ERROR_SUCCESS)
return 0;
if (RegQueryValueEx (our, key, 0 , &type, 0, &len) != ERROR_SUCCESS) {
RegCloseKey (our);
return 0;
}
New (101, value, len+1, char);
if (value == 0) {
RegCloseKey (our);
return 0;
}
if (RegQueryValueEx (our, key, 0 , &type, value, &len) != ERROR_SUCCESS) {
RegCloseKey (our);
return 0;
}
RegCloseKey (our);
switch (type) {
case REG_SZ:
return (value);
case REG_EXPAND_SZ:
ExpandEnvironmentStrings (value, buffer, sizeof (buffer));
Safefree (value);
New (101, value, strlen (buffer) + 1, char);
if (value == 0)
return 0;
strcpy (value, buffer);
return (value);
}
return 0;
}
static char *
get_dbowner (char *dbname) {
char *owner;
char *key_name;
if (dbname == 0 || dbname[0] == '\0')
return 0;
New (101, key_name, strlen (services_key) + 1 +
strlen (key_prefix) + strlen (dbname) + 1, char);
if (key_name == 0)
return 0;
strcpy (key_name, services_key);
strcat (key_name, "\\");
strcat (key_name, key_prefix);
strcat (key_name, dbname);
owner = get_value (HKEY_LOCAL_MACHINE, key_name, "ObjectName");
Safefree (key_name);
if (owner == 0)
return 0;
if (owner[0] == '\0') {
Safefree (owner);
return 0;
}
return (owner);
}
static char *
get_paramfile (char *datadir, char *dbswdir, char *dbname) {
char subdirname[] = "config";
char *filename;
Stat_t statbuff[1];
int rc;
filename = 0;
/* first look in <sapdbdata>\config if <sapdbdata> is known */
if (datadir != 0 && datadir[0] != '\0') {
New (101, filename, strlen (datadir) + 1 +
strlen (subdirname) + 1 + strlen (dbname) + 1, char);
if (filename == 0)
return 0;
strcpy (filename, datadir);
strcat (filename, "\\");
strcat (filename, subdirname);
strcat (filename, "\\");
strcat (filename, dbname);
rc = stat (filename, statbuff);
}
if (rc == 0)
return (filename);
if (filename != 0) {
Safefree (filename);
filename = 0;
}
/* look in dbswdir\config, maybe DBROOT installation */
if (rc != 0 && errno == ENOENT && dbswdir != 0 && dbswdir[0] != '\0') {
New (101, filename, strlen (dbswdir) + 1 +
strlen (subdirname) + 1 + strlen (dbname) + 1, char);
if (filename == 0)
return 0;
strcpy (filename, dbswdir);
strcat (filename, "\\");
strcat (filename, subdirname);
strcat (filename, "\\");
strcat (filename, dbname);
rc = stat (filename, statbuff);
}
if (rc == 0)
return (filename);
if (filename != 0)
Safefree (filename);
return 0;
}
static char *
get_dbswdir (char *dbname) {
int i;
char *ptr;
char *image_name;
char *key_name;
if (dbname == 0 || dbname[0] == '\0')
return 0;
New (101, key_name,
strlen (services_key) + 1 +
strlen (key_prefix) + strlen (dbname) + 1, char);
if (key_name == 0)
return 0;
strcpy (key_name, services_key);
strcat (key_name, "\\");
strcat (key_name, key_prefix);
strcat (key_name, dbname);
image_name = get_value (HKEY_LOCAL_MACHINE, key_name, "ImagePath");
if (image_name == 0)
return 0;
for (i = 0; i <= 1; i++) {
ptr = strrchr (image_name, '\\');
if (ptr == 0) {
Safefree (image_name);
return 0;
}
*ptr = '\0';
}
if (image_name[0] == '\0') {
Safefree (image_name);
return 0;
}
New (101, ptr, strlen (image_name) + 1, char);
if (ptr == 0) {
Safefree (image_name);
return 0;
}
strcpy (ptr, image_name);
Safefree (image_name);
return (ptr);
}
static info_t *
get_instinfo (char *dbname) {
info_t *info;
info_t *curr;
char *datadir;
datadir = get_value (HKEY_LOCAL_MACHINE, sapdb_key, "IndepData");
info = 0;
info = infoadd (info, "datadir", datadir);
info = infoadd (info, "progdir",
get_value (HKEY_LOCAL_MACHINE, sapdb_key, "IndepPrograms"));
if (dbname != 0 && dbname[0] != '\0') {
char *mydbname;
char *mydbswdir;
char *myparamfile;
New (101, mydbname, strlen (dbname) + 1, char);
if (mydbname != 0)
strcpy (mydbname, dbname);
mydbswdir = get_dbswdir (dbname);
myparamfile = get_paramfile (datadir, mydbswdir, mydbname);;
curr = 0;
if (mydbname != 0 && myparamfile != 0) {
curr = infoadd (curr, "dbname", mydbname);
curr = infoadd (curr, "dbswdir", mydbswdir);
curr = infoadd (curr, "dbowner", get_dbowner (mydbname));
curr = infoadd (curr, "paramfile", myparamfile);
}
if (curr != 0)
info = infoadd (info, "db", (char *) curr);
} else {
int i;
for (i = 0;; i++) {
char *mydbname=NULL;
char *mydbswdir=NULL;
char *myparamfile=NULL;
if (enum_db (HKEY_LOCAL_MACHINE, services_key, &mydbname, i) == 0)
break;
if (mydbname != 0) {
mydbswdir = get_dbswdir (mydbname);
myparamfile = get_paramfile (datadir, mydbswdir, mydbname);
}
curr = 0;
if (mydbname != 0 && myparamfile != 0) {
curr = infoadd (curr, "dbname", mydbname);
curr = infoadd (curr, "dbswdir", mydbswdir);
curr = infoadd (curr, "dbowner", get_dbowner (mydbname));
curr = infoadd (curr, "paramfile", myparamfile);
}
if (curr != 0)
info = infoadd (info, "db", (char *) curr);
}
}
return (info);
}
#endif
/*
* will return a structure like this or undef
*
* ref-+->progdir
* |
* +->datadir
* |
* +->user
* |
* +->group
* |
* +->database-+->SID0-+->dbname
* | |
* | +->dbowner
* | |
* | +->dbswdir
* |
* +->SID1-+->dbname
* | |
* | +->dbowner
* | |
* | +->dbswdir
* ...
*
* expects one parameter,
* this is the name of the database we are looking for
*
* if no parameter is given,
* it will look for all know database instances
*/
DBISTATE_DECLARE;
/*
* The source code of the package BD::MaxDB::util is taken from
* MaxDB's installation tool sdbinst.
*
* :install56\perl\sdbrun\InstInfo.xs
*
* Thanks to ChristophB
*/
MODULE = DBD::MaxDB PACKAGE = DBD::MaxDB::InstInfo
PROTOTYPES: DISABLE
void
new (...)
PREINIT:
char *dbname;
info_t *info;
info_t *curr0;
info_t *curr1;
HV *hv0;
HV *hv1;
HV *hv2;
SV *rv;
PPCODE:
if (items >= 2)
XSRETURN_UNDEF;
dbname = 0;
if (items == 1 && SvPOKp (ST(0)))
dbname = (char *) SvPV (ST(0), PL_na);
info = get_instinfo (dbname);
if (info == 0)
XSRETURN_UNDEF;
hv0 = newHV ();
hv1 = 0;
for (curr0 = info; curr0 != 0; curr0 = curr0->next) {
if (curr0->key == 0)
continue;
if (strcmp (curr0->key, "db") == 0) {
if (curr0->val == 0)
continue;
if (hv1 == 0)
hv1 = newHV ();
hv2 = newHV ();
for (curr1 = (info_t *)(curr0->val); curr1 != 0; curr1 = curr1->next) {
if (curr1->key == 0)
continue;
if (strcmp (curr1->key, "dbname") == 0) {
New (101, dbname, strlen (curr1->val) + 1, char);
if (dbname == 0)
break;
strcpy (dbname, curr1->val);
}
if (curr1->val == 0) {
hv_store (
hv2, curr1->key, strlen (curr1->key),
newSVpv ("", 0), 0);
continue;
}
if (strcmp (curr1->key, "dbswdir") == 0 ||
strcmp (curr1->key, "paramfile") == 0) {
char *ptr;
for (ptr = curr1->val; *ptr != 0; ptr++)
if (*ptr == '\\')
*ptr = '/';
}
hv_store (
hv2, curr1->key, strlen (curr1->key),
newSVpv (curr1->val, strlen (curr1->val)), 0);
}
rv = newRV ((SV *) hv2);
SvREFCNT_dec (hv2);
hv_store (hv1, dbname, strlen (dbname), rv, 0);
Safefree (dbname);
continue;
}
if (curr0->val == 0) {
hv_store (
hv0, curr0->key, strlen (curr0->key),
newSVpv ("", 0), 0);
continue;
}
if (strcmp (curr0->key, "progdir") == 0 ||
strcmp (curr0->key, "datadir") == 0 ||
strcmp (curr0->key, "uid") == 0 ||
strcmp (curr0->key, "gid") == 0 ||
strcmp (curr0->key, "user") == 0 ||
strcmp (curr0->key, "group") == 0) {
char *ptr;
for (ptr = curr0->val; *ptr != 0; ptr++)
if (*ptr == '\\')
*ptr = '/';
}
hv_store (
hv0, curr0->key, strlen (curr0->key),
newSVpv (curr0->val, strlen (curr0->val)), 0);
}
if (hv1 != 0) {
rv = newRV ((SV *) hv1);
SvREFCNT_dec (hv1);
hv_store (hv0, "database", 8, rv, 0);
}
infofree (info);
rv = sv_2mortal (newRV ((SV *) hv0));
SvREFCNT_dec (hv0);
XPUSHs (rv);
XSRETURN (1);
MODULE = DBD::MaxDB PACKAGE = DBD::MaxDB
INCLUDE: MaxDB.xsi
MODULE = DBD::MaxDB PACKAGE = DBD::MaxDB::dr
MODULE = DBD::MaxDB PACKAGE = DBD::MaxDB::db
void
_ping(dbh)
SV * dbh
CODE:
ST(0) = dbd_maxdb_db_ping(dbh)? &sv_yes : &sv_no;
void
_isunicode(dbh)
SV * dbh
CODE:
ST(0) = dbd_maxdb_db_isunicode(dbh)? &sv_yes : &sv_no;
void
_getSQLMode(dbh)
SV * dbh
CODE:
ST(0) = dbd_maxdb_db_getSQLMode(dbh);
void
_getVersion(dbh)
SV * dbh
CODE:
ST(0) = dbd_maxdb_db_getVersion(dbh);
void
_executeUpdate( dbh, stmt )
SV * dbh
SV * stmt
CODE:
{
ST(0) = sv_2mortal(newSViv((IV)dbd_maxdb_db_executeUpdate(dbh, stmt)));
}
MODULE = DBD::MaxDB PACKAGE = DBD::MaxDB::st
void
_Cancel(sth)
SV * sth
CODE:
ST(0) = dbd_maxdb_st_cancel(sth);
void
_executeInternal( dbh, sth, stmt )
SV * dbh
SV* sth
SV * stmt
CODE:
{
STRLEN lna;
char *pstmt = SvOK(stmt) ? SvPV(stmt,lna) : "";
ST(0) = sv_2mortal(newSViv((IV)dbd_maxdb_db_executeInternal(dbh, sth, pstmt)));
}