Commit f6ca3b05 authored by Olivier Bertrand's avatar Olivier Bertrand

Bug fixed: Column charset were not handled on read.

Modified: ha_connect.cc (MakeRecord)

Moved PlgAllocResult to plgdbutl.cpp
Modified:
mycat.cpp
plgdbutl.cpp

Continuing implementing the "catalog" tables (ex "info").
Already existing were the ODBC data source table and the
WMI column info table.

The common way to handle them was modified to enable each
table types to send personalized data.

Now takes care of all existing catalog functions for table
types that can retrieve and use such information.

Modified:
ha_connect.cc
odbconn.cpp
tabodbc.h
tabodbc.cpp
tabfmt.h
tabfmt.cpp
tabmysql.h
tabmysql.cpp
tabwmi.h
tabwmi.cpp
myconn.h
myconn.cpp
filamdbf.cpp
plgdbsem.h
reldef.h
reldef.cpp
tabdos.h
tabdos.cpp
tabfix.h
xtable.h
table.cpp
parent b93db097
...@@ -48,8 +48,6 @@ ...@@ -48,8 +48,6 @@
/***********************************************************************/ /***********************************************************************/
#include "global.h" #include "global.h"
#include "plgdbsem.h" #include "plgdbsem.h"
//#include "catalog.h"
//#include "kindex.h"
#include "filamdbf.h" #include "filamdbf.h"
#include "tabdos.h" #include "tabdos.h"
#include "valblk.h" #include "valblk.h"
...@@ -65,12 +63,6 @@ ...@@ -65,12 +63,6 @@
#define DBFTYPE 3 /* value of bits 0 and 1 if .dbf */ #define DBFTYPE 3 /* value of bits 0 and 1 if .dbf */
#define EOH 0x0D /* end-of-header marker in .dbf file */ #define EOH 0x0D /* end-of-header marker in .dbf file */
/****************************************************************************/
/* Catalog utility function. */
/****************************************************************************/
PQRYRES PlgAllocResult(PGLOBAL, int, int, int, int *, int *,
unsigned int *, bool blank = true, bool nonull = false);
extern "C" int trace; // The general trace value extern "C" int trace; // The general trace value
/****************************************************************************/ /****************************************************************************/
...@@ -190,6 +182,8 @@ PQRYRES DBFColumns(PGLOBAL g, char *fn, BOOL info) ...@@ -190,6 +182,8 @@ PQRYRES DBFColumns(PGLOBAL g, char *fn, BOOL info)
DB_INT, DB_INT, DB_SHORT}; DB_INT, DB_INT, DB_SHORT};
static int buftyp[] = {TYPE_STRING, TYPE_SHORT, TYPE_STRING, static int buftyp[] = {TYPE_STRING, TYPE_SHORT, TYPE_STRING,
TYPE_INT, TYPE_INT, TYPE_SHORT}; TYPE_INT, TYPE_INT, TYPE_SHORT};
static XFLD fldtyp[] = {FLD_NAME, FLD_TYPE, FLD_TYPENAME,
FLD_PREC, FLD_LENGTH, FLD_SCALE};
static unsigned int length[] = {11, 6, 8, 10, 10, 6}; static unsigned int length[] = {11, 6, 8, 10, 10, 6};
char buf[2], filename[_MAX_PATH]; char buf[2], filename[_MAX_PATH];
int ncol = sizeof(dbtype) / sizeof(int); int ncol = sizeof(dbtype) / sizeof(int);
...@@ -204,35 +198,41 @@ PQRYRES DBFColumns(PGLOBAL g, char *fn, BOOL info) ...@@ -204,35 +198,41 @@ PQRYRES DBFColumns(PGLOBAL g, char *fn, BOOL info)
if (trace) if (trace)
htrc("DBFColumns: File %s\n", SVP(fn)); htrc("DBFColumns: File %s\n", SVP(fn));
if (!info) {
if (!fn) { if (!fn) {
strcpy(g->Message, MSG(MISSING_FNAME)); strcpy(g->Message, MSG(MISSING_FNAME));
return NULL; return NULL;
} // endif fn } // endif fn
/**************************************************************************/ /************************************************************************/
/* Open the input file. */ /* Open the input file. */
/**************************************************************************/ /************************************************************************/
PlugSetPath(filename, fn, PlgGetDataPath(g)); PlugSetPath(filename, fn, PlgGetDataPath(g));
if (!(infile= global_fopen(g, MSGID_CANNOT_OPEN, filename, "rb"))) if (!(infile= global_fopen(g, MSGID_CANNOT_OPEN, filename, "rb")))
return NULL; return NULL;
/**************************************************************************/ /************************************************************************/
/* Get the first 32 bytes of the header. */ /* Get the first 32 bytes of the header. */
/**************************************************************************/ /************************************************************************/
if ((rc = dbfhead(g, infile, filename, &mainhead)) == RC_FX) { if ((rc = dbfhead(g, infile, filename, &mainhead)) == RC_FX) {
fclose(infile); fclose(infile);
return NULL; return NULL;
} // endif dbfhead } // endif dbfhead
/**************************************************************************/ /************************************************************************/
/* Allocate the structures used to refer to the result set. */ /* Allocate the structures used to refer to the result set. */
/**************************************************************************/ /************************************************************************/
//fields = (mainhead.Headlen - 33) / 32;
fields = mainhead.Fields; fields = mainhead.Fields;
} else
fields = 0;
qrp = PlgAllocResult(g, ncol, fields, IDS_COLUMNS + 3, qrp = PlgAllocResult(g, ncol, fields, IDS_COLUMNS + 3,
dbtype, buftyp, length); dbtype, buftyp, fldtyp, length, true, false);
qrp->Info = info || (rc == RC_INFO); //qrp->Info = info || (rc == RC_INFO);
if (info)
return qrp;
if (trace) { if (trace) {
htrc("Structure of %s\n", filename); htrc("Structure of %s\n", filename);
...@@ -316,6 +316,7 @@ PQRYRES DBFColumns(PGLOBAL g, char *fn, BOOL info) ...@@ -316,6 +316,7 @@ PQRYRES DBFColumns(PGLOBAL g, char *fn, BOOL info)
qrp->Nblin = field; qrp->Nblin = field;
fclose(infile); fclose(infile);
#if 0
if (info) { if (info) {
/************************************************************************/ /************************************************************************/
/* Prepare return message for dbfinfo command. */ /* Prepare return message for dbfinfo command. */
...@@ -330,6 +331,7 @@ PQRYRES DBFColumns(PGLOBAL g, char *fn, BOOL info) ...@@ -330,6 +331,7 @@ PQRYRES DBFColumns(PGLOBAL g, char *fn, BOOL info)
strcat(g->Message, buf); strcat(g->Message, buf);
} // endif info } // endif info
#endif // 0
/**************************************************************************/ /**************************************************************************/
/* Return the result pointer for use by GetData routines. */ /* Return the result pointer for use by GetData routines. */
......
...@@ -138,10 +138,6 @@ ...@@ -138,10 +138,6 @@
#define my_strlwr(p) my_casedn_str(default_charset_info, (p)); #define my_strlwr(p) my_casedn_str(default_charset_info, (p));
#define my_stricmp(a,b) my_strcasecmp(default_charset_info, (a), (b)) #define my_stricmp(a,b) my_strcasecmp(default_charset_info, (a), (b))
#if defined (WIN32)
typedef struct _WMIutil *PWMIUT; /* Used to call WMIColumns */
#endif
#ifdef LIBXML2_SUPPORT #ifdef LIBXML2_SUPPORT
void XmlInitParserLib(void); void XmlInitParserLib(void);
void XmlCleanupParserLib(void); void XmlCleanupParserLib(void);
...@@ -1379,9 +1375,6 @@ int ha_connect::MakeRecord(char *buf) ...@@ -1379,9 +1375,6 @@ int ha_connect::MakeRecord(char *buf)
// This is for variable_length rows // This is for variable_length rows
memset(buf, 0, table->s->null_bytes); memset(buf, 0, table->s->null_bytes);
// store needs a charset, why not this one?
charset= table->s->table_charset;
// When sorting read_set selects all columns, so we use def_read_set // When sorting read_set selects all columns, so we use def_read_set
map= (const MY_BITMAP *)&table->def_read_set; map= (const MY_BITMAP *)&table->def_read_set;
...@@ -1389,6 +1382,9 @@ int ha_connect::MakeRecord(char *buf) ...@@ -1389,6 +1382,9 @@ int ha_connect::MakeRecord(char *buf)
for (field= table->field; *field && !rc; field++) { for (field= table->field; *field && !rc; field++) {
fp= *field; fp= *field;
// Default charset
charset= table->s->table_charset;
#if defined(MARIADB) #if defined(MARIADB)
if (fp->vcol_info && !fp->stored_in_db) if (fp->vcol_info && !fp->stored_in_db)
continue; // This is a virtual column continue; // This is a virtual column
...@@ -1409,7 +1405,8 @@ int ha_connect::MakeRecord(char *buf) ...@@ -1409,7 +1405,8 @@ int ha_connect::MakeRecord(char *buf)
value= colp->GetValue(); value= colp->GetValue();
// All this could be better optimized // All this could be better optimized
if (value->GetType() == TYPE_DATE) { switch (value->GetType()) {
case TYPE_DATE:
if (!sdval) if (!sdval)
sdval= AllocateValue(xp->g, TYPE_STRING, 20); sdval= AllocateValue(xp->g, TYPE_STRING, 20);
...@@ -1427,10 +1424,16 @@ int ha_connect::MakeRecord(char *buf) ...@@ -1427,10 +1424,16 @@ int ha_connect::MakeRecord(char *buf)
// Get date in the format required by MySQL fields // Get date in the format required by MySQL fields
value->FormatValue(sdval, fmt); value->FormatValue(sdval, fmt);
p= sdval->GetCharValue(); p= sdval->GetCharValue();
} else if (value->GetType() == TYPE_FLOAT) break;
case TYPE_FLOAT:
p= NULL; p= NULL;
else break;
case TYPE_STRING:
charset= fp->charset();
// Passthru
default:
p= value->GetCharString(val); p= value->GetCharString(val);
} // endswitch Type
if (p) { if (p) {
if (fp->store(p, strlen(p), charset, CHECK_FIELD_WARN)) { if (fp->store(p, strlen(p), charset, CHECK_FIELD_WARN)) {
...@@ -3253,17 +3256,20 @@ bool ha_connect::add_fields(THD *thd, void *alt_info, ...@@ -3253,17 +3256,20 @@ bool ha_connect::add_fields(THD *thd, void *alt_info,
*/ */
bool ha_connect::pre_create(THD *thd, void *crt_info, void *alt_info) bool ha_connect::pre_create(THD *thd, void *crt_info, void *alt_info)
{ {
char ttp= '?', spc= ',', qch= 0, fnc= 0; char ttp= '?', spc= ',', qch= 0, fnc= '*';
const char *typn= "DOS"; const char *typn= "?";
const char *user; const char *user;
char *fn, *dsn, *tab, *db, *host, *pwd, *prt, *sep; char *fn, *dsn, *tab, *db, *host, *pwd, *prt, *sep, *csn;
#if defined(WIN32) #if defined(WIN32)
char *nsp= NULL, *cls= NULL; char *nsp= NULL, *cls= NULL;
#endif // WIN32 #endif // WIN32
char *supfnc = "*C";
int port= MYSQL_PORT, hdr= 0, mxr= 0; int port= MYSQL_PORT, hdr= 0, mxr= 0;
uint tm;
bool b= false, ok= false, dbf= false; bool b= false, ok= false, dbf= false;
LEX_STRING *comment, *name; LEX_STRING *comment, *name;
HA_CREATE_INFO *create_info= (HA_CREATE_INFO *)crt_info; HA_CREATE_INFO *create_info= (HA_CREATE_INFO *)crt_info;
CHARSET_INFO *cs;
engine_option_value *pov; engine_option_value *pov;
PQRYRES qrp; PQRYRES qrp;
PCOLRES crp; PCOLRES crp;
...@@ -3325,6 +3331,7 @@ bool ha_connect::pre_create(THD *thd, void *crt_info, void *alt_info) ...@@ -3325,6 +3331,7 @@ bool ha_connect::pre_create(THD *thd, void *crt_info, void *alt_info)
else else
ok= true; ok= true;
supfnc = "*CTSD";
break; break;
#endif // ODBC_SUPPORT #endif // ODBC_SUPPORT
case 'A': // DBF case 'A': // DBF
...@@ -3354,6 +3361,13 @@ bool ha_connect::pre_create(THD *thd, void *crt_info, void *alt_info) ...@@ -3354,6 +3361,13 @@ bool ha_connect::pre_create(THD *thd, void *crt_info, void *alt_info)
sprintf(g->Message, "Cannot get column info for table type %s", typn); sprintf(g->Message, "Cannot get column info for table type %s", typn);
} // endif ttp } // endif ttp
// Check for supported catalog function
if (ok && !strchr(supfnc, fnc)) {
sprintf(g->Message, "Unsupported catalog function %c for table type %s",
fnc, typn);
ok= false;
} // endif supfnc
if (ok) { if (ok) {
char *length, *decimals, *cnm, *rem; char *length, *decimals, *cnm, *rem;
int i, len, dec; int i, len, dec;
...@@ -3368,7 +3382,7 @@ bool ha_connect::pre_create(THD *thd, void *crt_info, void *alt_info) ...@@ -3368,7 +3382,7 @@ bool ha_connect::pre_create(THD *thd, void *crt_info, void *alt_info)
switch (ttp) { switch (ttp) {
case 'A': case 'A':
qrp= DBFColumns(g, fn, false); qrp= DBFColumns(g, fn, fnc == 'C');
break; break;
#if defined(ODBC_SUPPORT) #if defined(ODBC_SUPPORT)
case 'O': case 'O':
...@@ -3394,15 +3408,16 @@ bool ha_connect::pre_create(THD *thd, void *crt_info, void *alt_info) ...@@ -3394,15 +3408,16 @@ bool ha_connect::pre_create(THD *thd, void *crt_info, void *alt_info)
#endif // ODBC_SUPPORT #endif // ODBC_SUPPORT
#if defined(MYSQL_SUPPORT) #if defined(MYSQL_SUPPORT)
case 'Y': case 'Y':
qrp= MyColumns(g, host, db, user, pwd, tab, NULL, port, false); qrp= MyColumns(g, host, db, user, pwd, tab,
NULL, port, false, fnc == 'C');
break; break;
#endif // MYSQL_SUPPORT #endif // MYSQL_SUPPORT
case 'C': case 'C':
qrp= CSVColumns(g, fn, spc, qch, hdr, mxr); qrp= CSVColumns(g, fn, spc, qch, hdr, mxr, fnc == 'C');
break; break;
#if defined(WIN32) #if defined(WIN32)
case 'W': case 'W':
qrp= WMIColumns(g, nsp, cls, NULL); qrp= WMIColumns(g, nsp, cls, fnc == 'C');
break; break;
#endif // WIN32 #endif // WIN32
} // endswitch ttp } // endswitch ttp
...@@ -3412,7 +3427,8 @@ bool ha_connect::pre_create(THD *thd, void *crt_info, void *alt_info) ...@@ -3412,7 +3427,8 @@ bool ha_connect::pre_create(THD *thd, void *crt_info, void *alt_info)
return true; return true;
} // endif qrp } // endif qrp
if (fnc) { if (fnc && fnc != '*') {
// Catalog table
for (crp=qrp->Colresp; !b && crp; crp= crp->Next) { for (crp=qrp->Colresp; !b && crp; crp= crp->Next) {
cnm= encode(g, crp->Name); cnm= encode(g, crp->Name);
name= thd->make_lex_string(NULL, cnm, strlen(cnm), true); name= thd->make_lex_string(NULL, cnm, strlen(cnm), true);
...@@ -3425,39 +3441,60 @@ bool ha_connect::pre_create(THD *thd, void *crt_info, void *alt_info) ...@@ -3425,39 +3441,60 @@ bool ha_connect::pre_create(THD *thd, void *crt_info, void *alt_info)
// Now add the field // Now add the field
b= add_fields(thd, alt_info, name, type, length, decimals, b= add_fields(thd, alt_info, name, type, length, decimals,
0, comment, NULL, NULL, NULL); NOT_NULL_FLAG, comment, NULL, NULL, NULL);
} // endfor crp } // endfor crp
} else } else // Not a catalog table
for (i= 0; !b && i < qrp->Nblin; i++) { for (i= 0; !b && i < qrp->Nblin; i++) {
crp= qrp->Colresp; // Column Name rem= "";
length= "";
decimals= NULL;
tm= NOT_NULL_FLAG;
cs= NULL;
for (crp= qrp->Colresp; crp; crp= crp->Next)
switch (crp->Fld) {
case FLD_NAME:
cnm= encode(g, crp->Kdata->GetCharValue(i)); cnm= encode(g, crp->Kdata->GetCharValue(i));
name= thd->make_lex_string(NULL, cnm, strlen(cnm), true); name= thd->make_lex_string(NULL, cnm, strlen(cnm), true);
crp= crp->Next; // Data Type break;
case FLD_TYPE:
type= PLGtoMYSQL(crp->Kdata->GetIntValue(i), true); type= PLGtoMYSQL(crp->Kdata->GetIntValue(i), true);
crp= crp->Next; // Type Name break;
crp= crp->Next; // Precision (length) case FLD_PREC:
len= crp->Kdata->GetIntValue(i); len= crp->Kdata->GetIntValue(i);
length= (char*)PlugSubAlloc(g, NULL, 8); length= (char*)PlugSubAlloc(g, NULL, 8);
sprintf(length, "%d", len); sprintf(length, "%d", len);
crp= crp->Next; // Length break;
crp= crp->Next; // Scale (precision) case FLD_SCALE:
if ((dec= crp->Kdata->GetIntValue(i))) { if ((dec= crp->Kdata->GetIntValue(i))) {
decimals= (char*)PlugSubAlloc(g, NULL, 8); decimals= (char*)PlugSubAlloc(g, NULL, 8);
sprintf(decimals, "%d", dec); sprintf(decimals, "%d", dec);
} else } else
decimals= NULL; decimals= NULL;
if ((crp= crp->Next) && // Remark (comment) break;
(rem= crp->Kdata->GetCharValue(i))) case FLD_NULL:
if (crp->Kdata->GetIntValue(i))
tm= 0; // Nullable
break;
case FLD_REM:
rem= crp->Kdata->GetCharValue(i);
break;
// case FLD_CHARSET:
// No good because remote table is already translated
// if (*(csn= crp->Kdata->GetCharValue(i)))
// cs= get_charset_by_name(csn, 0);
// break;
} // endswitch Fld
comment= thd->make_lex_string(NULL, rem, strlen(rem), true); comment= thd->make_lex_string(NULL, rem, strlen(rem), true);
else
comment= thd->make_lex_string(NULL, "", 0, true);
// Now add the field // Now add the field
b= add_fields(thd, alt_info, name, type, length, decimals, b= add_fields(thd, alt_info, name, type, length, decimals,
0, comment, NULL, NULL, NULL); tm, comment, cs, NULL, NULL);
} // endfor i } // endfor i
return b; return b;
......
...@@ -100,84 +100,9 @@ extern int xtrace; ...@@ -100,84 +100,9 @@ extern int xtrace;
/**************************************************************************/ /**************************************************************************/
//bool PlugCheckPattern(PGLOBAL, LPCSTR, LPCSTR); //bool PlugCheckPattern(PGLOBAL, LPCSTR, LPCSTR);
//#if !defined(WIN32) //#if !defined(WIN32)
extern "C" int GetRcString(int id, char *buf, int bufsize);
//#endif // !WIN32 //#endif // !WIN32
//void ptrc(char const *fmt, ...); //void ptrc(char const *fmt, ...);
/**************************************************************************/
/* Allocate the result structure that will contain result data. */
/**************************************************************************/
PQRYRES PlgAllocResult(PGLOBAL g, int ncol, int maxres, int ids,
int *dbtype, int *buftyp, unsigned int *length,
bool blank = false, bool nonull = false)
{
char cname[NAM_LEN+1];
int i;
PCOLRES *pcrp, crp;
PQRYRES qrp;
/************************************************************************/
/* Allocate the structure used to contain the result set. */
/************************************************************************/
qrp = (PQRYRES)PlugSubAlloc(g, NULL, sizeof(QRYRES));
pcrp = &qrp->Colresp;
qrp->Continued = false;
qrp->Truncated = false;
qrp->Info = false;
qrp->Suball = true;
qrp->Maxres = maxres;
qrp->Maxsize = 0;
qrp->Nblin = 0;
qrp->Nbcol = 0; // will be ncol
qrp->Cursor = 0;
qrp->BadLines = 0;
for (i = 0; i < ncol; i++) {
*pcrp = (PCOLRES)PlugSubAlloc(g, NULL, sizeof(COLRES));
crp = *pcrp;
pcrp = &crp->Next;
crp->Colp = NULL;
crp->Ncol = ++qrp->Nbcol;
crp->Type = buftyp[i];
crp->Length = length[i];
crp->Clen = GetTypeSize(crp->Type, length[i]);
crp->Prec = 0;
crp->DBtype = dbtype[i];
if (ids > 0) {
#if defined(XMSG)
// Get header from message file
strncpy(cname, PlugReadMessage(g, ids + crp->Ncol, NULL), NAM_LEN);
cname[NAM_LEN] = 0; // for truncated long names
//#elif defined(WIN32)
// Get header from ressource file
// LoadString(s_hModule, ids + crp->Ncol, cname, sizeof(cname));
#else // !WIN32
GetRcString(ids + crp->Ncol, cname, sizeof(cname));
#endif // !WIN32
crp->Name = (PSZ)PlugSubAlloc(g, NULL, strlen(cname) + 1);
strcpy(crp->Name, cname);
} else
crp->Name = NULL; // Will be set by caller
// Allocate the Value Block that will contain data
if (crp->Length || nonull)
crp->Kdata = AllocValBlock(g, NULL, crp->Type, maxres,
crp->Length, 0, true, blank);
else
crp->Kdata = NULL;
if (g->Trace)
htrc("Column(%d) %s type=%d len=%d value=%p\n",
crp->Ncol, crp->Name, crp->Type, crp->Length, crp->Kdata);
} // endfor i
*pcrp = NULL;
return qrp;
} // end of PlgAllocResult
/***********************************************************************/ /***********************************************************************/
/* Get a unique char identifier for types. The letter used are: */ /* Get a unique char identifier for types. The letter used are: */
/* ABCDEF..I.KLM.O..R.T.VWXY.. */ /* ABCDEF..I.KLM.O..R.T.VWXY.. */
...@@ -345,14 +270,14 @@ char *MYCAT::GetStringCatInfo(PGLOBAL g, PSZ name, PSZ what, PSZ sdef) ...@@ -345,14 +270,14 @@ char *MYCAT::GetStringCatInfo(PGLOBAL g, PSZ name, PSZ what, PSZ sdef)
/***********************************************************************/ /***********************************************************************/
int MYCAT::GetColCatInfo(PGLOBAL g, PTABDEF defp) int MYCAT::GetColCatInfo(PGLOBAL g, PTABDEF defp)
{ {
char *type= GetStringCatInfo(g, NULL, "Type", "DOS"); char tc, *type= GetStringCatInfo(g, NULL, "Type", "DOS");
int i, loff, poff, nof, nlg; int i, loff, poff, nof, nlg;
void *field= NULL; void *field= NULL;
PCOLDEF cdp, lcdp= NULL, tocols= NULL; PCOLDEF cdp, lcdp= NULL, tocols= NULL;
PCOLINFO pcf= (PCOLINFO)PlugSubAlloc(g, NULL, sizeof(COLINFO)); PCOLINFO pcf= (PCOLINFO)PlugSubAlloc(g, NULL, sizeof(COLINFO));
// Get a unique char identifier for type // Get a unique char identifier for type
char tc= GetTypeID(type); tc= (!defp->Catfunc) ? GetTypeID(type) : 0;
// Take care of the column definitions // Take care of the column definitions
i= poff= nof= nlg= 0; i= poff= nof= nlg= 0;
......
This diff is collapsed.
...@@ -38,7 +38,7 @@ typedef class MYSQLC *PMYC; ...@@ -38,7 +38,7 @@ typedef class MYSQLC *PMYC;
PQRYRES MyColumns(PGLOBAL g, const char *host, const char *db, PQRYRES MyColumns(PGLOBAL g, const char *host, const char *db,
const char *user, const char *pwd, const char *user, const char *pwd,
const char *table, const char *colpat, const char *table, const char *colpat,
int port, bool key); int port, bool key, bool info);
/* -------------------------- MYCONN class --------------------------- */ /* -------------------------- MYCONN class --------------------------- */
......
...@@ -171,13 +171,6 @@ int TranslateSQLType(int stp, int prec, int& len) ...@@ -171,13 +171,6 @@ int TranslateSQLType(int stp, int prec, int& len)
HENV ODBConn::m_henv = SQL_NULL_HENV; HENV ODBConn::m_henv = SQL_NULL_HENV;
int ODBConn::m_nAlloc = 0; // per-Appl reference to HENV above int ODBConn::m_nAlloc = 0; // per-Appl reference to HENV above
/**************************************************************************/
/* Allocate the result structure that will contain result data. */
/**************************************************************************/
PQRYRES PlgAllocResult(PGLOBAL g, int ncol, int maxres, int ids,
int *dbtype, int *buftyp, unsigned int *length,
bool blank = true, bool nonull = true);
/***********************************************************************/ /***********************************************************************/
/* Allocate the structure used to refer to the result set. */ /* Allocate the structure used to refer to the result set. */
/***********************************************************************/ /***********************************************************************/
...@@ -243,6 +236,10 @@ PQRYRES ODBCColumns(PGLOBAL g, ODBConn *ocp, char *dsn, char *table, ...@@ -243,6 +236,10 @@ PQRYRES ODBCColumns(PGLOBAL g, ODBConn *ocp, char *dsn, char *table,
TYPE_STRING, TYPE_SHORT, TYPE_STRING, TYPE_STRING, TYPE_SHORT, TYPE_STRING,
TYPE_INT, TYPE_INT, TYPE_SHORT, TYPE_INT, TYPE_INT, TYPE_SHORT,
TYPE_SHORT, TYPE_SHORT, TYPE_STRING}; TYPE_SHORT, TYPE_SHORT, TYPE_STRING};
static XFLD fldtyp[] = {FLD_NO, FLD_NO,
FLD_NAME, FLD_TYPE, FLD_TYPENAME,
FLD_PREC, FLD_LENGTH, FLD_SCALE,
FLD_RADIX, FLD_NULL, FLD_REM};
static unsigned int length[] = {0, 0, 0, 6, 20, 10, 10, 6, 6, 6, 128}; static unsigned int length[] = {0, 0, 0, 6, 20, 10, 10, 6, 6, 6, 128};
int n, ncol = 11; int n, ncol = 11;
int maxres; int maxres;
...@@ -277,7 +274,7 @@ PQRYRES ODBCColumns(PGLOBAL g, ODBConn *ocp, char *dsn, char *table, ...@@ -277,7 +274,7 @@ PQRYRES ODBCColumns(PGLOBAL g, ODBConn *ocp, char *dsn, char *table,
/* Allocate the structures used to refer to the result set. */ /* Allocate the structures used to refer to the result set. */
/************************************************************************/ /************************************************************************/
qrp = PlgAllocResult(g, ncol, maxres, IDS_COLUMNS + 1, qrp = PlgAllocResult(g, ncol, maxres, IDS_COLUMNS + 1,
dbtype, buftyp, length); dbtype, buftyp, NULL, length, true, true);
if (!ocp) // Info table if (!ocp) // Info table
return qrp; return qrp;
...@@ -313,8 +310,8 @@ PQRYRES ODBCColumns(PGLOBAL g, ODBConn *ocp, char *dsn, char *table, ...@@ -313,8 +310,8 @@ PQRYRES ODBCColumns(PGLOBAL g, ODBConn *ocp, char *dsn, char *table,
/**************************************************************************/ /**************************************************************************/
PQRYRES MyODBCCols(PGLOBAL g, char *dsn, char *tab, bool info) PQRYRES MyODBCCols(PGLOBAL g, char *dsn, char *tab, bool info)
{ {
int type, len, prec; // int i, type, len, prec;
PCOLRES crpt, crpl, crpp; // PCOLRES crp, crpt, crpl, crpp;
PQRYRES qrp; PQRYRES qrp;
ODBConn *ocp; ODBConn *ocp;
...@@ -342,6 +339,7 @@ PQRYRES MyODBCCols(PGLOBAL g, char *dsn, char *tab, bool info) ...@@ -342,6 +339,7 @@ PQRYRES MyODBCCols(PGLOBAL g, char *dsn, char *tab, bool info)
if (ocp) if (ocp)
ocp->Close(); ocp->Close();
#if 0
if (!qrp) if (!qrp)
return NULL; // Error in ODBCColumns return NULL; // Error in ODBCColumns
...@@ -371,7 +369,13 @@ PQRYRES MyODBCCols(PGLOBAL g, char *dsn, char *tab, bool info) ...@@ -371,7 +369,13 @@ PQRYRES MyODBCCols(PGLOBAL g, char *dsn, char *tab, bool info)
} // endfor i } // endfor i
crpp->Next = crpp->Next->Next->Next; // Should be Remark crpp->Next = crpp->Next->Next->Next; // Should be Remark
qrp->Nbcol = 7; // Was 11, skipped 4
// Renumber crp's for flag comparison
for (i = 0, crp = qrp->Colresp; crp; crp = crp->Next)
crp->Ncol = ++i;
qrp->Nbcol = i; // Should be 7; was 11, skipped 4
#endif // 0
return qrp; return qrp;
} // end of MyODBCCols } // end of MyODBCCols
...@@ -410,7 +414,8 @@ PQRYRES ODBCDataSources(PGLOBAL g, bool info) ...@@ -410,7 +414,8 @@ PQRYRES ODBCDataSources(PGLOBAL g, bool info)
/************************************************************************/ /************************************************************************/
/* Allocate the structures used to refer to the result set. */ /* Allocate the structures used to refer to the result set. */
/************************************************************************/ /************************************************************************/
qrp = PlgAllocResult(g, ncol, maxres, IDS_DSRC, dbtype, buftyp, length); qrp = PlgAllocResult(g, ncol, maxres, IDS_DSRC,
dbtype, buftyp, NULL, length, true, true);
/************************************************************************/ /************************************************************************/
/* Now get the results into blocks. */ /* Now get the results into blocks. */
...@@ -455,7 +460,8 @@ PQRYRES ODBCDrivers(PGLOBAL g, bool info) ...@@ -455,7 +460,8 @@ PQRYRES ODBCDrivers(PGLOBAL g, bool info)
/************************************************************************/ /************************************************************************/
/* Allocate the structures used to refer to the result set. */ /* Allocate the structures used to refer to the result set. */
/************************************************************************/ /************************************************************************/
qrp = PlgAllocResult(g, ncol, maxres, IDS_DRIVER, dbtype, buftyp, length); qrp = PlgAllocResult(g, ncol, maxres, IDS_DRIVER,
dbtype, buftyp, NULL, length, true, true);
/************************************************************************/ /************************************************************************/
/* Now get the results into blocks. */ /* Now get the results into blocks. */
...@@ -521,7 +527,7 @@ PQRYRES ODBCTables(PGLOBAL g, char *dsn, char *tabpat, bool info) ...@@ -521,7 +527,7 @@ PQRYRES ODBCTables(PGLOBAL g, char *dsn, char *tabpat, bool info)
/* Allocate the structures used to refer to the result set. */ /* Allocate the structures used to refer to the result set. */
/************************************************************************/ /************************************************************************/
qrp = PlgAllocResult(g, ncol, maxres, IDS_TABLES + 1, qrp = PlgAllocResult(g, ncol, maxres, IDS_TABLES + 1,
dbtype, buftyp, length); dbtype, buftyp, NULL, length, true, true);
if (info) if (info)
return qrp; return qrp;
...@@ -606,7 +612,7 @@ PQRYRES ODBCPrimaryKeys(PGLOBAL g, ODBConn *op, char *dsn, char *table) ...@@ -606,7 +612,7 @@ PQRYRES ODBCPrimaryKeys(PGLOBAL g, ODBConn *op, char *dsn, char *table)
/* Allocate the structure used to refer to the result set. */ /* Allocate the structure used to refer to the result set. */
/************************************************************************/ /************************************************************************/
qrp = PlgAllocResult(g, ncol, maxres, IDS_PKEY + 1, qrp = PlgAllocResult(g, ncol, maxres, IDS_PKEY + 1,
dbtype, buftyp, length); dbtype, buftyp, NULL, length, true, true);
#ifdef DEBTRACE #ifdef DEBTRACE
htrc("Getting pkey results ncol=%d\n", qrp->Nbcol); htrc("Getting pkey results ncol=%d\n", qrp->Nbcol);
...@@ -693,7 +699,7 @@ PQRYRES ODBCStatistics(PGLOBAL g, ODBConn *op, char *dsn, char *pat, ...@@ -693,7 +699,7 @@ PQRYRES ODBCStatistics(PGLOBAL g, ODBConn *op, char *dsn, char *pat,
/* Allocate the structure used to refer to the result set. */ /* Allocate the structure used to refer to the result set. */
/************************************************************************/ /************************************************************************/
qrp = PlgAllocResult(g, ncol, maxres, IDS_STAT + 1, qrp = PlgAllocResult(g, ncol, maxres, IDS_STAT + 1,
dbtype, buftyp, length); dbtype, buftyp, NULL, length, true, true);
#ifdef DEBTRACE #ifdef DEBTRACE
htrc("Getting stat results ncol=%d\n", qrp->Nbcol); htrc("Getting stat results ncol=%d\n", qrp->Nbcol);
......
...@@ -96,6 +96,7 @@ enum AMT {TYPE_AM_ERROR = 0, /* Type not defined */ ...@@ -96,6 +96,7 @@ enum AMT {TYPE_AM_ERROR = 0, /* Type not defined */
TYPE_AM_DMY = 172, /* DMY Dummy tables am type no */ TYPE_AM_DMY = 172, /* DMY Dummy tables am type no */
TYPE_AM_SET = 180, /* SET Set tables am type no */ TYPE_AM_SET = 180, /* SET Set tables am type no */
TYPE_AM_MYSQL = 192, /* MYSQL access method type no */ TYPE_AM_MYSQL = 192, /* MYSQL access method type no */
TYPE_AM_CAT = 193, /* Catalog access method type no */
TYPE_AM_OUT = 200}; /* Output relations (storage) */ TYPE_AM_OUT = 200}; /* Output relations (storage) */
enum RECFM {RECFM_NAF = -2, /* Not a file */ enum RECFM {RECFM_NAF = -2, /* Not a file */
...@@ -440,6 +441,25 @@ typedef struct _tabs { ...@@ -440,6 +441,25 @@ typedef struct _tabs {
PTABADR P3; PTABADR P3;
} TABS; } TABS;
/***********************************************************************/
/* Following definitions are used to define table fields (columns). */
/***********************************************************************/
enum XFLD {FLD_NO = 0, /* Not a field definition item */
FLD_NAME = 1, /* Field name */
FLD_TYPE = 2, /* Field type */
FLD_TYPENAME = 3, /* Field type name */
FLD_PREC = 4, /* Field precision (length?) */
FLD_LENGTH = 5, /* Field length (?) */
FLD_SCALE = 6, /* Field scale (precision) */
FLD_RADIX = 7, /* Field radix */
FLD_NULL = 8, /* Field nullable property */
FLD_REM = 9, /* Field comment (remark) */
FLD_CHARSET = 10, /* Field collation */
FLD_KEY = 11, /* Field key property */
FLD_DEFAULT = 12, /* Field default value */
FLD_PRIV = 13, /* Field priviledges */
FLD_DATEFMT = 14}; /* Field date format */
/***********************************************************************/ /***********************************************************************/
/* Result of last SQL noconv query. */ /* Result of last SQL noconv query. */
/***********************************************************************/ /***********************************************************************/
...@@ -470,6 +490,7 @@ typedef struct _colres { ...@@ -470,6 +490,7 @@ typedef struct _colres {
int Clen; /* Data individual internal size */ int Clen; /* Data individual internal size */
int Length; /* Data individual print length */ int Length; /* Data individual print length */
int Prec; /* Precision */ int Prec; /* Precision */
XFLD Fld; /* Type of field info */
} COLRES; } COLRES;
#if defined(WIN32) && !defined(NOEX) #if defined(WIN32) && !defined(NOEX)
...@@ -491,6 +512,13 @@ void AddPointer(PTABS, void *); ...@@ -491,6 +512,13 @@ void AddPointer(PTABS, void *);
PDTP MakeDateFormat(PGLOBAL, PSZ, bool, bool, int); PDTP MakeDateFormat(PGLOBAL, PSZ, bool, bool, int);
int ExtractDate(char *, PDTP, int, int val[6]); int ExtractDate(char *, PDTP, int, int val[6]);
/**************************************************************************/
/* Allocate the result structure that will contain result data. */
/**************************************************************************/
PQRYRES PlgAllocResult(PGLOBAL g, int ncol, int maxres, int ids,
int *dbtype, int *buftyp, XFLD *fldtyp,
unsigned int *length, bool blank, bool nonull);
/***********************************************************************/ /***********************************************************************/
/* Exported utility routines. */ /* Exported utility routines. */
/***********************************************************************/ /***********************************************************************/
......
/********** PlgDBUtl Fpe C++ Program Source Code File (.CPP) ***********/ /********** PlgDBUtl Fpe C++ Program Source Code File (.CPP) ***********/
/* PROGRAM NAME: PLGDBUTL */ /* PROGRAM NAME: PLGDBUTL */
/* ------------- */ /* ------------- */
/* Version 3.7 */ /* Version 3.8 */
/* */ /* */
/* COPYRIGHT: */ /* COPYRIGHT: */
/* ---------- */ /* ---------- */
/* (C) Copyright to the author Olivier BERTRAND 1998-2012 */ /* (C) Copyright to the author Olivier BERTRAND 1998-2013 */
/* */ /* */
/* WHAT THIS PROGRAM DOES: */ /* WHAT THIS PROGRAM DOES: */
/* ----------------------- */ /* ----------------------- */
...@@ -66,6 +66,7 @@ ...@@ -66,6 +66,7 @@
#include "colblk.h" #include "colblk.h"
#include "xtable.h" // header of TBX, TDB and TDBASE classes #include "xtable.h" // header of TBX, TDB and TDBASE classes
#include "tabcol.h" // header of XTAB and COLUMN classes #include "tabcol.h" // header of XTAB and COLUMN classes
#include "valblk.h"
/***********************************************************************/ /***********************************************************************/
/* Macro or external routine definition */ /* Macro or external routine definition */
...@@ -128,6 +129,7 @@ void CloseXMLFile(PGLOBAL, PFBLOCK, bool); ...@@ -128,6 +129,7 @@ void CloseXMLFile(PGLOBAL, PFBLOCK, bool);
void CloseXML2File(PGLOBAL, PFBLOCK, bool); void CloseXML2File(PGLOBAL, PFBLOCK, bool);
#endif // LIBXML2_SUPPORT #endif // LIBXML2_SUPPORT
extern "C" int GetRcString(int id, char *buf, int bufsize);
/***********************************************************************/ /***********************************************************************/
/* Routines for file IO with error reporting to g->Message */ /* Routines for file IO with error reporting to g->Message */
...@@ -262,6 +264,85 @@ void ptrc(char const *fmt, ...) ...@@ -262,6 +264,85 @@ void ptrc(char const *fmt, ...)
} // end of ptrc } // end of ptrc
#endif // 0 #endif // 0
/**************************************************************************/
/* Allocate the result structure that will contain result data. */
/**************************************************************************/
PQRYRES PlgAllocResult(PGLOBAL g, int ncol, int maxres, int ids,
int *dbtype, int *buftyp, XFLD *fldtyp,
unsigned int *length, bool blank, bool nonull)
{
char cname[NAM_LEN+1];
int i;
PCOLRES *pcrp, crp;
PQRYRES qrp;
/************************************************************************/
/* Allocate the structure used to contain the result set. */
/************************************************************************/
qrp = (PQRYRES)PlugSubAlloc(g, NULL, sizeof(QRYRES));
pcrp = &qrp->Colresp;
qrp->Continued = false;
qrp->Truncated = false;
qrp->Info = false;
qrp->Suball = true;
qrp->Maxres = maxres;
qrp->Maxsize = 0;
qrp->Nblin = 0;
qrp->Nbcol = 0; // will be ncol
qrp->Cursor = 0;
qrp->BadLines = 0;
for (i = 0; i < ncol; i++) {
*pcrp = (PCOLRES)PlugSubAlloc(g, NULL, sizeof(COLRES));
crp = *pcrp;
pcrp = &crp->Next;
crp->Colp = NULL;
crp->Ncol = ++qrp->Nbcol;
crp->Type = buftyp[i];
crp->Length = length[i];
crp->Clen = GetTypeSize(crp->Type, length[i]);
crp->Prec = 0;
crp->DBtype = dbtype[i];
if (ids > 0) {
#if defined(XMSG)
// Get header from message file
strncpy(cname, PlugReadMessage(g, ids + crp->Ncol, NULL), NAM_LEN);
cname[NAM_LEN] = 0; // for truncated long names
//#elif defined(WIN32)
// Get header from ressource file
// LoadString(s_hModule, ids + crp->Ncol, cname, sizeof(cname));
#else // !WIN32
GetRcString(ids + crp->Ncol, cname, sizeof(cname));
#endif // !WIN32
crp->Name = (PSZ)PlugSubAlloc(g, NULL, strlen(cname) + 1);
strcpy(crp->Name, cname);
} else
crp->Name = NULL; // Will be set by caller
if (fldtyp)
crp->Fld = fldtyp[i];
else
crp->Fld = FLD_NO;
// Allocate the Value Block that will contain data
if (crp->Length || nonull)
crp->Kdata = AllocValBlock(g, NULL, crp->Type, maxres,
crp->Length, 0, true, blank);
else
crp->Kdata = NULL;
if (g->Trace)
htrc("Column(%d) %s type=%d len=%d value=%p\n",
crp->Ncol, crp->Name, crp->Type, crp->Length, crp->Kdata);
} // endfor i
*pcrp = NULL;
return qrp;
} // end of PlgAllocResult
/***********************************************************************/ /***********************************************************************/
/* Allocate and initialize the new DB User Block. */ /* Allocate and initialize the new DB User Block. */
/***********************************************************************/ /***********************************************************************/
......
...@@ -74,6 +74,7 @@ TABDEF::TABDEF(void) ...@@ -74,6 +74,7 @@ TABDEF::TABDEF(void)
{ {
Owner = NULL; Owner = NULL;
Desc = NULL; Desc = NULL;
Catfunc = 0;
Card = 0; Card = 0;
Elemt = 0; Elemt = 0;
Sort = 0; Sort = 0;
...@@ -95,6 +96,7 @@ bool TABDEF::Define(PGLOBAL g, PCATLG cat, LPCSTR name, LPCSTR am) ...@@ -95,6 +96,7 @@ bool TABDEF::Define(PGLOBAL g, PCATLG cat, LPCSTR name, LPCSTR am)
Name = (PSZ)PlugSubAlloc(g, memp, strlen(name) + 1); Name = (PSZ)PlugSubAlloc(g, memp, strlen(name) + 1);
strcpy(Name, name); strcpy(Name, name);
Cat = cat; Cat = cat;
Catfunc = toupper(*Cat->GetStringCatInfo(g, Name, "Catfunc", ""));
Elemt = cat->GetIntCatInfo(name, "Elements", 0); Elemt = cat->GetIntCatInfo(name, "Elements", 0);
Multiple = cat->GetIntCatInfo(name, "Multiple", 0); Multiple = cat->GetIntCatInfo(name, "Multiple", 0);
Degree = cat->GetIntCatInfo(name, "Degree", 0); Degree = cat->GetIntCatInfo(name, "Degree", 0);
......
...@@ -85,6 +85,7 @@ class DllExport TABDEF : public RELDEF { /* Logical table descriptor */ ...@@ -85,6 +85,7 @@ class DllExport TABDEF : public RELDEF { /* Logical table descriptor */
// Members // Members
PSZ Owner; /* Table owner (for ODBC) */ PSZ Owner; /* Table owner (for ODBC) */
PSZ Desc; /* Table description */ PSZ Desc; /* Table description */
char Catfunc; /* Catalog function */
int Card; /* (max) number of rows in table */ int Card; /* (max) number of rows in table */
int Elemt; /* Number of rows in blocks or rowset */ int Elemt; /* Number of rows in blocks or rowset */
int Sort; /* Table already sorted ??? */ int Sort; /* Table already sorted ??? */
......
...@@ -297,12 +297,16 @@ PTDB DOSDEF::GetTable(PGLOBAL g, MODE mode) ...@@ -297,12 +297,16 @@ PTDB DOSDEF::GetTable(PGLOBAL g, MODE mode)
/* Column blocks will be allocated only when needed. */ /* Column blocks will be allocated only when needed. */
/*********************************************************************/ /*********************************************************************/
if (Recfm == RECFM_DBF) { if (Recfm == RECFM_DBF) {
if (!Catfunc) {
if (map) if (map)
txfp = new(g) DBMFAM(this); txfp = new(g) DBMFAM(this);
else else
txfp = new(g) DBFFAM(this); txfp = new(g) DBFFAM(this);
tdbp = new(g) TDBFIX(this, txfp); tdbp = new(g) TDBFIX(this, txfp);
} else // Catfunc should be 'C'
tdbp = new(g) TDBDCL(this);
} else if (Recfm != RECFM_VAR && Compressed < 2) { } else if (Recfm != RECFM_VAR && Compressed < 2) {
if (Huge) if (Huge)
txfp = new(g) BGXFAM(this); txfp = new(g) BGXFAM(this);
......
...@@ -34,6 +34,7 @@ class DllExport DOSDEF : public TABDEF { /* Logical table description */ ...@@ -34,6 +34,7 @@ class DllExport DOSDEF : public TABDEF { /* Logical table description */
virtual const char *GetType(void) {return "DOS";} virtual const char *GetType(void) {return "DOS";}
virtual PIXDEF GetIndx(void) {return To_Indx;} virtual PIXDEF GetIndx(void) {return To_Indx;}
virtual void SetIndx(PIXDEF xdp) {To_Indx = xdp;} virtual void SetIndx(PIXDEF xdp) {To_Indx = xdp;}
PSZ GetFn(void) {return Fn;}
PSZ GetOfn(void) {return Ofn;} PSZ GetOfn(void) {return Ofn;}
void SetBlock(int block) {Block = block;} void SetBlock(int block) {Block = block;}
int GetBlock(void) {return Block;} int GetBlock(void) {return Block;}
......
...@@ -8,6 +8,7 @@ ...@@ -8,6 +8,7 @@
#ifndef __TABFIX__ #ifndef __TABFIX__
#define __TABFIX__ #define __TABFIX__
#include "tabdos.h" /* Base class declares */ #include "tabdos.h" /* Base class declares */
#include "filamdbf.h"
typedef class FIXCOL *PFIXCOL; typedef class FIXCOL *PFIXCOL;
typedef class BINCOL *PBINCOL; typedef class BINCOL *PBINCOL;
...@@ -77,4 +78,22 @@ class DllExport BINCOL : public DOSCOL { ...@@ -77,4 +78,22 @@ class DllExport BINCOL : public DOSCOL {
// Members // Members
char Fmt; // The column numeric format char Fmt; // The column numeric format
}; // end of class BINCOL }; // end of class BINCOL
/***********************************************************************/
/* This is the class declaration for the DBF columns catalog table. */
/***********************************************************************/
class TDBDCL : public TDBCAT {
public:
// Constructor
TDBDCL(PDOSDEF tdp) : TDBCAT(tdp) {Fn = tdp->GetFn();}
protected:
// Specific routines
virtual PQRYRES GetResult(PGLOBAL g) {return DBFColumns(g, Fn, false);}
// Members
char *Fn; // The DBF file (path) name
}; // end of class TDBOCL
#endif // __TABFIX__ #endif // __TABFIX__
/************* TabFmt C++ Program Source Code File (.CPP) **************/ /************* TabFmt C++ Program Source Code File (.CPP) **************/
/* PROGRAM NAME: TABFMT */ /* PROGRAM NAME: TABFMT */
/* ------------- */ /* ------------- */
/* Version 3.7 */ /* Version 3.8 */
/* */ /* */
/* COPYRIGHT: */ /* COPYRIGHT: */
/* ---------- */ /* ---------- */
...@@ -67,12 +67,6 @@ ...@@ -67,12 +67,6 @@
extern "C" int trace; extern "C" int trace;
/***********************************************************************/
/* CSV Catalog utility functions. */
/***********************************************************************/
PQRYRES PlgAllocResult(PGLOBAL, int, int, int, int *, int *,
unsigned int *, bool blank = true, bool nonull = false);
/***********************************************************************/ /***********************************************************************/
/* CSVColumns: constructs the result blocks containing the description */ /* CSVColumns: constructs the result blocks containing the description */
/* of all the columns of a CSV file that will be retrieved by #GetData.*/ /* of all the columns of a CSV file that will be retrieved by #GetData.*/
...@@ -80,12 +74,15 @@ PQRYRES PlgAllocResult(PGLOBAL, int, int, int, int *, int *, ...@@ -80,12 +74,15 @@ PQRYRES PlgAllocResult(PGLOBAL, int, int, int, int *, int *,
/* of types (TYPE_STRING < TYPE_FLOAT < TYPE_INT) (1 < 2 < 7). */ /* of types (TYPE_STRING < TYPE_FLOAT < TYPE_INT) (1 < 2 < 7). */
/* If these values are changed, this will have to be revisited. */ /* If these values are changed, this will have to be revisited. */
/***********************************************************************/ /***********************************************************************/
PQRYRES CSVColumns(PGLOBAL g, char *fn, char sep, char q, int hdr, int mxr) PQRYRES CSVColumns(PGLOBAL g, char *fn, char sep, char q,
int hdr, int mxr, bool info)
{ {
static int dbtype[] = {DB_CHAR, DB_SHORT, DB_CHAR, static int dbtype[] = {DB_CHAR, DB_SHORT, DB_CHAR,
DB_INT, DB_INT, DB_SHORT}; DB_INT, DB_INT, DB_SHORT};
static int buftyp[] = {TYPE_STRING, TYPE_SHORT, TYPE_STRING, static int buftyp[] = {TYPE_STRING, TYPE_SHORT, TYPE_STRING,
TYPE_INT, TYPE_INT, TYPE_SHORT}; TYPE_INT, TYPE_INT, TYPE_SHORT};
static XFLD fldtyp[] = {FLD_NAME, FLD_TYPE, FLD_TYPENAME,
FLD_PREC, FLD_LENGTH, FLD_SCALE};
static unsigned int length[] = {6, 6, 8, 10, 10, 6}; static unsigned int length[] = {6, 6, 8, 10, 10, 6};
char *p, *colname[MAXCOL], dechar, filename[_MAX_PATH], buf[4096]; char *p, *colname[MAXCOL], dechar, filename[_MAX_PATH], buf[4096];
int i, imax, hmax, n, nerr, phase, blank, digit, dec, type; int i, imax, hmax, n, nerr, phase, blank, digit, dec, type;
...@@ -96,9 +93,15 @@ PQRYRES CSVColumns(PGLOBAL g, char *fn, char sep, char q, int hdr, int mxr) ...@@ -96,9 +93,15 @@ PQRYRES CSVColumns(PGLOBAL g, char *fn, char sep, char q, int hdr, int mxr)
PQRYRES qrp; PQRYRES qrp;
PCOLRES crp; PCOLRES crp;
if (info) {
imax = 0;
length[0] = 128;
goto skipit;
} // endif info
// num_max = atoi(p+1); // Max num of record to test // num_max = atoi(p+1); // Max num of record to test
#if defined(WIN32) #if defined(WIN32)
if (strnicmp(setlocale(LC_NUMERIC, NULL), "French", 6)) if (sep == ',' || strnicmp(setlocale(LC_NUMERIC, NULL), "French", 6))
dechar = '.'; dechar = '.';
else else
dechar = ','; dechar = ',';
...@@ -328,6 +331,7 @@ PQRYRES CSVColumns(PGLOBAL g, char *fn, char sep, char q, int hdr, int mxr) ...@@ -328,6 +331,7 @@ PQRYRES CSVColumns(PGLOBAL g, char *fn, char sep, char q, int hdr, int mxr)
fclose(infile); fclose(infile);
skipit:
if (trace) if (trace)
htrc("CSVColumns: imax=%d hmax=%d len=%d\n", htrc("CSVColumns: imax=%d hmax=%d len=%d\n",
imax, hmax, length[0]); imax, hmax, length[0]);
...@@ -336,9 +340,12 @@ PQRYRES CSVColumns(PGLOBAL g, char *fn, char sep, char q, int hdr, int mxr) ...@@ -336,9 +340,12 @@ PQRYRES CSVColumns(PGLOBAL g, char *fn, char sep, char q, int hdr, int mxr)
/* Allocate the structures used to refer to the result set. */ /* Allocate the structures used to refer to the result set. */
/*********************************************************************/ /*********************************************************************/
qrp = PlgAllocResult(g, ncol, imax, IDS_COLUMNS + 3, qrp = PlgAllocResult(g, ncol, imax, IDS_COLUMNS + 3,
dbtype, buftyp, length); dbtype, buftyp, fldtyp, length, true, false);
qrp->Nblin = imax; qrp->Nblin = imax;
if (info)
return qrp;
/*********************************************************************/ /*********************************************************************/
/* Now get the results into blocks. */ /* Now get the results into blocks. */
/*********************************************************************/ /*********************************************************************/
...@@ -398,6 +405,7 @@ bool CSVDEF::DefineAM(PGLOBAL g, LPCSTR am, int poff) ...@@ -398,6 +405,7 @@ bool CSVDEF::DefineAM(PGLOBAL g, LPCSTR am, int poff)
char buf[8]; char buf[8];
// Double check correctness of offset values // Double check correctness of offset values
if (!Catfunc)
for (PCOLDEF cdp = To_Cols; cdp; cdp = cdp->GetNext()) for (PCOLDEF cdp = To_Cols; cdp; cdp = cdp->GetNext())
if (cdp->GetOffset() < 1) { if (cdp->GetOffset() < 1) {
strcpy(g->Message, MSG(BAD_OFFSET_VAL)); strcpy(g->Message, MSG(BAD_OFFSET_VAL));
...@@ -431,17 +439,19 @@ bool CSVDEF::DefineAM(PGLOBAL g, LPCSTR am, int poff) ...@@ -431,17 +439,19 @@ bool CSVDEF::DefineAM(PGLOBAL g, LPCSTR am, int poff)
/***********************************************************************/ /***********************************************************************/
PTDB CSVDEF::GetTable(PGLOBAL g, MODE mode) PTDB CSVDEF::GetTable(PGLOBAL g, MODE mode)
{ {
PTDBASE tdbp;
if (Catfunc != 'C') {
USETEMP tmp = PlgGetUser(g)->UseTemp; USETEMP tmp = PlgGetUser(g)->UseTemp;
bool map = Mapped && mode != MODE_INSERT && bool map = Mapped && mode != MODE_INSERT &&
!(tmp != TMP_NO && mode == MODE_UPDATE) && !(tmp != TMP_NO && mode == MODE_UPDATE) &&
!(tmp == TMP_FORCE && !(tmp == TMP_FORCE &&
(mode == MODE_UPDATE || mode == MODE_DELETE)); (mode == MODE_UPDATE || mode == MODE_DELETE));
PTXF txfp; PTXF txfp;
PTDBASE tdbp;
/*********************************************************************/ /*******************************************************************/
/* Allocate a file processing class of the proper type. */ /* Allocate a file processing class of the proper type. */
/*********************************************************************/ /*******************************************************************/
if (map) { if (map) {
// Should be now compatible with UNIX // Should be now compatible with UNIX
txfp = new(g) MAPFAM(this); txfp = new(g) MAPFAM(this);
...@@ -461,10 +471,10 @@ PTDB CSVDEF::GetTable(PGLOBAL g, MODE mode) ...@@ -461,10 +471,10 @@ PTDB CSVDEF::GetTable(PGLOBAL g, MODE mode)
} else } else
txfp = new(g) DOSFAM(this); txfp = new(g) DOSFAM(this);
/*********************************************************************/ /*******************************************************************/
/* Allocate a TDB of the proper type. */ /* Allocate a TDB of the proper type. */
/* Column blocks will be allocated only when needed. */ /* Column blocks will be allocated only when needed. */
/*********************************************************************/ /*******************************************************************/
if (!Fmtd) if (!Fmtd)
tdbp = new(g) TDBCSV(this, txfp); tdbp = new(g) TDBCSV(this, txfp);
else else
...@@ -473,6 +483,9 @@ PTDB CSVDEF::GetTable(PGLOBAL g, MODE mode) ...@@ -473,6 +483,9 @@ PTDB CSVDEF::GetTable(PGLOBAL g, MODE mode)
if (Multiple) if (Multiple)
tdbp = new(g) TDBMUL(tdbp); tdbp = new(g) TDBMUL(tdbp);
} else
tdbp = new(g)TDBCCL(this);
return tdbp; return tdbp;
} // end of GetTable } // end of GetTable
...@@ -1389,4 +1402,26 @@ void CSVCOL::WriteColumn(PGLOBAL g) ...@@ -1389,4 +1402,26 @@ void CSVCOL::WriteColumn(PGLOBAL g)
} // end of WriteColumn } // end of WriteColumn
/* ---------------------------TDBCCL class --------------------------- */
/***********************************************************************/
/* TDBCCL class constructor. */
/***********************************************************************/
TDBCCL::TDBCCL(PCSVDEF tdp) : TDBCAT(tdp)
{
Fn = tdp->GetFn();
Hdr = tdp->Header;
Mxr = tdp->Maxerr;
Qtd = tdp->Quoted;
Sep = tdp->Sep;
} // end of TDBCCL constructor
/***********************************************************************/
/* GetResult: Get the list the CSV file columns. */
/***********************************************************************/
PQRYRES TDBCCL::GetResult(PGLOBAL g)
{
return CSVColumns(g, Fn, Sep, Qtd, Hdr, Mxr, false);
} // end of GetResult
/* ------------------------ End of TabFmt ---------------------------- */ /* ------------------------ End of TabFmt ---------------------------- */
/*************** TabFmt H Declares Source Code File (.H) ***************/ /*************** TabFmt H Declares Source Code File (.H) ***************/
/* Name: TABFMT.H Version 2.2 */ /* Name: TABFMT.H Version 2.3 */
/* */ /* */
/* (C) Copyright to the author Olivier BERTRAND 2001-2012 */ /* (C) Copyright to the author Olivier BERTRAND 2001-2013 */
/* */ /* */
/* This file contains the CSV and FMT classes declares. */ /* This file contains the CSV and FMT classes declares. */
/***********************************************************************/ /***********************************************************************/
...@@ -14,14 +14,15 @@ typedef class TDBFMT *PTDBFMT; ...@@ -14,14 +14,15 @@ typedef class TDBFMT *PTDBFMT;
/***********************************************************************/ /***********************************************************************/
/* Functions used externally. */ /* Functions used externally. */
/***********************************************************************/ /***********************************************************************/
PQRYRES CSVColumns(PGLOBAL g, char *fn, char sep, char q, int hdr, int mxr); PQRYRES CSVColumns(PGLOBAL g, char *fn, char sep, char q,
int hdr, int mxr, bool info);
/***********************************************************************/ /***********************************************************************/
/* CSV table. */ /* CSV table. */
/***********************************************************************/ /***********************************************************************/
class DllExport CSVDEF : public DOSDEF { /* Logical table description */ class DllExport CSVDEF : public DOSDEF { /* Logical table description */
friend class TDBCSV; friend class TDBCSV;
//friend class TDBMCV; friend class TDBCCL;
public: public:
// Constructor // Constructor
CSVDEF(void); CSVDEF(void);
...@@ -166,4 +167,24 @@ class TDBFMT : public TDBCSV { ...@@ -166,4 +167,24 @@ class TDBFMT : public TDBCSV {
int Linenum; // Last read line int Linenum; // Last read line
}; // end of class TDBFMT }; // end of class TDBFMT
/***********************************************************************/
/* This is the class declaration for the CSV catalog table. */
/***********************************************************************/
class TDBCCL : public TDBCAT {
public:
// Constructor
TDBCCL(PCSVDEF tdp);
protected:
// Specific routines
virtual PQRYRES GetResult(PGLOBAL g);
// Members
char *Fn; // The CSV file (path) name
bool Hdr; // true if first line contains headers
int Mxr; // Maximum number of bad records
int Qtd; // Quoting level for quoted fields
char Sep; // Separator for standard CSV files
}; // end of class TDBCCL
/* ------------------------- End of TabFmt.H ------------------------- */ /* ------------------------- End of TabFmt.H ------------------------- */
/************** Table C++ Functions Source Code File (.CPP) ************/ /************** Table C++ Functions Source Code File (.CPP) ************/
/* Name: TABLE.CPP Version 2.5 */ /* Name: TABLE.CPP Version 2.6 */
/* */ /* */
/* (C) Copyright to the author Olivier BERTRAND 1999-2012 */ /* (C) Copyright to the author Olivier BERTRAND 1999-2013 */
/* */ /* */
/* This file contains the TBX, TDB and OPJOIN classes functions. */ /* This file contains the TBX, TDB and OPJOIN classes functions. */
/***********************************************************************/ /***********************************************************************/
...@@ -425,3 +425,180 @@ void TDBASE::MarkDB(PGLOBAL g, PTDB tdb2) ...@@ -425,3 +425,180 @@ void TDBASE::MarkDB(PGLOBAL g, PTDB tdb2)
htrc("DOS MarkDB: tdbp=%p tdb2=%p\n", this, tdb2); htrc("DOS MarkDB: tdbp=%p tdb2=%p\n", this, tdb2);
} // end of MarkDB } // end of MarkDB
/* ---------------------------TDBCAT class --------------------------- */
/***********************************************************************/
/* Implementation of the TDBCAT class. */
/***********************************************************************/
TDBCAT::TDBCAT(PTABDEF tdp) : TDBASE(tdp)
{
Qrp = NULL;
Init = false;
N = -1;
} // end of TDBCAT constructor
/***********************************************************************/
/* Allocate CAT column description block. */
/***********************************************************************/
PCOL TDBCAT::MakeCol(PGLOBAL g, PCOLDEF cdp, PCOL cprec, int n)
{
PCATCOL colp;
colp = (PCATCOL)new(g) CATCOL(cdp, this, n);
if (cprec) {
colp->SetNext(cprec->GetNext());
cprec->SetNext(colp);
} else {
colp->SetNext(Columns);
Columns = colp;
} // endif cprec
return colp;
} // end of MakeCol
/***********************************************************************/
/* Initialize: Get the result query block. */
/***********************************************************************/
bool TDBCAT::Initialize(PGLOBAL g)
{
if (Init)
return false;
if (!(Qrp = GetResult(g)))
return true;
Init = true;
return false;
} // end of Initialize
/***********************************************************************/
/* CAT: Get the number of properties. */
/***********************************************************************/
int TDBCAT::GetMaxSize(PGLOBAL g)
{
if (MaxSize < 0) {
if (Initialize(g))
return -1;
MaxSize = Qrp->Nblin;
} // endif MaxSize
return MaxSize;
} // end of GetMaxSize
/***********************************************************************/
/* CAT Access Method opening routine. */
/***********************************************************************/
bool TDBCAT::OpenDB(PGLOBAL g)
{
if (Use == USE_OPEN) {
/*******************************************************************/
/* Table already open. */
/*******************************************************************/
N = -1;
return false;
} // endif use
if (Mode != MODE_READ) {
/*******************************************************************/
/* ODBC Info tables cannot be modified. */
/*******************************************************************/
strcpy(g->Message, "CAT tables are read only");
return true;
} // endif Mode
/*********************************************************************/
/* Initialize the ODBC processing. */
/*********************************************************************/
if (Initialize(g))
return true;
return InitCol(g);
} // end of OpenDB
/***********************************************************************/
/* Initialize columns. */
/***********************************************************************/
bool TDBCAT::InitCol(PGLOBAL g)
{
PCATCOL colp;
PCOLRES crp;
for (colp = (PCATCOL)Columns; colp; colp = (PCATCOL)colp->GetNext()) {
for (crp = Qrp->Colresp; crp; crp = crp->Next)
if ((colp->Flag == crp->Ncol) ||
(!colp->Flag && !stricmp(colp->Name, crp->Name))) {
colp->Crp = crp;
break;
} // endif Flag
if (!colp->Crp /*&& !colp->GetValue()->IsConstant()*/) {
sprintf(g->Message, "Invalid flag %d for column %s",
colp->Flag, colp->Name);
return true;
} // endif Crp
} // endfor colp
return false;
} // end of InitCol
/***********************************************************************/
/* Data Base read routine for CAT access method. */
/***********************************************************************/
int TDBCAT::ReadDB(PGLOBAL g)
{
return (++N < Qrp->Nblin) ? RC_OK : RC_EF;
} // end of ReadDB
/***********************************************************************/
/* WriteDB: Data Base write routine for CAT access methods. */
/***********************************************************************/
int TDBCAT::WriteDB(PGLOBAL g)
{
strcpy(g->Message, "CAT tables are read only");
return RC_FX;
} // end of WriteDB
/***********************************************************************/
/* Data Base delete line routine for CAT access methods. */
/***********************************************************************/
int TDBCAT::DeleteDB(PGLOBAL g, int irc)
{
strcpy(g->Message, "Delete not enabled for CAT tables");
return RC_FX;
} // end of DeleteDB
/***********************************************************************/
/* Data Base close routine for WMI access method. */
/***********************************************************************/
void TDBCAT::CloseDB(PGLOBAL g)
{
// Nothing to do
} // end of CloseDB
// ------------------------ CATCOL functions ----------------------------
/***********************************************************************/
/* CATCOL public constructor. */
/***********************************************************************/
CATCOL::CATCOL(PCOLDEF cdp, PTDB tdbp, int n)
: COLBLK(cdp, tdbp, n)
{
Tdbp = (PTDBCAT)tdbp;
Crp = NULL;
Flag = cdp->GetOffset();
} // end of WMICOL constructor
/***********************************************************************/
/* Read the next Data Source elements. */
/***********************************************************************/
void CATCOL::ReadColumn(PGLOBAL g)
{
// Get the value of the Name or Description property
Value->SetValue_pvblk(Crp->Kdata, Tdbp->N);
} // end of ReadColumn
/************* TabMySQL C++ Program Source Code File (.CPP) *************/ /************* TabMySQL C++ Program Source Code File (.CPP) *************/
/* PROGRAM NAME: TABMYSQL */ /* PROGRAM NAME: TABMYSQL */
/* ------------- */ /* ------------- */
/* Version 1.5 */ /* Version 1.6 */
/* */ /* */
/* AUTHOR: */ /* AUTHOR: */
/* ------- */ /* ------- */
...@@ -105,7 +105,11 @@ bool MYSQLDEF::DefineAM(PGLOBAL g, LPCSTR am, int poff) ...@@ -105,7 +105,11 @@ bool MYSQLDEF::DefineAM(PGLOBAL g, LPCSTR am, int poff)
/***********************************************************************/ /***********************************************************************/
PTDB MYSQLDEF::GetTable(PGLOBAL g, MODE m) PTDB MYSQLDEF::GetTable(PGLOBAL g, MODE m)
{ {
if (Catfunc == 'C')
return new(g) TDBMCL(this);
else
return new(g) TDBMYSQL(this); return new(g) TDBMYSQL(this);
} // end of GetTable } // end of GetTable
/* ------------------------------------------------------------------- */ /* ------------------------------------------------------------------- */
...@@ -859,3 +863,26 @@ void MYSQLCOL::WriteColumn(PGLOBAL g) ...@@ -859,3 +863,26 @@ void MYSQLCOL::WriteColumn(PGLOBAL g)
} // endif Prep } // endif Prep
} // end of WriteColumn } // end of WriteColumn
/* ---------------------------TDBMCL class --------------------------- */
/***********************************************************************/
/* TDBMCL class constructor. */
/***********************************************************************/
TDBMCL::TDBMCL(PMYDEF tdp) : TDBCAT(tdp)
{
Host = tdp->Hostname;
Db = tdp->Database;
Tab = tdp->Tabname;
User = tdp->Username;
Pwd = tdp->Password;
Port = tdp->Portnumber;
} // end of TDBMCL constructor
/***********************************************************************/
/* GetResult: Get the list the MYSQL table columns. */
/***********************************************************************/
PQRYRES TDBMCL::GetResult(PGLOBAL g)
{
return MyColumns(g, Host, Db, User, Pwd, Tab, NULL, Port, false, false);
} // end of GetResult
// TDBMYSQL.H Olivier Bertrand 2007-2012 // TDBMYSQL.H Olivier Bertrand 2007-2013
#include "myconn.h" // MySQL connection declares #include "myconn.h" // MySQL connection declares
typedef class MYSQLDEF *PMYDEF; typedef class MYSQLDEF *PMYDEF;
...@@ -18,6 +18,7 @@ typedef class MYSQLCOL *PMYCOL; ...@@ -18,6 +18,7 @@ typedef class MYSQLCOL *PMYCOL;
/***********************************************************************/ /***********************************************************************/
class MYSQLDEF : public TABDEF {/* Logical table description */ class MYSQLDEF : public TABDEF {/* Logical table description */
friend class TDBMYSQL; friend class TDBMYSQL;
friend class TDBMCL;
public: public:
// Constructor // Constructor
MYSQLDEF(void); MYSQLDEF(void);
...@@ -137,7 +138,23 @@ class MYSQLCOL : public COLBLK { ...@@ -137,7 +138,23 @@ class MYSQLCOL : public COLBLK {
int Rank; // Rank (position) number in the query int Rank; // Rank (position) number in the query
}; // end of class MYSQLCOL }; // end of class MYSQLCOL
/***********************************************************************/
/* This is the class declaration for the MYSQL column catalog table. */
/***********************************************************************/
class TDBMCL : public TDBCAT {
public:
// Constructor
TDBMCL(PMYDEF tdp);
PQRYRES MyColumns(PGLOBAL g, const char *host, const char *db, protected:
const char *user, const char *pwd, // Specific routines
const char *table, const char *colpat, int port, bool key); virtual PQRYRES GetResult(PGLOBAL g);
// Members
PSZ Host; // Host machine to use
PSZ Db; // Database to be used by server
PSZ Tab; // External table name
PSZ User; // User logon name
PSZ Pwd; // Password logon info
int Port; // MySQL port number (0 = default)
}; // end of class TDBMCL
This diff is collapsed.
...@@ -44,7 +44,6 @@ class DllExport ODBCDEF : public TABDEF { /* Logical table description */ ...@@ -44,7 +44,6 @@ class DllExport ODBCDEF : public TABDEF { /* Logical table description */
PSZ Tabowner; /* External table owner */ PSZ Tabowner; /* External table owner */
PSZ Tabqual; /* External table qualifier */ PSZ Tabqual; /* External table qualifier */
PSZ Qchar; /* Identifier quoting character */ PSZ Qchar; /* Identifier quoting character */
char Catfunc; /* Catalog function */
int Catver; /* ODBC version for catalog functions */ int Catver; /* ODBC version for catalog functions */
int Options; /* Open connection options */ int Options; /* Open connection options */
}; // end of ODBCDEF }; // end of ODBCDEF
...@@ -163,128 +162,64 @@ class ODBCCOL : public COLBLK { ...@@ -163,128 +162,64 @@ class ODBCCOL : public COLBLK {
int Rank; // Rank (position) number in the query int Rank; // Rank (position) number in the query
}; // end of class ODBCCOL }; // end of class ODBCCOL
/***********************************************************************/
/* This is the base class declaration for the ODBC info tables. */
/***********************************************************************/
class TDBOIF : public TDBASE {
friend class OIFCOL;
public:
// Constructor
TDBOIF(PODEF tdp);
// Implementation
virtual AMT GetAmType(void) {return TYPE_AM_ODBC;}
// Methods
virtual int GetRecpos(void) {return N;}
virtual int GetProgCur(void) {return N;}
virtual int RowNumber(PGLOBAL g, bool b = false) {return N + 1;}
// Database routines
virtual PCOL MakeCol(PGLOBAL g, PCOLDEF cdp, PCOL cprec, int n);
virtual int GetMaxSize(PGLOBAL g);
virtual bool OpenDB(PGLOBAL g);
virtual int ReadDB(PGLOBAL g);
virtual int WriteDB(PGLOBAL g);
virtual int DeleteDB(PGLOBAL g, int irc);
virtual void CloseDB(PGLOBAL g);
protected:
// Specific routines
virtual bool Initialize(PGLOBAL g) = 0;
bool InitCol(PGLOBAL g);
// Members
PQRYRES Qrp;
int ID; // Base of Column names
int NC; // Number of valid flags
int N; // Row number
bool Init;
}; // end of class TDBOIF
/***********************************************************************/
/* Class OIFCOL: ODBC info column. */
/***********************************************************************/
class OIFCOL : public COLBLK {
friend class TDBOIF;
public:
// Constructors
OIFCOL(PCOLDEF cdp, PTDB tdbp, int n);
// Implementation
virtual int GetAmType(void) {return TYPE_AM_ODBC;}
// Methods
virtual void ReadColumn(PGLOBAL g);
protected:
OIFCOL(void) {} // Default constructor not to be used
// Members
PTDBOIF Tdbp; // Points to ODBC table block
PCOLRES Crp; // The column data array
int Flag;
}; // end of class OIFCOL
/***********************************************************************/ /***********************************************************************/
/* This is the class declaration for the Data Sources catalog table. */ /* This is the class declaration for the Data Sources catalog table. */
/***********************************************************************/ /***********************************************************************/
class TDBSRC : public TDBOIF { class TDBSRC : public TDBCAT {
public: public:
// Constructor // Constructor
TDBSRC(PODEF tdp) : TDBOIF(tdp) {ID = IDS_DSRC; NC = 2;} TDBSRC(PODEF tdp) : TDBCAT(tdp) {}
protected: protected:
// Specific routines // Specific routines
virtual bool Initialize(PGLOBAL g); virtual PQRYRES GetResult(PGLOBAL g);
}; // end of class TDBSRC }; // end of class TDBSRC
/***********************************************************************/ /***********************************************************************/
/* This is the class declaration for the Drivers catalog table. */ /* This is the class declaration for the Drivers catalog table. */
/***********************************************************************/ /***********************************************************************/
class TDBDRV : public TDBOIF { class TDBDRV : public TDBCAT {
public: public:
// Constructor // Constructor
TDBDRV(PODEF tdp) : TDBOIF(tdp) {ID = IDS_DRIVER; NC = 2;} TDBDRV(PODEF tdp) : TDBCAT(tdp) {}
protected: protected:
// Specific routines // Specific routines
virtual bool Initialize(PGLOBAL g); virtual PQRYRES GetResult(PGLOBAL g);
}; // end of class TDBDRV }; // end of class TDBDRV
/***********************************************************************/ /***********************************************************************/
/* This is the class declaration for the columns catalog table. */ /* This is the class declaration for the tables catalog table. */
/***********************************************************************/ /***********************************************************************/
class TDBOCL : public TDBOIF { class TDBOTB : public TDBCAT {
public: public:
// Constructor // Constructor
TDBOCL(PODEF tdp); TDBOTB(PODEF tdp);
protected: protected:
// Specific routines // Specific routines
virtual bool Initialize(PGLOBAL g); virtual PQRYRES GetResult(PGLOBAL g);
// Members // Members
char *Dsn; // Points to connection string char *Dsn; // Points to connection string
char *Tabn; // Points to ODBC table name char *Tab; // Points to ODBC table name or pattern
}; // end of class TDBOCL }; // end of class TDBOTB
/***********************************************************************/ /***********************************************************************/
/* This is the class declaration for the tables catalog table. */ /* This is the class declaration for the columns catalog table. */
/***********************************************************************/ /***********************************************************************/
class TDBOTB : public TDBOIF { class TDBOCL : public TDBOTB {
public: public:
// Constructor // Constructor
TDBOTB(PODEF tdp); TDBOCL(PODEF tdp) : TDBOTB(tdp) {}
protected: protected:
// Specific routines // Specific routines
virtual bool Initialize(PGLOBAL g); virtual PQRYRES GetResult(PGLOBAL g);
// Members // Members
char *Dsn; // Points to connection string }; // end of class TDBOCL
char *Tabpat; // Points to ODBC table pattern
}; // end of class TDBOTB
#endif // !NODBC #endif // !NODBC
This diff is collapsed.
...@@ -27,7 +27,7 @@ typedef struct _WMIutil { ...@@ -27,7 +27,7 @@ typedef struct _WMIutil {
/***********************************************************************/ /***********************************************************************/
/* Functions used externally. */ /* Functions used externally. */
/***********************************************************************/ /***********************************************************************/
PQRYRES WMIColumns(PGLOBAL g, char *nsp, char *classname, PWMIUT wp); PQRYRES WMIColumns(PGLOBAL g, char *nsp, char *cls, bool info);
/* -------------------------- WMI classes ---------------------------- */ /* -------------------------- WMI classes ---------------------------- */
...@@ -37,10 +37,10 @@ PQRYRES WMIColumns(PGLOBAL g, char *nsp, char *classname, PWMIUT wp); ...@@ -37,10 +37,10 @@ PQRYRES WMIColumns(PGLOBAL g, char *nsp, char *classname, PWMIUT wp);
class WMIDEF : public TABDEF { /* Logical table description */ class WMIDEF : public TABDEF { /* Logical table description */
friend class TDBWMI; friend class TDBWMI;
friend class TDBWCL; friend class TDBWCL;
friend class TDBWCX;
public: public:
// Constructor // Constructor
WMIDEF(void) WMIDEF(void) {Pseudo = 3; Nspace = NULL; Wclass = NULL; Ems = 0;}
{Pseudo = 3; Nspace = NULL; Wclass = NULL; Ems = 0; Info = false;}
// Implementation // Implementation
virtual const char *GetType(void) {return "WMI";} virtual const char *GetType(void) {return "WMI";}
...@@ -55,7 +55,6 @@ class WMIDEF : public TABDEF { /* Logical table description */ ...@@ -55,7 +55,6 @@ class WMIDEF : public TABDEF { /* Logical table description */
char *Nspace; char *Nspace;
char *Wclass; char *Wclass;
int Ems; int Ems;
bool Info;
}; // end of WMIDEF }; // end of WMIDEF
/***********************************************************************/ /***********************************************************************/
...@@ -135,70 +134,18 @@ class WMICOL : public COLBLK { ...@@ -135,70 +134,18 @@ class WMICOL : public COLBLK {
}; // end of class WMICOL }; // end of class WMICOL
/***********************************************************************/ /***********************************************************************/
/* This is the class declaration for the WCL table. */ /* This is the class declaration for the WMI catalog table. */
/***********************************************************************/ /***********************************************************************/
class TDBWCL : public TDBASE { class TDBWCL : public TDBCAT {
friend class WCLCOL;
public: public:
// Constructor // Constructor
TDBWCL(PWMIDEF tdp); TDBWCL(PWMIDEF tdp);
// Implementation
virtual AMT GetAmType(void) {return TYPE_AM_WMI;}
// Methods
virtual int GetRecpos(void) {return N;}
virtual int GetProgCur(void) {return N;}
virtual int RowNumber(PGLOBAL g, bool b = false) {return N + 1;}
// Database routines
virtual PCOL MakeCol(PGLOBAL g, PCOLDEF cdp, PCOL cprec, int n);
virtual int GetMaxSize(PGLOBAL g);
virtual bool OpenDB(PGLOBAL g);
virtual int ReadDB(PGLOBAL g);
virtual int WriteDB(PGLOBAL g);
virtual int DeleteDB(PGLOBAL g, int irc);
virtual void CloseDB(PGLOBAL g);
protected: protected:
// Specific routines // Specific routines
bool Initialize(PGLOBAL g); virtual PQRYRES GetResult(PGLOBAL g);
// Members // Members
IWbemServices *Svc; // IWbemServices pointer char *Nsp; // Name space
IWbemClassObject *ClsObj; char *Cls; // Class
BSTR Propname;
char *Nspace; // Namespace
char *Wclass; // Class name
HRESULT Res;
bool Init;
bool Done;
int N; // Row number
int Lng;
int Typ;
int Prec;
}; // end of class TDBWCL }; // end of class TDBWCL
/***********************************************************************/
/* Class WMICOL: WMI Address column. */
/***********************************************************************/
class WCLCOL : public COLBLK {
friend class TDBWCL;
public:
// Constructors
WCLCOL(PCOLDEF cdp, PTDB tdbp, int n);
// Implementation
virtual int GetAmType(void) {return TYPE_AM_WMI;}
// Methods
virtual void ReadColumn(PGLOBAL g);
protected:
WCLCOL(void) {} // Default constructor not to be used
// Members
PTDBWCL Tdbp; // Points to WMI table block
HRESULT Res;
int Flag;
}; // end of class WCLCOL
...@@ -15,9 +15,12 @@ ...@@ -15,9 +15,12 @@
/***********************************************************************/ /***********************************************************************/
#include "assert.h" #include "assert.h"
#include "block.h" #include "block.h"
#include "colblk.h"
//pedef class INDEXDEF *PIXDEF; //pedef class INDEXDEF *PIXDEF;
typedef char *PFIL; // Specific to CONNECT typedef char *PFIL; // Specific to CONNECT
typedef class TDBCAT *PTDBCAT;
typedef class CATCOL *PCATCOL;
/***********************************************************************/ /***********************************************************************/
/* Definition of class TBX (pure virtual class for TDB and OPJOIN) */ /* Definition of class TBX (pure virtual class for TDB and OPJOIN) */
...@@ -198,4 +201,66 @@ class DllExport TDBASE : public TDB { ...@@ -198,4 +201,66 @@ class DllExport TDBASE : public TDB {
bool Read_Only; // True for read only tables bool Read_Only; // True for read only tables
}; // end of class TDBASE }; // end of class TDBASE
/***********************************************************************/
/* The abstract base class declaration for the catalog tables. */
/***********************************************************************/
class TDBCAT : public TDBASE {
friend class CATCOL;
public:
// Constructor
TDBCAT(PTABDEF tdp);
// Implementation
virtual AMT GetAmType(void) {return TYPE_AM_CAT;}
// Methods
virtual int GetRecpos(void) {return N;}
virtual int GetProgCur(void) {return N;}
virtual int RowNumber(PGLOBAL g, bool b = false) {return N + 1;}
// Database routines
virtual PCOL MakeCol(PGLOBAL g, PCOLDEF cdp, PCOL cprec, int n);
virtual int GetMaxSize(PGLOBAL g);
virtual bool OpenDB(PGLOBAL g);
virtual int ReadDB(PGLOBAL g);
virtual int WriteDB(PGLOBAL g);
virtual int DeleteDB(PGLOBAL g, int irc);
virtual void CloseDB(PGLOBAL g);
protected:
// Specific routines
virtual PQRYRES GetResult(PGLOBAL g) = 0;
bool Initialize(PGLOBAL g);
bool InitCol(PGLOBAL g);
// Members
PQRYRES Qrp;
int N; // Row number
bool Init;
}; // end of class TDBCAT
/***********************************************************************/
/* Class CATCOL: ODBC info column. */
/***********************************************************************/
class CATCOL : public COLBLK {
friend class TDBCAT;
public:
// Constructors
CATCOL(PCOLDEF cdp, PTDB tdbp, int n);
// Implementation
virtual int GetAmType(void) {return TYPE_AM_ODBC;}
// Methods
virtual void ReadColumn(PGLOBAL g);
protected:
CATCOL(void) {} // Default constructor not to be used
// Members
PTDBCAT Tdbp; // Points to ODBC table block
PCOLRES Crp; // The column data array
int Flag;
}; // end of class CATCOL
#endif // TABLE_DEFINED #endif // TABLE_DEFINED
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