summaryrefslogtreecommitdiff
path: root/storage/connect
diff options
context:
space:
mode:
authorSergei Golubchik <serg@mariadb.org>2017-03-30 12:48:42 +0200
committerSergei Golubchik <serg@mariadb.org>2017-03-30 12:48:42 +0200
commitda4d71d10d23c1ac2d10b72baee14991ccb7a146 (patch)
tree7cdf3a8c8e72ca7c1c8105427c04123f025bd870 /storage/connect
parent9ec85009985d644ce7ae797bc3572d0ad0f69bb0 (diff)
parenta00517ac9707ffd51c092f5af5d198c5ee789bb4 (diff)
downloadmariadb-git-da4d71d10d23c1ac2d10b72baee14991ccb7a146.tar.gz
Merge branch '10.1' into 10.2
Diffstat (limited to 'storage/connect')
-rw-r--r--storage/connect/CMakeLists.txt10
-rw-r--r--storage/connect/array.cpp108
-rw-r--r--storage/connect/array.h6
-rw-r--r--storage/connect/colblk.cpp16
-rw-r--r--storage/connect/connect.cc79
-rw-r--r--storage/connect/connect.h2
-rw-r--r--storage/connect/domdoc.cpp11
-rw-r--r--storage/connect/domdoc.h1
-rw-r--r--storage/connect/filamap.cpp12
-rw-r--r--storage/connect/filamdbf.cpp27
-rw-r--r--storage/connect/filamgz.cpp12
-rw-r--r--storage/connect/filamgz.h12
-rw-r--r--storage/connect/filamzip.cpp561
-rw-r--r--storage/connect/filamzip.h164
-rw-r--r--storage/connect/ha_connect.cc347
-rw-r--r--storage/connect/ha_connect.h2
-rw-r--r--storage/connect/inihandl.c2
-rw-r--r--storage/connect/ioapi.c21
-rw-r--r--storage/connect/jdbconn.cpp24
-rw-r--r--storage/connect/json.cpp80
-rw-r--r--storage/connect/jsonudf.cpp109
-rw-r--r--storage/connect/mycat.cc17
-rw-r--r--storage/connect/mycat.h2
-rw-r--r--storage/connect/myconn.cpp20
-rw-r--r--storage/connect/mysql-test/connect/r/xml_zip.result98
-rw-r--r--storage/connect/mysql-test/connect/r/zip.result240
-rw-r--r--storage/connect/mysql-test/connect/std_data/bios.json273
-rw-r--r--storage/connect/mysql-test/connect/std_data/xsample2.xml47
-rw-r--r--storage/connect/mysql-test/connect/t/have_zip.inc19
-rw-r--r--storage/connect/mysql-test/connect/t/xml_zip.test41
-rw-r--r--storage/connect/mysql-test/connect/t/zip.test136
-rw-r--r--storage/connect/odbconn.cpp14
-rw-r--r--storage/connect/plgdbsem.h26
-rw-r--r--storage/connect/plgdbutl.cpp14
-rw-r--r--storage/connect/plgxml.cpp4
-rw-r--r--storage/connect/plgxml.h2
-rw-r--r--storage/connect/plugutil.c3
-rw-r--r--storage/connect/reldef.cpp6
-rw-r--r--storage/connect/reldef.h18
-rw-r--r--storage/connect/tabdos.cpp40
-rw-r--r--storage/connect/tabdos.h8
-rw-r--r--storage/connect/tabext.cpp640
-rw-r--r--storage/connect/tabext.h200
-rw-r--r--storage/connect/tabfix.cpp4
-rw-r--r--storage/connect/tabfix.h2
-rw-r--r--storage/connect/tabfmt.cpp75
-rw-r--r--storage/connect/tabfmt.h5
-rw-r--r--storage/connect/tabjdbc.cpp555
-rw-r--r--storage/connect/tabjdbc.h129
-rw-r--r--storage/connect/tabjson.cpp31
-rw-r--r--storage/connect/tabjson.h4
-rw-r--r--storage/connect/table.cpp249
-rw-r--r--storage/connect/tabmac.cpp2
-rw-r--r--storage/connect/tabmac.h2
-rw-r--r--storage/connect/tabmul.cpp30
-rw-r--r--storage/connect/tabmul.h18
-rw-r--r--storage/connect/tabmysql.cpp183
-rw-r--r--storage/connect/tabmysql.h75
-rw-r--r--storage/connect/taboccur.cpp9
-rw-r--r--storage/connect/tabodbc.cpp321
-rw-r--r--storage/connect/tabodbc.h133
-rw-r--r--storage/connect/tabpivot.cpp7
-rw-r--r--storage/connect/tabpivot.h2
-rw-r--r--storage/connect/tabsys.cpp8
-rw-r--r--storage/connect/tabsys.h4
-rw-r--r--storage/connect/tabtbl.cpp23
-rw-r--r--storage/connect/tabutil.cpp23
-rw-r--r--storage/connect/tabutil.h8
-rw-r--r--storage/connect/tabvct.cpp6
-rw-r--r--storage/connect/tabvct.h2
-rw-r--r--storage/connect/tabvir.cpp2
-rw-r--r--storage/connect/tabwmi.cpp21
-rw-r--r--storage/connect/tabxcl.cpp8
-rw-r--r--storage/connect/tabxcl.h2
-rw-r--r--storage/connect/tabxml.cpp13
-rw-r--r--storage/connect/tabxml.h2
-rw-r--r--storage/connect/tabzip.cpp16
-rw-r--r--storage/connect/tabzip.h2
-rw-r--r--storage/connect/user_connect.cc2
-rw-r--r--storage/connect/user_connect.h2
-rw-r--r--storage/connect/value.h2
-rwxr-xr-xstorage/connect/xindex.cpp8
-rw-r--r--storage/connect/xindex.h4
-rw-r--r--storage/connect/xobject.h3
-rw-r--r--storage/connect/xtable.h211
-rw-r--r--storage/connect/zip.c14
86 files changed, 3994 insertions, 1702 deletions
diff --git a/storage/connect/CMakeLists.txt b/storage/connect/CMakeLists.txt
index ce6de424421..a602084b5bd 100644
--- a/storage/connect/CMakeLists.txt
+++ b/storage/connect/CMakeLists.txt
@@ -22,16 +22,16 @@ fmdlex.c osutil.c plugutil.c rcmsg.c rcmsg.h
array.cpp blkfil.cpp colblk.cpp csort.cpp
filamap.cpp filamdbf.cpp filamfix.cpp filamgz.cpp filamtxt.cpp
filter.cpp json.cpp jsonudf.cpp maputil.cpp myconn.cpp myutil.cpp plgdbutl.cpp
-reldef.cpp tabcol.cpp tabdos.cpp tabfix.cpp tabfmt.cpp tabjson.cpp table.cpp
-tabmul.cpp tabmysql.cpp taboccur.cpp tabpivot.cpp tabsys.cpp tabtbl.cpp tabutil.cpp
-tabvir.cpp tabxcl.cpp valblk.cpp value.cpp xindex.cpp xobject.cpp
+reldef.cpp tabcol.cpp tabdos.cpp tabext.cpp tabfix.cpp tabfmt.cpp tabjson.cpp
+table.cpp tabmul.cpp tabmysql.cpp taboccur.cpp tabpivot.cpp tabsys.cpp tabtbl.cpp
+tabutil.cpp tabvir.cpp tabxcl.cpp valblk.cpp value.cpp xindex.cpp xobject.cpp
array.h blkfil.h block.h catalog.h checklvl.h colblk.h connect.h csort.h
engmsg.h filamap.h filamdbf.h filamfix.h filamgz.h filamtxt.h
filter.h global.h ha_connect.h inihandl.h json.h jsonudf.h maputil.h msgid.h
mycat.h myconn.h myutil.h os.h osutil.h plgcnx.h plgdbsem.h preparse.h reldef.h
-resource.h tabcol.h tabdos.h tabfix.h tabfmt.h tabjson.h tabmul.h tabmysql.h
-taboccur.h tabpivot.h tabsys.h tabtbl.h tabutil.h tabvir.h tabxcl.h
+resource.h tabcol.h tabdos.h tabext.h tabfix.h tabfmt.h tabjson.h tabmul.h
+tabmysql.h taboccur.h tabpivot.h tabsys.h tabtbl.h tabutil.h tabvir.h tabxcl.h
user_connect.h valblk.h value.h xindex.h xobject.h xtable.h)
#
diff --git a/storage/connect/array.cpp b/storage/connect/array.cpp
index 193514eeb99..1998ab890e9 100644
--- a/storage/connect/array.cpp
+++ b/storage/connect/array.cpp
@@ -1,7 +1,7 @@
/************* Array C++ Functions Source Code File (.CPP) *************/
/* Name: ARRAY.CPP Version 2.3 */
/* */
-/* (C) Copyright to the author Olivier BERTRAND 2005-2015 */
+/* (C) Copyright to the author Olivier BERTRAND 2005-2017 */
/* */
/* This file contains the XOBJECT derived class ARRAY functions. */
/* ARRAY is used for elaborate type of processing, such as sorting */
@@ -141,7 +141,7 @@ PARRAY MakeValueArray(PGLOBAL g, PPARM pp)
/* ARRAY public constructor. */
/***********************************************************************/
ARRAY::ARRAY(PGLOBAL g, int type, int size, int length, int prec)
- : CSORT(FALSE)
+ : CSORT(false)
{
Nval = 0;
Ndif = 0;
@@ -188,14 +188,14 @@ ARRAY::ARRAY(PGLOBAL g, int type, int size, int length, int prec)
else if (type != TYPE_PCHAR)
Value = AllocateValue(g, type, Len, prec);
- Constant = TRUE;
+ Constant = true;
} // end of ARRAY constructor
#if 0
/***********************************************************************/
/* ARRAY public constructor from a QUERY. */
/***********************************************************************/
-ARRAY::ARRAY(PGLOBAL g, PQUERY qryp) : CSORT(FALSE)
+ARRAY::ARRAY(PGLOBAL g, PQUERY qryp) : CSORT(false)
{
Type = qryp->GetColType(0);
Nval = qryp->GetNblin();
@@ -206,7 +206,7 @@ ARRAY::ARRAY(PGLOBAL g, PQUERY qryp) : CSORT(FALSE)
Xsize = -1;
Len = qryp->GetColLength(0);
X = Inf = Sup = 0;
- Correlated = FALSE;
+ Correlated = false;
switch (Type) {
case TYPE_STRING:
@@ -229,13 +229,13 @@ ARRAY::ARRAY(PGLOBAL g, PQUERY qryp) : CSORT(FALSE)
// The error message was built by ???
Type = TYPE_ERROR;
- Constant = TRUE;
+ Constant = true;
} // end of ARRAY constructor
/***********************************************************************/
/* ARRAY constructor from a TYPE_LIST subarray. */
/***********************************************************************/
-ARRAY::ARRAY(PGLOBAL g, PARRAY par, int k) : CSORT(FALSE)
+ARRAY::ARRAY(PGLOBAL g, PARRAY par, int k) : CSORT(false)
{
int prec;
LSTBLK *lp;
@@ -260,7 +260,7 @@ ARRAY::ARRAY(PGLOBAL g, PARRAY par, int k) : CSORT(FALSE)
Len = (Type == TYPE_STRING) ? Vblp->GetVlen() : 0;
prec = (Type == TYPE_FLOAT) ? 2 : 0;
Value = AllocateValue(g, Type, Len, prec, NULL);
- Constant = TRUE;
+ Constant = true;
} // end of ARRAY constructor
/***********************************************************************/
@@ -283,7 +283,7 @@ bool ARRAY::AddValue(PGLOBAL g, PSZ strp)
{
if (Type != TYPE_STRING) {
sprintf(g->Message, MSG(ADD_BAD_TYPE), GetTypeName(Type), "CHAR");
- return TRUE;
+ return true;
} // endif Type
if (trace)
@@ -292,7 +292,7 @@ bool ARRAY::AddValue(PGLOBAL g, PSZ strp)
//Value->SetValue_psz(strp);
//Vblp->SetValue(valp, Nval++);
Vblp->SetValue(strp, Nval++);
- return FALSE;
+ return false;
} // end of AddValue
/***********************************************************************/
@@ -302,14 +302,14 @@ bool ARRAY::AddValue(PGLOBAL g, void *p)
{
if (Type != TYPE_PCHAR) {
sprintf(g->Message, MSG(ADD_BAD_TYPE), GetTypeName(Type), "PCHAR");
- return TRUE;
+ return true;
} // endif Type
if (trace)
htrc(" adding pointer(%d): %p\n", Nval, p);
Vblp->SetValue((PSZ)p, Nval++);
- return FALSE;
+ return false;
} // end of AddValue
/***********************************************************************/
@@ -319,7 +319,7 @@ bool ARRAY::AddValue(PGLOBAL g, short n)
{
if (Type != TYPE_SHORT) {
sprintf(g->Message, MSG(ADD_BAD_TYPE), GetTypeName(Type), "SHORT");
- return TRUE;
+ return true;
} // endif Type
if (trace)
@@ -328,7 +328,7 @@ bool ARRAY::AddValue(PGLOBAL g, short n)
//Value->SetValue(n);
//Vblp->SetValue(valp, Nval++);
Vblp->SetValue(n, Nval++);
- return FALSE;
+ return false;
} // end of AddValue
/***********************************************************************/
@@ -338,7 +338,7 @@ bool ARRAY::AddValue(PGLOBAL g, int n)
{
if (Type != TYPE_INT) {
sprintf(g->Message, MSG(ADD_BAD_TYPE), GetTypeName(Type), "INTEGER");
- return TRUE;
+ return true;
} // endif Type
if (trace)
@@ -347,7 +347,7 @@ bool ARRAY::AddValue(PGLOBAL g, int n)
//Value->SetValue(n);
//Vblp->SetValue(valp, Nval++);
Vblp->SetValue(n, Nval++);
- return FALSE;
+ return false;
} // end of AddValue
/***********************************************************************/
@@ -357,7 +357,7 @@ bool ARRAY::AddValue(PGLOBAL g, double d)
{
if (Type != TYPE_DOUBLE) {
sprintf(g->Message, MSG(ADD_BAD_TYPE), GetTypeName(Type), "DOUBLE");
- return TRUE;
+ return true;
} // endif Type
if (trace)
@@ -365,7 +365,7 @@ bool ARRAY::AddValue(PGLOBAL g, double d)
Value->SetValue(d);
Vblp->SetValue(Value, Nval++);
- return FALSE;
+ return false;
} // end of AddValue
/***********************************************************************/
@@ -376,7 +376,7 @@ bool ARRAY::AddValue(PGLOBAL g, PXOB xp)
if (Type != xp->GetResultType()) {
sprintf(g->Message, MSG(ADD_BAD_TYPE),
GetTypeName(xp->GetResultType()), GetTypeName(Type));
- return TRUE;
+ return true;
} // endif Type
if (trace)
@@ -384,7 +384,7 @@ bool ARRAY::AddValue(PGLOBAL g, PXOB xp)
//AddValue(xp->GetValue());
Vblp->SetValue(xp->GetValue(), Nval++);
- return FALSE;
+ return false;
} // end of AddValue
/***********************************************************************/
@@ -395,14 +395,14 @@ bool ARRAY::AddValue(PGLOBAL g, PVAL vp)
if (Type != vp->GetType()) {
sprintf(g->Message, MSG(ADD_BAD_TYPE),
GetTypeName(vp->GetType()), GetTypeName(Type));
- return TRUE;
+ return true;
} // endif Type
if (trace)
htrc(" adding (%d) from vp=%p\n", Nval, vp);
Vblp->SetValue(vp, Nval++);
- return FALSE;
+ return false;
} // end of AddValue
/***********************************************************************/
@@ -423,12 +423,12 @@ bool ARRAY::GetSubValue(PGLOBAL g, PVAL valp, int *kp)
if (Type != TYPE_LIST) {
sprintf(g->Message, MSG(NO_SUB_VAL), Type);
- return TRUE;
+ return true;
} // endif Type
vblp = ((LSTBLK*)Vblp)->Mbvk[kp[0]]->Vblk;
valp->SetValue_pvblk(vblp, kp[1]);
- return FALSE;
+ return false;
} // end of GetSubValue
#endif // 0
@@ -476,11 +476,11 @@ bool ARRAY::Find(PVAL valp)
else if (n > 0)
Inf = X;
else
- return TRUE;
+ return true;
} // endwhile
- return FALSE;
+ return false;
} // end of Find
/***********************************************************************/
@@ -504,9 +504,9 @@ bool ARRAY::FilTest(PGLOBAL g, PVAL valp, OPVAL opc, int opm)
int top = Nval - 1;
if (top < 0) // Array is empty
- // Return TRUE for ALL because it means that there are no item that
+ // Return true for ALL because it means that there are no item that
// does not verify the condition, which is true indeed.
- // Return FALSE for ANY because TRUE means that there is at least
+ // Return false for ANY because true means that there is at least
// one item that verifies the condition, which is false.
return opm == 2;
@@ -528,9 +528,9 @@ bool ARRAY::FilTest(PGLOBAL g, PVAL valp, OPVAL opc, int opm)
else if (opc == OP_NE && opm == 2)
return !Find(vp);
else if (opc == OP_EQ && opm == 2)
- return (Ndif == 1) ? !(Vcompare(vp, 0) & bt) : FALSE;
+ return (Ndif == 1) ? !(Vcompare(vp, 0) & bt) : false;
else if (opc == OP_NE && opm == 1)
- return (Ndif == 1) ? !(Vcompare(vp, 0) & bt) : TRUE;
+ return (Ndif == 1) ? !(Vcompare(vp, 0) & bt) : true;
if (Type != TYPE_LIST) {
if (opc == OP_GT || opc == OP_GE)
@@ -544,15 +544,15 @@ bool ARRAY::FilTest(PGLOBAL g, PVAL valp, OPVAL opc, int opm)
if (opm == 2) {
for (i = 0; i < Nval; i++)
if (Vcompare(vp, i) & bt)
- return FALSE;
+ return false;
- return TRUE;
+ return true;
} else { // opm == 1
for (i = 0; i < Nval; i++)
if (!(Vcompare(vp, i) & bt))
- return TRUE;
+ return true;
- return FALSE;
+ return false;
} // endif opm
} // end of FilTest
@@ -566,7 +566,7 @@ bool ARRAY::CanBeShort(void)
int* To_Val = (int*)Valblk->GetMemp();
if (Type != TYPE_INT || !Ndif)
- return FALSE;
+ return false;
// Because the array is sorted, this is true if all the array
// int values are in the range of SHORT values
@@ -582,7 +582,7 @@ bool ARRAY::CanBeShort(void)
int ARRAY::Convert(PGLOBAL g, int k, PVAL vp)
{
int i, prec = 0;
- bool b = FALSE;
+ bool b = false;
PMBV ovblk = Valblk;
PVBLK ovblp = Vblp;
@@ -619,7 +619,7 @@ int ARRAY::Convert(PGLOBAL g, int k, PVAL vp)
if (((DTVAL*)Value)->SetFormat(g, vp))
return TYPE_ERROR;
else
- b = TRUE; // Sort the new array on date internal values
+ b = true; // Sort the new array on date internal values
/*********************************************************************/
/* Do the actual conversion. */
@@ -706,7 +706,7 @@ void ARRAY::SetPrecision(PGLOBAL g, int p)
/***********************************************************************/
/* Sort and eliminate distinct values from an array. */
/* Note: this is done by making a sorted index on distinct values. */
-/* Returns FALSE if Ok or TRUE in case of error. */
+/* Returns false if Ok or true in case of error. */
/***********************************************************************/
bool ARRAY::Sort(PGLOBAL g)
{
@@ -789,14 +789,14 @@ bool ARRAY::Sort(PGLOBAL g)
Bot = -1; // For non optimized search
Top = Ndif; // Find searches the whole array.
- return FALSE;
+ return false;
error:
Nval = Ndif = 0;
Valblk->Free();
PlgDBfree(Index);
PlgDBfree(Offset);
- return TRUE;
+ return true;
} // end of Sort
/***********************************************************************/
@@ -839,9 +839,9 @@ void *ARRAY::GetSortIndex(PGLOBAL g)
/***********************************************************************/
/* Block filter testing for IN operator on Column/Array operands. */
-/* Here we call Find that returns TRUE if the value is in the array */
+/* Here we call Find that returns true if the value is in the array */
/* with X equal to the index of the found value in the array, or */
-/* FALSE if the value is not in the array with Inf and Sup being the */
+/* false if the value is not in the array with Inf and Sup being the */
/* indexes of the array values that are immediately below and over */
/* the not found value. This enables to restrict the array to the */
/* values that are between the min and max block values and to return */
@@ -854,9 +854,9 @@ int ARRAY::BlockTest(PGLOBAL, int opc, int opm,
bool bin, bax, pin, pax, veq, all = (opm == 2);
if (Ndif == 0) // Array is empty
- // Return TRUE for ALL because it means that there are no item that
+ // Return true for ALL because it means that there are no item that
// does not verify the condition, which is true indeed.
- // Return FALSE for ANY because TRUE means that there is at least
+ // Return false for ANY because true means that there is at least
// one item that verifies the condition, which is false.
return (all) ? 2 : -2;
else if (opc == OP_EQ && all && Ndif > 1)
@@ -864,7 +864,7 @@ int ARRAY::BlockTest(PGLOBAL, int opc, int opm,
else if (opc == OP_NE && !all && Ndif > 1)
return 2;
// else if (Ndif == 1)
-// all = FALSE;
+// all = false;
// veq is true when all values in the block are equal
switch (Type) {
@@ -874,7 +874,7 @@ int ARRAY::BlockTest(PGLOBAL, int opc, int opm,
case TYPE_SHORT: veq = *(short*)minp == *(short*)maxp; break;
case TYPE_INT: veq = *(int*)minp == *(int*)maxp; break;
case TYPE_DOUBLE: veq = *(double*)minp == *(double*)maxp; break;
- default: veq = FALSE; // Error ?
+ default: veq = false; // Error ?
} // endswitch type
if (!s)
@@ -898,7 +898,7 @@ int ARRAY::BlockTest(PGLOBAL, int opc, int opm,
case OP_GT: return -1; break;
} // endswitch opc
- pax = (opc == OP_GE) ? (X < Ndif - 1) : TRUE;
+ pax = (opc == OP_GE) ? (X < Ndif - 1) : true;
} else if (Inf == Bot) {
// Max value is smaller than min list value
return (opc == OP_LT || opc == OP_LE || opc == OP_NE) ? 1 : -1;
@@ -924,7 +924,7 @@ int ARRAY::BlockTest(PGLOBAL, int opc, int opm,
case OP_LT: return (s) ? -2 : -1; break;
} // endswitch opc
- pin = (opc == OP_LE) ? (X > 0) : TRUE;
+ pin = (opc == OP_LE) ? (X > 0) : true;
} else if (Sup == Ndif) {
// Min value is greater than max list value
if (opc == OP_GT || opc == OP_GE || opc == OP_NE)
@@ -956,7 +956,7 @@ int ARRAY::BlockTest(PGLOBAL, int opc, int opm,
// the only possible overlaps between the array and the block are:
// Array: +-------+ +-------+ +-------+ +-----+
// Block: +-----+ +---+ +------+ +--------+
- // TRUE: pax pin pax pin
+ // true: pax pin pax pin
if (all) switch (opc) {
case OP_GT:
case OP_GE: return (pax) ? -1 : 0; break;
@@ -1052,7 +1052,7 @@ void ARRAY::Print(PGLOBAL, char *ps, uint z)
/***********************************************************************/
/* MULAR public constructor. */
/***********************************************************************/
-MULAR::MULAR(PGLOBAL g, int n) : CSORT(FALSE)
+MULAR::MULAR(PGLOBAL g, int n) : CSORT(false)
{
Narray = n;
Pars = (PARRAY*)PlugSubAlloc(g, NULL, n * sizeof(PARRAY));
@@ -1075,7 +1075,7 @@ int MULAR::Qcompare(int *i1, int *i2)
/***********************************************************************/
/* Sort and eliminate distinct values from multiple arrays. */
/* Note: this is done by making a sorted index on distinct values. */
-/* Returns FALSE if Ok or TRUE in case of error. */
+/* Returns false if Ok or true in case of error. */
/***********************************************************************/
bool MULAR::Sort(PGLOBAL g)
{
@@ -1087,7 +1087,7 @@ bool MULAR::Sort(PGLOBAL g)
for (n = 1; n < Narray; n++)
if (Pars[n]->Nval != nval) {
strcpy(g->Message, MSG(BAD_ARRAY_VAL));
- return TRUE;
+ return true;
} // endif nval
// Prepare non conservative sort with offet values
@@ -1161,10 +1161,10 @@ bool MULAR::Sort(PGLOBAL g)
Pars[n]->Top = ndif; // Find searches the whole array.
} // endfor n
- return FALSE;
+ return false;
error:
PlgDBfree(Index);
PlgDBfree(Offset);
- return TRUE;
+ return true;
} // end of Sort
diff --git a/storage/connect/array.h b/storage/connect/array.h
index 6fb38ae6b47..dfc3638de8a 100644
--- a/storage/connect/array.h
+++ b/storage/connect/array.h
@@ -1,7 +1,7 @@
/**************** Array H Declares Source Code File (.H) ***************/
/* Name: ARRAY.H Version 3.1 */
/* */
-/* (C) Copyright to the author Olivier BERTRAND 2005-2014 */
+/* (C) Copyright to the author Olivier BERTRAND 2005-2017 */
/* */
/* This file contains the ARRAY and VALBASE derived classes declares. */
/***********************************************************************/
@@ -53,8 +53,8 @@ class DllExport ARRAY : public XOBJECT, public CSORT { // Array descblock
using XOBJECT::GetIntValue;
virtual void Reset(void) {Bot = -1;}
virtual int Qcompare(int *, int *);
- virtual bool Compare(PXOB) {assert(FALSE); return FALSE;}
- virtual bool SetFormat(PGLOBAL, FORMAT&) {assert(FALSE); return FALSE;}
+ virtual bool Compare(PXOB) {assert(false); return false;}
+ virtual bool SetFormat(PGLOBAL, FORMAT&) {assert(false); return false;}
//virtual int CheckSpcCol(PTDB, int) {return 0;}
virtual void Print(PGLOBAL g, FILE *f, uint n);
virtual void Print(PGLOBAL g, char *ps, uint z);
diff --git a/storage/connect/colblk.cpp b/storage/connect/colblk.cpp
index 80b405be041..58841387249 100644
--- a/storage/connect/colblk.cpp
+++ b/storage/connect/colblk.cpp
@@ -1,7 +1,7 @@
/************* Colblk C++ Functions Source Code File (.CPP) ************/
-/* Name: COLBLK.CPP Version 2.1 */
+/* Name: COLBLK.CPP Version 2.2 */
/* */
-/* (C) Copyright to the author Olivier BERTRAND 1998-2015 */
+/* (C) Copyright to the author Olivier BERTRAND 1998-2017 */
/* */
/* This file contains the COLBLK class functions. */
/***********************************************************************/
@@ -300,7 +300,7 @@ FIDBLK::FIDBLK(PCOLUMN cp, OPVAL op) : SPCBLK(cp), Op(op)
#if defined(__WIN__)
Format.Prec = 1; // Case insensitive
#endif // __WIN__
- Constant = (!((PTDBASE)To_Tdb)->GetDef()->GetMultiple() &&
+ Constant = (!To_Tdb->GetDef()->GetMultiple() &&
To_Tdb->GetAmType() != TYPE_AM_PLG &&
To_Tdb->GetAmType() != TYPE_AM_PLM);
Fn = NULL;
@@ -312,11 +312,11 @@ FIDBLK::FIDBLK(PCOLUMN cp, OPVAL op) : SPCBLK(cp), Op(op)
/***********************************************************************/
void FIDBLK::ReadColumn(PGLOBAL g)
{
- if (Fn != ((PTDBASE)To_Tdb)->GetFile(g)) {
+ if (Fn != To_Tdb->GetFile(g)) {
char filename[_MAX_PATH];
- Fn = ((PTDBASE)To_Tdb)->GetFile(g);
- PlugSetPath(filename, Fn, ((PTDBASE)To_Tdb)->GetPath());
+ Fn = To_Tdb->GetFile(g);
+ PlugSetPath(filename, Fn, To_Tdb->GetPath());
if (Op != OP_XX) {
char buff[_MAX_PATH];
@@ -378,10 +378,8 @@ void PRTBLK::ReadColumn(PGLOBAL g)
{
if (Pname == NULL) {
char *p;
- PTDBASE tdbp = (PTDBASE)To_Tdb;
-
- Pname = tdbp->GetDef()->GetStringCatInfo(g, "partname", "?");
+ Pname = To_Tdb->GetDef()->GetStringCatInfo(g, "partname", "?");
p = strrchr(Pname, '#');
Value->SetValue_psz((p) ? p + 1 : Pname);
} // endif Pname
diff --git a/storage/connect/connect.cc b/storage/connect/connect.cc
index 460d47bcf62..098119e7be1 100644
--- a/storage/connect/connect.cc
+++ b/storage/connect/connect.cc
@@ -12,7 +12,7 @@
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 */
+ Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02111-1301 USA */
/***********************************************************************/
/* Author Olivier BERTRAND bertrandop@gmail.com 2004-2015 */
@@ -157,23 +157,22 @@ bool CntCheckDB(PGLOBAL g, PHC handler, const char *pathname)
/* Returns valid: true if this is a table info. */
/***********************************************************************/
bool CntInfo(PGLOBAL g, PTDB tp, PXF info)
- {
- bool b;
- PTDBDOS tdbp= (PTDBDOS)tp;
+{
+ if (tp) {
+ bool b = (tp->GetFtype() == RECFM_NAF);
+ PTDBDOS tdbp = b ? NULL : (PTDBDOS)tp;
- if (tdbp) {
- b= tdbp->GetFtype() != RECFM_NAF;
- info->data_file_length= (b) ? (ulonglong)tdbp->GetFileLength(g) : 0;
+ info->data_file_length = (b) ? 0 : (ulonglong)tdbp->GetFileLength(g);
- if (!b || info->data_file_length)
- info->records= (unsigned)tdbp->Cardinality(g);
-// info->records= (unsigned)tdbp->GetMaxSize(g);
+ if (b || info->data_file_length)
+ info->records= (unsigned)tp->Cardinality(g);
+// info->records= (unsigned)tp->GetMaxSize(g);
else
info->records= 0;
// info->mean_rec_length= tdbp->GetLrecl();
info->mean_rec_length= 0;
- info->data_file_name= (b) ? tdbp->GetFile(g) : NULL;
+ info->data_file_name= (b) ? NULL : tdbp->GetFile(g);
return true;
} else {
info->data_file_length= 0;
@@ -183,7 +182,7 @@ bool CntInfo(PGLOBAL g, PTDB tp, PXF info)
return false;
} // endif tdbp
- } // end of CntInfo
+} // end of CntInfo
/***********************************************************************/
/* GetTDB: Get the table description block of a CONNECT table. */
@@ -332,9 +331,9 @@ bool CntOpenTable(PGLOBAL g, PTDB tdbp, MODE mode, char *c1, char *c2,
} // endfor colp
// Attach the updated columns list to the main table
- ((PTDBASE)tdbp)->SetSetCols(utp->GetColumns());
+ tdbp->SetSetCols(utp->GetColumns());
} else if (tdbp && mode == MODE_INSERT)
- ((PTDBASE)tdbp)->SetSetCols(tdbp->GetColumns());
+ tdbp->SetSetCols(tdbp->GetColumns());
// Now do open the physical table
if (trace)
@@ -343,7 +342,7 @@ bool CntOpenTable(PGLOBAL g, PTDB tdbp, MODE mode, char *c1, char *c2,
//tdbp->SetMode(mode);
- if (del/* && ((PTDBASE)tdbp)->GetFtype() != RECFM_NAF*/) {
+ if (del/* && (tdbp->GetFtype() != RECFM_NAF*/) {
// To avoid erasing the table when doing a partial delete
// make a fake Next
// PDOSDEF ddp= new(g) DOSDEF;
@@ -436,7 +435,7 @@ RCODE CntReadNext(PGLOBAL g, PTDB tdbp)
if (!tdbp)
return RC_FX;
- else if (((PTDBASE)tdbp)->GetKindex()) {
+ else if (tdbp->GetKindex()) {
// Reading sequencially an indexed table. This happens after the
// handler function records_in_range was called and MySQL decides
// to quit using the index (!!!) Drop the index.
@@ -483,7 +482,7 @@ RCODE CntWriteRow(PGLOBAL g, PTDB tdbp)
{
RCODE rc;
PCOL colp;
- PTDBASE tp= (PTDBASE)tdbp;
+//PTDBASE tp= (PTDBASE)tdbp;
if (!tdbp)
return RC_FX;
@@ -501,13 +500,13 @@ RCODE CntWriteRow(PGLOBAL g, PTDB tdbp)
} // endif rc
// Store column values in table write buffer(s)
- for (colp= tp->GetSetCols(); colp; colp= colp->GetNext())
+ for (colp= tdbp->GetSetCols(); colp; colp= colp->GetNext())
if (!colp->GetColUse(U_VIRTUAL))
colp->WriteColumn(g);
- if (tp->IsIndexed())
+ if (tdbp->IsIndexed())
// Index values must be sorted before updating
- rc= (RCODE)((PTDBDOS)tp)->GetTxfp()->StoreValues(g, true);
+ rc= (RCODE)((PTDBDOS)tdbp)->GetTxfp()->StoreValues(g, true);
else
// Return result code from write operation
rc= (RCODE)tdbp->WriteDB(g);
@@ -535,7 +534,7 @@ RCODE CntUpdateRow(PGLOBAL g, PTDB tdbp)
RCODE CntDeleteRow(PGLOBAL g, PTDB tdbp, bool all)
{
RCODE rc;
- PTDBASE tp= (PTDBASE)tdbp;
+//PTDBASE tp= (PTDBASE)tdbp;
if (!tdbp || tdbp->GetMode() != MODE_DELETE)
return RC_FX;
@@ -543,16 +542,16 @@ RCODE CntDeleteRow(PGLOBAL g, PTDB tdbp, bool all)
return RC_NF;
if (all) {
- if (((PTDBASE)tdbp)->GetDef()->Indexable())
+ if (tdbp->GetDef()->Indexable())
((PTDBDOS)tdbp)->Cardinal= 0;
// Note: if all, this call will be done when closing the table
rc= (RCODE)tdbp->DeleteDB(g, RC_FX);
-//} else if (tp->GetKindex() && !tp->GetKindex()->IsSorted() &&
-// tp->Txfp->GetAmType() != TYPE_AM_DBF) {
- } else if(tp->IsIndexed()) {
+//} else if (tdbp->GetKindex() && !((PTDBASE)tdbp)->GetKindex()->IsSorted() &&
+// ((PTDBASE)tdbp)->Txfp->GetAmType() != TYPE_AM_DBF) {
+ } else if(tdbp->IsIndexed()) {
// Index values must be sorted before updating
- rc= (RCODE)((PTDBDOS)tp)->GetTxfp()->StoreValues(g, false);
+ rc= (RCODE)((PTDBDOS)tdbp)->GetTxfp()->StoreValues(g, false);
} else // Return result code from delete operation
rc= (RCODE)tdbp->DeleteDB(g, RC_OK);
@@ -565,7 +564,7 @@ RCODE CntDeleteRow(PGLOBAL g, PTDB tdbp, bool all)
int CntCloseTable(PGLOBAL g, PTDB tdbp, bool nox, bool abort)
{
int rc= RC_OK;
- TDBASE *tbxp= (PTDBASE)tdbp;
+//TDBASE *tbxp= (PTDBASE)tdbp;
if (!tdbp)
return rc; // Nothing to do
@@ -581,13 +580,13 @@ int CntCloseTable(PGLOBAL g, PTDB tdbp, bool nox, bool abort)
tdbp, tdbp->GetMode(), nox, abort);
if (tdbp->GetMode() == MODE_DELETE && tdbp->GetUse() == USE_OPEN) {
- if (tbxp->IsIndexed())
+ if (tdbp->IsIndexed())
rc= ((PTDBDOS)tdbp)->GetTxfp()->DeleteSortedRows(g);
if (!rc)
rc= tdbp->DeleteDB(g, RC_EF); // Specific A.M. delete routine
- } else if (tbxp->GetMode() == MODE_UPDATE && tbxp->IsIndexed())
+ } else if (tdbp->GetMode() == MODE_UPDATE && tdbp->IsIndexed())
rc= ((PTDBDOX)tdbp)->Txfp->UpdateSortedRows(g);
switch(rc) {
@@ -595,7 +594,7 @@ int CntCloseTable(PGLOBAL g, PTDB tdbp, bool nox, bool abort)
abort= true;
break;
case RC_INFO:
- PushWarning(g, tbxp);
+ PushWarning(g, tdbp);
break;
} // endswitch rc
@@ -631,11 +630,13 @@ int CntCloseTable(PGLOBAL g, PTDB tdbp, bool nox, bool abort)
if (trace > 1)
printf("About to reset opt\n");
- // Make all the eventual indexes
- tbxp= (TDBDOX*)tdbp;
- tbxp->ResetKindex(g, NULL);
- tbxp->SetKey_Col(NULL);
- rc= tbxp->ResetTableOpt(g, true, tbxp->GetDef()->Indexable() == 1);
+ if (!tdbp->IsRemote()) {
+ // Make all the eventual indexes
+ PTDBDOX tbxp = (PTDBDOX)tdbp;
+ tbxp->ResetKindex(g, NULL);
+ tbxp->SetKey_Col(NULL);
+ rc = tbxp->ResetTableOpt(g, true, tbxp->GetDef()->Indexable() == 1);
+ } // endif remote
err:
if (trace > 1)
@@ -657,10 +658,10 @@ int CntIndexInit(PGLOBAL g, PTDB ptdb, int id, bool sorted)
if (!ptdb)
return -1;
- else if (!((PTDBASE)ptdb)->GetDef()->Indexable()) {
+ else if (!ptdb->GetDef()->Indexable()) {
sprintf(g->Message, MSG(TABLE_NO_INDEX), ptdb->GetName());
return 0;
- } else if (((PTDBASE)ptdb)->GetDef()->Indexable() == 3) {
+ } else if (ptdb->GetDef()->Indexable() == 3) {
return 1;
} else
tdbp= (PTDBDOX)ptdb;
@@ -745,7 +746,7 @@ RCODE CntIndexRead(PGLOBAL g, PTDB ptdb, OPVAL op,
if (!ptdb)
return RC_FX;
else
- x= ((PTDBASE)ptdb)->GetDef()->Indexable();
+ x= ptdb->GetDef()->Indexable();
if (!x) {
sprintf(g->Message, MSG(TABLE_NO_INDEX), ptdb->GetName());
@@ -875,7 +876,7 @@ int CntIndexRange(PGLOBAL g, PTDB ptdb, const uchar* *key, uint *len,
if (!ptdb)
return -1;
- x= ((PTDBASE)ptdb)->GetDef()->Indexable();
+ x= ptdb->GetDef()->Indexable();
if (!x) {
sprintf(g->Message, MSG(TABLE_NO_INDEX), ptdb->GetName());
diff --git a/storage/connect/connect.h b/storage/connect/connect.h
index ce4cf9bf8b9..128561b80f3 100644
--- a/storage/connect/connect.h
+++ b/storage/connect/connect.h
@@ -11,7 +11,7 @@
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 */
+ Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02111-1301 USA */
/**************** Cnt H Declares Source Code File (.H) *****************/
/* Name: CONNECT.H Version 2.4 */
diff --git a/storage/connect/domdoc.cpp b/storage/connect/domdoc.cpp
index eb9660b439d..1622ec16c68 100644
--- a/storage/connect/domdoc.cpp
+++ b/storage/connect/domdoc.cpp
@@ -116,7 +116,9 @@ bool DOMDOC::ParseFile(PGLOBAL g, char *fn)
// Parse an in memory document
char *xdoc = GetMemDoc(g, fn);
- b = (xdoc) ? (bool)Docp->loadXML((_bstr_t)xdoc) : false;
+ // This is not equivalent to load for UTF8 characters
+ // It is why get node content is not the same
+ b = (xdoc) ? (bool)Docp->loadXML((_bstr_t)xdoc) : false;
} else
// Load the document
b = (bool)Docp->load((_bstr_t)fn);
@@ -266,6 +268,7 @@ DOMNODE::DOMNODE(PXDOC dp, MSXML2::IXMLDOMNodePtr np) : XMLNODE(dp)
Nodep = np;
Ws = NULL;
Len = 0;
+ Zip = (bool)dp->zip;
} // end of DOMNODE constructor
/******************************************************************/
@@ -316,8 +319,10 @@ RCODE DOMNODE::GetContent(PGLOBAL g, char *buf, int len)
RCODE rc = RC_OK;
// Nodep can be null for a missing HTML table column
- if (Nodep) {
- if (!WideCharToMultiByte(CP_UTF8, 0, Nodep->text, -1,
+ if (Nodep) {
+ if (Zip) {
+ strcpy(buf, Nodep->text);
+ } else if (!WideCharToMultiByte(CP_UTF8, 0, Nodep->text, -1,
buf, len, NULL, NULL)) {
DWORD lsr = GetLastError();
diff --git a/storage/connect/domdoc.h b/storage/connect/domdoc.h
index cfec98a9422..7f269002d59 100644
--- a/storage/connect/domdoc.h
+++ b/storage/connect/domdoc.h
@@ -93,6 +93,7 @@ class DOMNODE : public XMLNODE {
char Name[64];
WCHAR *Ws;
int Len;
+ bool Zip;
}; // end of class DOMNODE
/******************************************************************/
diff --git a/storage/connect/filamap.cpp b/storage/connect/filamap.cpp
index 94c562a9981..8fffaca3d06 100644
--- a/storage/connect/filamap.cpp
+++ b/storage/connect/filamap.cpp
@@ -5,7 +5,7 @@
/* */
/* COPYRIGHT: */
/* ---------- */
-/* (C) Copyright to the author Olivier BERTRAND 2005-2015 */
+/* (C) Copyright to the author Olivier BERTRAND 2005-2017 */
/* */
/* WHAT THIS PROGRAM DOES: */
/* ----------------------- */
@@ -45,6 +45,7 @@
#include "maputil.h"
#include "filamap.h"
#include "tabdos.h"
+#include "tabfmt.h"
/* --------------------------- Class MAPFAM -------------------------- */
@@ -322,17 +323,20 @@ int MAPFAM::ReadBuffer(PGLOBAL g)
int rc, len;
// Are we at the end of the memory
- if (Mempos >= Top)
+ if (Mempos >= Top) {
if ((rc = GetNext(g)) != RC_OK)
return rc;
+ else if (Tdbp->GetAmType() == TYPE_AM_CSV && ((PTDBCSV)Tdbp)->Header)
+ if ((rc = SkipRecord(g, true)) != RC_OK)
+ return rc;
+
+ } // endif Mempos
if (!Placed) {
/*******************************************************************/
/* Record file position in case of UPDATE or DELETE. */
/*******************************************************************/
- int rc;
-
next:
Fpos = Mempos;
CurBlk = (int)Rows++;
diff --git a/storage/connect/filamdbf.cpp b/storage/connect/filamdbf.cpp
index 5e3dfd8fe60..55feaa02bc4 100644
--- a/storage/connect/filamdbf.cpp
+++ b/storage/connect/filamdbf.cpp
@@ -5,7 +5,7 @@
/* */
/* COPYRIGHT: */
/* ---------- */
-/* (C) Copyright to the author Olivier BERTRAND 2005-2015 */
+/* (C) Copyright to the author Olivier BERTRAND 2005-2017 */
/* */
/* WHAT THIS PROGRAM DOES: */
/* ----------------------- */
@@ -281,15 +281,25 @@ PQRYRES DBFColumns(PGLOBAL g, char *dp, const char *fn, bool info)
/************************************************************************/
switch (thisfield.Type) {
case 'C': // Characters
- case 'L': // Logical 'T' or 'F'
- type = TYPE_STRING;
+ case 'L': // Logical 'T' or 'F' or space
+ type = TYPE_STRING;
+ break;
+ case 'M': // Memo a .DBT block number
+ case 'B': // Binary a .DBT block number
+ case 'G': // Ole a .DBT block number
+ type = TYPE_STRING;
break;
+ //case 'I': // Long
+ //case '+': // Autoincrement
+ // type = TYPE_INT;
+ // break;
case 'N':
type = (thisfield.Decimals) ? TYPE_DOUBLE
: (len > 10) ? TYPE_BIGINT : TYPE_INT;
break;
- case 'F':
- type = TYPE_DOUBLE;
+ case 'F': // Float
+ //case 'O': // Double
+ type = TYPE_DOUBLE;
break;
case 'D':
type = TYPE_DATE; // Is this correct ???
@@ -441,6 +451,7 @@ int DBFFAM::Cardinality(PGLOBAL g)
if (Accept) {
Lrecl = rln;
+ Blksize = Nrec * rln;
PushWarning(g, Tdbp);
} else
return -1;
@@ -582,6 +593,7 @@ bool DBFFAM::AllocateBuffer(PGLOBAL g)
if (Accept) {
Lrecl = reclen;
+ Blksize = Nrec * Lrecl;
PushWarning(g, Tdbp);
} else
return true;
@@ -598,7 +610,7 @@ bool DBFFAM::AllocateBuffer(PGLOBAL g)
header->Filedate[1] = datm->tm_mon + 1;
header->Filedate[2] = datm->tm_mday;
header->SetHeadlen((ushort)hlen);
- header->SetReclen((ushort)reclen);
+ header->SetReclen(reclen);
descp = (DESCRIPTOR*)header;
// Currently only standard Xbase types are supported
@@ -664,6 +676,7 @@ bool DBFFAM::AllocateBuffer(PGLOBAL g)
if (Accept) {
Lrecl = header.Reclen();
+ Blksize = Nrec * Lrecl;
PushWarning(g, Tdbp);
} else
return true;
@@ -956,6 +969,7 @@ int DBMFAM::Cardinality(PGLOBAL g)
if (Accept) {
Lrecl = rln;
+ Blksize = Nrec * Lrecl;
PushWarning(g, Tdbp);
} else
return -1;
@@ -1008,6 +1022,7 @@ bool DBMFAM::AllocateBuffer(PGLOBAL g)
if (Accept) {
Lrecl = hp->Reclen();
+ Blksize = Nrec * Lrecl;
PushWarning(g, Tdbp);
} else
return true;
diff --git a/storage/connect/filamgz.cpp b/storage/connect/filamgz.cpp
index 07242ea633c..dc6f277ee27 100644
--- a/storage/connect/filamgz.cpp
+++ b/storage/connect/filamgz.cpp
@@ -724,20 +724,20 @@ void ZBKFAM::Rewind(void)
/***********************************************************************/
/* Constructors. */
/***********************************************************************/
-ZIXFAM::ZIXFAM(PDOSDEF tdp) : ZBKFAM(tdp)
+GZXFAM::GZXFAM(PDOSDEF tdp) : ZBKFAM(tdp)
{
//Block = tdp->GetBlock();
//Last = tdp->GetLast();
Nrec = (tdp->GetElemt()) ? tdp->GetElemt() : DOS_BUFF_LEN;
Blksize = Nrec * Lrecl;
- } // end of ZIXFAM standard constructor
+ } // end of GZXFAM standard constructor
/***********************************************************************/
/* ZIX Cardinality: returns table cardinality in number of rows. */
/* This function can be called with a null argument to test the */
/* availability of Cardinality implementation (1 yes, 0 no). */
/***********************************************************************/
-int ZIXFAM::Cardinality(PGLOBAL g)
+int GZXFAM::Cardinality(PGLOBAL g)
{
if (Last)
return (g) ? (int)((Block - 1) * Nrec + Last) : 1;
@@ -750,7 +750,7 @@ int ZIXFAM::Cardinality(PGLOBAL g)
/* Allocate the line buffer. For mode Delete a bigger buffer has to */
/* be allocated because is it also used to move lines into the file. */
/***********************************************************************/
-bool ZIXFAM::AllocateBuffer(PGLOBAL g)
+bool GZXFAM::AllocateBuffer(PGLOBAL g)
{
Buflen = Blksize;
To_Buf = (char*)PlugSubAlloc(g, NULL, Buflen);
@@ -788,7 +788,7 @@ bool ZIXFAM::AllocateBuffer(PGLOBAL g)
/***********************************************************************/
/* ReadBuffer: Read one line from a compressed text file. */
/***********************************************************************/
-int ZIXFAM::ReadBuffer(PGLOBAL g)
+int GZXFAM::ReadBuffer(PGLOBAL g)
{
int n, rc = RC_OK;
@@ -850,7 +850,7 @@ int ZIXFAM::ReadBuffer(PGLOBAL g)
/* WriteDB: Data Base write routine for ZDOS access method. */
/* Update is not possible without using a temporary file (NIY). */
/***********************************************************************/
-int ZIXFAM::WriteBuffer(PGLOBAL g)
+int GZXFAM::WriteBuffer(PGLOBAL g)
{
/*********************************************************************/
/* In Insert mode, blocs are added sequentialy to the file end. */
diff --git a/storage/connect/filamgz.h b/storage/connect/filamgz.h
index d667fdddcc2..7a00c0d4bc7 100644
--- a/storage/connect/filamgz.h
+++ b/storage/connect/filamgz.h
@@ -12,7 +12,7 @@
typedef class GZFAM *PGZFAM;
typedef class ZBKFAM *PZBKFAM;
-typedef class ZIXFAM *PZIXFAM;
+typedef class GZXFAM *PZIXFAM;
typedef class ZLBFAM *PZLBFAM;
/***********************************************************************/
@@ -101,16 +101,16 @@ class DllExport ZBKFAM : public GZFAM {
/* length files compressed using the gzip library functions. */
/* The file is always accessed by block. */
/***********************************************************************/
-class DllExport ZIXFAM : public ZBKFAM {
+class DllExport GZXFAM : public ZBKFAM {
public:
// Constructor
- ZIXFAM(PDOSDEF tdp);
- ZIXFAM(PZIXFAM txfp) : ZBKFAM(txfp) {}
+ GZXFAM(PDOSDEF tdp);
+ GZXFAM(PZIXFAM txfp) : ZBKFAM(txfp) {}
// Implementation
virtual int GetNextPos(void) {return 0;}
virtual PTXF Duplicate(PGLOBAL g)
- {return (PTXF)new(g) ZIXFAM(this);}
+ {return (PTXF)new(g) GZXFAM(this);}
// Methods
virtual int Cardinality(PGLOBAL g);
@@ -120,7 +120,7 @@ class DllExport ZIXFAM : public ZBKFAM {
protected:
// No additional Members
- }; // end of class ZIXFAM
+ }; // end of class GZXFAM
/***********************************************************************/
/* This is the DOS/UNIX Access Method class declaration for PlugDB */
diff --git a/storage/connect/filamzip.cpp b/storage/connect/filamzip.cpp
index 6aca4631f32..3d157da5e87 100644
--- a/storage/connect/filamzip.cpp
+++ b/storage/connect/filamzip.cpp
@@ -1,11 +1,11 @@
/*********** File AM Zip C++ Program Source Code File (.CPP) ***********/
/* PROGRAM NAME: FILAMZIP */
/* ------------- */
-/* Version 1.0 */
+/* Version 1.1 */
/* */
/* COPYRIGHT: */
/* ---------- */
-/* (C) Copyright to the author Olivier BERTRAND 2016 */
+/* (C) Copyright to the author Olivier BERTRAND 2016-2017 */
/* */
/* WHAT THIS PROGRAM DOES: */
/* ----------------------- */
@@ -19,13 +19,16 @@
#include "my_global.h"
#if !defined(__WIN__)
#if defined(UNIX)
+#include <fnmatch.h>
#include <errno.h>
+#include <dirent.h>
#include <unistd.h>
#else // !UNIX
#include <io.h>
#endif // !UNIX
#include <fcntl.h>
#endif // !__WIN__
+#include <time.h>
/***********************************************************************/
/* Include application header files: */
@@ -40,12 +43,346 @@
//#include "tabzip.h"
#include "filamzip.h"
+#define WRITEBUFFERSIZE (16384)
+
+bool ZipLoadFile(PGLOBAL g, char *zfn, char *fn, char *entry, bool append, bool mul);
+
+/***********************************************************************/
+/* Compress a file in zip when creating a table. */
+/***********************************************************************/
+static bool ZipFile(PGLOBAL g, ZIPUTIL *zutp, char *fn, char *entry, char *buf)
+{
+ int rc = RC_OK, size_read, size_buf = WRITEBUFFERSIZE;
+ FILE *fin;
+
+ if (zutp->addEntry(g, entry))
+ return true;
+ else if (!(fin = fopen(fn, "rb"))) {
+ sprintf(g->Message, "error in opening %s for reading", fn);
+ return true;
+ } // endif fin
+
+ do {
+ size_read = (int)fread(buf, 1, size_buf, fin);
+
+ if (size_read < size_buf && feof(fin) == 0) {
+ sprintf(g->Message, "error in reading %s", fn);
+ rc = RC_FX;
+ } // endif size_read
+
+ if (size_read > 0) {
+ rc = zutp->writeEntry(g, buf, size_read);
+
+ if (rc == RC_FX)
+ sprintf(g->Message, "error in writing %s in the zipfile", fn);
+
+ } // endif size_read
+
+ } while (rc == RC_OK && size_read > 0);
+
+ fclose(fin);
+ zutp->closeEntry();
+ return rc != RC_OK;
+} // end of ZipFile
+
+/***********************************************************************/
+/* Find and Compress several files in zip when creating a table. */
+/***********************************************************************/
+static bool ZipFiles(PGLOBAL g, ZIPUTIL *zutp, char *pat, char *buf)
+{
+ char filename[_MAX_PATH];
+ int rc;
+
+ /*********************************************************************/
+ /* pat is a multiple file name with wildcard characters */
+ /*********************************************************************/
+ strcpy(filename, pat);
+
+#if defined(__WIN__)
+ char drive[_MAX_DRIVE], direc[_MAX_DIR];
+ WIN32_FIND_DATA FileData;
+ HANDLE hSearch;
+
+ _splitpath(filename, drive, direc, NULL, NULL);
+
+ // Start searching files in the target directory.
+ hSearch = FindFirstFile(filename, &FileData);
+
+ if (hSearch == INVALID_HANDLE_VALUE) {
+ rc = GetLastError();
+
+ if (rc != ERROR_FILE_NOT_FOUND) {
+ FormatMessage(FORMAT_MESSAGE_FROM_SYSTEM | FORMAT_MESSAGE_IGNORE_INSERTS,
+ NULL, GetLastError(), 0, (LPTSTR)&filename, sizeof(filename), NULL);
+ sprintf(g->Message, MSG(BAD_FILE_HANDLE), filename);
+ return true;
+ } else {
+ strcpy(g->Message, "Cannot find any file to load");
+ return true;
+ } // endif rc
+
+ } // endif hSearch
+
+ while (true) {
+ if (!(FileData.dwFileAttributes & FILE_ATTRIBUTE_DIRECTORY)) {
+ strcat(strcat(strcpy(filename, drive), direc), FileData.cFileName);
+
+ if (ZipFile(g, zutp, filename, FileData.cFileName, buf)) {
+ FindClose(hSearch);
+ return true;
+ } // endif ZipFile
+
+ } // endif dwFileAttributes
+
+ if (!FindNextFile(hSearch, &FileData)) {
+ rc = GetLastError();
+
+ if (rc != ERROR_NO_MORE_FILES) {
+ sprintf(g->Message, MSG(NEXT_FILE_ERROR), rc);
+ FindClose(hSearch);
+ return true;
+ } // endif rc
+
+ break;
+ } // endif FindNextFile
+
+ } // endwhile n
+
+ // Close the search handle.
+ if (!FindClose(hSearch)) {
+ strcpy(g->Message, MSG(SRCH_CLOSE_ERR));
+ return true;
+ } // endif FindClose
+
+#else // !__WIN__
+ struct stat fileinfo;
+ char fn[FN_REFLEN], direc[FN_REFLEN], pattern[FN_HEADLEN], ftype[FN_EXTLEN];
+ DIR *dir;
+ struct dirent *entry;
+
+ _splitpath(filename, NULL, direc, pattern, ftype);
+ strcat(pattern, ftype);
+
+ // Start searching files in the target directory.
+ if (!(dir = opendir(direc))) {
+ sprintf(g->Message, MSG(BAD_DIRECTORY), direc, strerror(errno));
+ return true;
+ } // endif dir
+
+ while ((entry = readdir(dir))) {
+ strcat(strcpy(fn, direc), entry->d_name);
+
+ if (lstat(fn, &fileinfo) < 0) {
+ sprintf(g->Message, "%s: %s", fn, strerror(errno));
+ return true;
+ } else if (!S_ISREG(fileinfo.st_mode))
+ continue; // Not a regular file (should test for links)
+
+ /*******************************************************************/
+ /* Test whether the file name matches the table name filter. */
+ /*******************************************************************/
+ if (fnmatch(pattern, entry->d_name, 0))
+ continue; // Not a match
+
+ strcat(strcpy(filename, direc), entry->d_name);
+
+ if (ZipFile(g, zutp, filename, entry->d_name, buf)) {
+ closedir(dir);
+ return true;
+ } // endif ZipFile
+
+ } // endwhile readdir
+
+ // Close the dir handle.
+ closedir(dir);
+#endif // !__WIN__
+
+ return false;
+} // end of ZipFiles
+
+/***********************************************************************/
+/* Load and Compress a file in zip when creating a table. */
+/***********************************************************************/
+bool ZipLoadFile(PGLOBAL g, char *zfn, char *fn, char *entry, bool append, bool mul)
+{
+ char *buf;
+ bool err;
+ ZIPUTIL *zutp = new(g) ZIPUTIL(NULL);
+
+ if (zutp->open(g, zfn, append))
+ return true;
+
+ buf = (char*)PlugSubAlloc(g, NULL, WRITEBUFFERSIZE);
+
+ if (mul)
+ err = ZipFiles(g, zutp, fn, buf);
+ else
+ err = ZipFile(g, zutp, fn, entry, buf);
+
+ zutp->close();
+ return err;
+} // end of ZipLoadFile
+
/* -------------------------- class ZIPUTIL -------------------------- */
/***********************************************************************/
/* Constructors. */
/***********************************************************************/
-ZIPUTIL::ZIPUTIL(PSZ tgt, bool mul)
+ZIPUTIL::ZIPUTIL(PSZ tgt)
+{
+ zipfile = NULL;
+ target = tgt;
+ fp = NULL;
+ entryopen = false;
+} // end of ZIPUTIL standard constructor
+
+#if 0
+ZIPUTIL::ZIPUTIL(ZIPUTIL *zutp)
+{
+ zipfile = zutp->zipfile;
+ target = zutp->target;
+ fp = zutp->fp;
+ entryopen = zutp->entryopen;
+} // end of UNZIPUTL copy constructor
+#endif // 0
+
+/***********************************************************************/
+/* Fill the zip time structure */
+/* param: tmZip time structure to be filled */
+/***********************************************************************/
+void ZIPUTIL::getTime(tm_zip& tmZip)
+{
+ time_t rawtime;
+ time(&rawtime);
+ struct tm *timeinfo = localtime(&rawtime);
+ tmZip.tm_sec = timeinfo->tm_sec;
+ tmZip.tm_min = timeinfo->tm_min;
+ tmZip.tm_hour = timeinfo->tm_hour;
+ tmZip.tm_mday = timeinfo->tm_mday;
+ tmZip.tm_mon = timeinfo->tm_mon;
+ tmZip.tm_year = timeinfo->tm_year;
+} // end of getTime
+
+/***********************************************************************/
+/* open a zip file for deflate. */
+/* param: filename path and the filename of the zip file to open. */
+/* append: set true to append the zip file */
+/* return: true if open, false otherwise. */
+/***********************************************************************/
+bool ZIPUTIL::open(PGLOBAL g, char *filename, bool append)
+{
+ if (!zipfile && !(zipfile = zipOpen64(filename,
+ append ? APPEND_STATUS_ADDINZIP
+ : APPEND_STATUS_CREATE)))
+ sprintf(g->Message, "Zipfile open error on %s", filename);
+
+ return (zipfile == NULL);
+} // end of open
+
+/***********************************************************************/
+/* Close the zip file. */
+/***********************************************************************/
+void ZIPUTIL::close()
+{
+ if (zipfile) {
+ closeEntry();
+ zipClose(zipfile, 0);
+ zipfile = NULL;
+ } // endif zipfile
+
+} // end of close
+
+/***********************************************************************/
+/* OpenTableFile: Open a DOS/UNIX table file from a ZIP file. */
+/***********************************************************************/
+bool ZIPUTIL::OpenTable(PGLOBAL g, MODE mode, char *fn, bool append)
+{
+ /*********************************************************************/
+ /* The file will be compressed. */
+ /*********************************************************************/
+ if (mode == MODE_INSERT) {
+ bool b = open(g, fn, append);
+
+ if (!b) {
+ if (addEntry(g, target))
+ return true;
+
+ /*****************************************************************/
+ /* Link a Fblock. This make possible to automatically close it */
+ /* in case of error g->jump. */
+ /*****************************************************************/
+ PDBUSER dbuserp = (PDBUSER)g->Activityp->Aptr;
+
+ fp = (PFBLOCK)PlugSubAlloc(g, NULL, sizeof(FBLOCK));
+ fp->Type = TYPE_FB_ZIP;
+ fp->Fname = PlugDup(g, fn);
+ fp->Next = dbuserp->Openlist;
+ dbuserp->Openlist = fp;
+ fp->Count = 1;
+ fp->Length = 0;
+ fp->Memory = NULL;
+ fp->Mode = mode;
+ fp->File = this;
+ fp->Handle = 0;
+ } else
+ return true;
+
+ } else {
+ strcpy(g->Message, "Only INSERT mode supported for ZIPPING files");
+ return true;
+ } // endif mode
+
+ return false;
+} // end of OpenTableFile
+
+/***********************************************************************/
+/* Add target in zip file. */
+/***********************************************************************/
+bool ZIPUTIL::addEntry(PGLOBAL g, char *entry)
+{
+ //?? we dont need the stinking time
+ zip_fileinfo zi = { 0, 0, 0, 0, 0, 0, 0, 0, 0 };
+
+ getTime(zi.tmz_date);
+ target = entry;
+
+ int err = zipOpenNewFileInZip(zipfile, target, &zi,
+ NULL, 0, NULL, 0, NULL, Z_DEFLATED, Z_DEFAULT_COMPRESSION);
+
+ return !(entryopen = (err == ZIP_OK));
+} // end of addEntry
+
+/***********************************************************************/
+/* writeEntry: Deflate the buffer to the zip file. */
+/***********************************************************************/
+int ZIPUTIL::writeEntry(PGLOBAL g, char *buf, int len)
+{
+ if (zipWriteInFileInZip(zipfile, buf, len) < 0) {
+ sprintf(g->Message, "Error writing %s in the zipfile", target);
+ return RC_FX;
+ } // endif zipWriteInFileInZip
+
+ return RC_OK;
+} // end of writeEntry
+
+/***********************************************************************/
+/* Close the zip file. */
+/***********************************************************************/
+void ZIPUTIL::closeEntry()
+{
+ if (entryopen) {
+ zipCloseFileInZip(zipfile);
+ entryopen = false;
+ } // endif entryopen
+
+} // end of closeEntry
+
+/* ------------------------- class UNZIPUTL -------------------------- */
+
+/***********************************************************************/
+/* Constructors. */
+/***********************************************************************/
+UNZIPUTL::UNZIPUTL(PSZ tgt, bool mul)
{
zipfile = NULL;
target = tgt;
@@ -62,10 +399,10 @@ ZIPUTIL::ZIPUTIL(PSZ tgt, bool mul)
#else
for (int i = 0; i < 256; ++i) mapCaseTable[i] = i;
#endif
-} // end of ZIPUTIL standard constructor
+} // end of UNZIPUTL standard constructor
#if 0
-ZIPUTIL::ZIPUTIL(PZIPUTIL zutp)
+UNZIPUTL::UNZIPUTL(PZIPUTIL zutp)
{
zipfile = zutp->zipfile;
target = zutp->target;
@@ -74,14 +411,14 @@ ZIPUTIL::ZIPUTIL(PZIPUTIL zutp)
entryopen = zutp->entryopen;
multiple = zutp->multiple;
for (int i = 0; i < 256; ++i) mapCaseTable[i] = zutp->mapCaseTable[i];
-} // end of ZIPUTIL copy constructor
+} // end of UNZIPUTL copy constructor
#endif // 0
/***********************************************************************/
/* This code is the copyright property of Alessandro Felice Cantatore. */
/* http://xoomer.virgilio.it/acantato/dev/wildcard/wildmatch.html */
/***********************************************************************/
-bool ZIPUTIL::WildMatch(PSZ pat, PSZ str) {
+bool UNZIPUTL::WildMatch(PSZ pat, PSZ str) {
PSZ s, p;
bool star = FALSE;
@@ -116,7 +453,7 @@ starCheck:
/* param: filename path and the filename of the zip file to open. */
/* return: true if open, false otherwise. */
/***********************************************************************/
-bool ZIPUTIL::open(PGLOBAL g, char *filename)
+bool UNZIPUTL::open(PGLOBAL g, char *filename)
{
if (!zipfile && !(zipfile = unzOpen64(filename)))
sprintf(g->Message, "Zipfile open error on %s", filename);
@@ -127,7 +464,7 @@ bool ZIPUTIL::open(PGLOBAL g, char *filename)
/***********************************************************************/
/* Close the zip file. */
/***********************************************************************/
-void ZIPUTIL::close()
+void UNZIPUTL::close()
{
if (zipfile) {
closeEntry();
@@ -140,7 +477,7 @@ void ZIPUTIL::close()
/***********************************************************************/
/* Find next entry matching target pattern. */
/***********************************************************************/
-int ZIPUTIL::findEntry(PGLOBAL g, bool next)
+int UNZIPUTL::findEntry(PGLOBAL g, bool next)
{
int rc;
@@ -183,7 +520,7 @@ int ZIPUTIL::findEntry(PGLOBAL g, bool next)
/***********************************************************************/
/* Get the next used entry. */
/***********************************************************************/
-int ZIPUTIL::nextEntry(PGLOBAL g)
+int UNZIPUTL::nextEntry(PGLOBAL g)
{
if (multiple) {
int rc;
@@ -206,7 +543,7 @@ int ZIPUTIL::nextEntry(PGLOBAL g)
/***********************************************************************/
/* OpenTableFile: Open a DOS/UNIX table file from a ZIP file. */
/***********************************************************************/
-bool ZIPUTIL::OpenTable(PGLOBAL g, MODE mode, char *fn)
+bool UNZIPUTL::OpenTable(PGLOBAL g, MODE mode, char *fn)
{
/*********************************************************************/
/* The file will be decompressed into virtual memory. */
@@ -268,7 +605,7 @@ bool ZIPUTIL::OpenTable(PGLOBAL g, MODE mode, char *fn)
return true;
} else {
- strcpy(g->Message, "Only READ mode supported for ZIP files");
+ strcpy(g->Message, "Only READ mode supported for ZIPPED tables");
return true;
} // endif mode
@@ -278,7 +615,7 @@ bool ZIPUTIL::OpenTable(PGLOBAL g, MODE mode, char *fn)
/***********************************************************************/
/* Open target in zip file. */
/***********************************************************************/
-bool ZIPUTIL::openEntry(PGLOBAL g)
+bool UNZIPUTL::openEntry(PGLOBAL g)
{
int rc;
@@ -316,7 +653,7 @@ bool ZIPUTIL::openEntry(PGLOBAL g)
/***********************************************************************/
/* Close the zip file. */
/***********************************************************************/
-void ZIPUTIL::closeEntry()
+void UNZIPUTL::closeEntry()
{
if (entryopen) {
unzCloseCurrentFile(zipfile);
@@ -330,36 +667,29 @@ void ZIPUTIL::closeEntry()
} // end of closeEntry
-/* -------------------------- class ZIPFAM --------------------------- */
+/* -------------------------- class UNZFAM --------------------------- */
/***********************************************************************/
/* Constructors. */
/***********************************************************************/
-ZIPFAM::ZIPFAM(PDOSDEF tdp) : MAPFAM(tdp)
+UNZFAM::UNZFAM(PDOSDEF tdp) : MAPFAM(tdp)
{
zutp = NULL;
target = tdp->GetEntry();
mul = tdp->GetMul();
-} // end of ZIPFAM standard constructor
-
-ZIPFAM::ZIPFAM(PZIPFAM txfp) : MAPFAM(txfp)
-{
- zutp = txfp->zutp;
- target = txfp->target;
- mul = txfp->mul;
-} // end of ZIPFAM copy constructor
+} // end of UNZFAM standard constructor
-ZIPFAM::ZIPFAM(PDOSDEF tdp, PZPXFAM txfp) : MAPFAM(tdp)
+UNZFAM::UNZFAM(PUNZFAM txfp) : MAPFAM(txfp)
{
zutp = txfp->zutp;
target = txfp->target;
mul = txfp->mul;
-} // end of ZIPFAM constructor used in ResetTableOpt
+} // end of UNZFAM copy constructor
/***********************************************************************/
/* ZIP GetFileLength: returns file size in number of bytes. */
/***********************************************************************/
-int ZIPFAM::GetFileLength(PGLOBAL g)
+int UNZFAM::GetFileLength(PGLOBAL g)
{
int len = (zutp && zutp->entryopen) ? Top - Memory
: TXTFAM::GetFileLength(g) * 3;
@@ -373,7 +703,7 @@ int ZIPFAM::GetFileLength(PGLOBAL g)
/***********************************************************************/
/* ZIP Cardinality: return the number of rows if possible. */
/***********************************************************************/
-int ZIPFAM::Cardinality(PGLOBAL g)
+int UNZFAM::Cardinality(PGLOBAL g)
{
if (!g)
return 1;
@@ -388,7 +718,7 @@ int ZIPFAM::Cardinality(PGLOBAL g)
/***********************************************************************/
/* OpenTableFile: Open a DOS/UNIX table file from a ZIP file. */
/***********************************************************************/
-bool ZIPFAM::OpenTableFile(PGLOBAL g)
+bool UNZFAM::OpenTableFile(PGLOBAL g)
{
char filename[_MAX_PATH];
MODE mode = Tdbp->GetMode();
@@ -396,7 +726,7 @@ bool ZIPFAM::OpenTableFile(PGLOBAL g)
/*********************************************************************/
/* Allocate the ZIP utility class. */
/*********************************************************************/
- zutp = new(g) ZIPUTIL(target, mul);
+ zutp = new(g) UNZIPUTL(target, mul);
// We used the file name relative to recorded datapath
PlugSetPath(filename, To_File, Tdbp->GetPath());
@@ -415,7 +745,7 @@ bool ZIPFAM::OpenTableFile(PGLOBAL g)
/***********************************************************************/
/* GetNext: go to next entry. */
/***********************************************************************/
-int ZIPFAM::GetNext(PGLOBAL g)
+int UNZFAM::GetNext(PGLOBAL g)
{
int rc = zutp->nextEntry(g);
@@ -431,7 +761,7 @@ int ZIPFAM::GetNext(PGLOBAL g)
/***********************************************************************/
/* ReadBuffer: Read one line for a ZIP file. */
/***********************************************************************/
-int ZIPFAM::ReadBuffer(PGLOBAL g)
+int UNZFAM::ReadBuffer(PGLOBAL g)
{
int rc, len;
@@ -497,37 +827,37 @@ int ZIPFAM::ReadBuffer(PGLOBAL g)
/***********************************************************************/
/* Table file close routine for MAP access method. */
/***********************************************************************/
-void ZIPFAM::CloseTableFile(PGLOBAL g, bool)
+void UNZFAM::CloseTableFile(PGLOBAL g, bool)
{
close();
} // end of CloseTableFile
#endif // 0
-/* -------------------------- class ZPXFAM --------------------------- */
+/* -------------------------- class UZXFAM --------------------------- */
/***********************************************************************/
/* Constructors. */
/***********************************************************************/
-ZPXFAM::ZPXFAM(PDOSDEF tdp) : MPXFAM(tdp)
+UZXFAM::UZXFAM(PDOSDEF tdp) : MPXFAM(tdp)
{
zutp = NULL;
target = tdp->GetEntry();
mul = tdp->GetMul();
//Lrecl = tdp->GetLrecl();
-} // end of ZPXFAM standard constructor
+} // end of UZXFAM standard constructor
-ZPXFAM::ZPXFAM(PZPXFAM txfp) : MPXFAM(txfp)
+UZXFAM::UZXFAM(PUZXFAM txfp) : MPXFAM(txfp)
{
zutp = txfp->zutp;
target = txfp->target;
mul = txfp->mul;
//Lrecl = txfp->Lrecl;
-} // end of ZPXFAM copy constructor
+} // end of UZXFAM copy constructor
/***********************************************************************/
/* ZIP GetFileLength: returns file size in number of bytes. */
/***********************************************************************/
-int ZPXFAM::GetFileLength(PGLOBAL g)
+int UZXFAM::GetFileLength(PGLOBAL g)
{
int len;
@@ -545,7 +875,7 @@ int ZPXFAM::GetFileLength(PGLOBAL g)
/***********************************************************************/
/* ZIP Cardinality: return the number of rows if possible. */
/***********************************************************************/
-int ZPXFAM::Cardinality(PGLOBAL g)
+int UZXFAM::Cardinality(PGLOBAL g)
{
if (!g)
return 1;
@@ -566,7 +896,7 @@ int ZPXFAM::Cardinality(PGLOBAL g)
/***********************************************************************/
/* OpenTableFile: Open a DOS/UNIX table file from a ZIP file. */
/***********************************************************************/
-bool ZPXFAM::OpenTableFile(PGLOBAL g)
+bool UZXFAM::OpenTableFile(PGLOBAL g)
{
// May have been already opened in GetFileLength
if (!zutp || !zutp->zipfile) {
@@ -577,7 +907,7 @@ bool ZPXFAM::OpenTableFile(PGLOBAL g)
/* Allocate the ZIP utility class. */
/*********************************************************************/
if (!zutp)
- zutp = new(g)ZIPUTIL(target, mul);
+ zutp = new(g)UNZIPUTL(target, mul);
// We used the file name relative to recorded datapath
PlugSetPath(filename, To_File, Tdbp->GetPath());
@@ -600,7 +930,7 @@ bool ZPXFAM::OpenTableFile(PGLOBAL g)
/***********************************************************************/
/* GetNext: go to next entry. */
/***********************************************************************/
-int ZPXFAM::GetNext(PGLOBAL g)
+int UZXFAM::GetNext(PGLOBAL g)
{
int rc = zutp->nextEntry(g);
@@ -620,3 +950,146 @@ int ZPXFAM::GetNext(PGLOBAL g)
return RC_OK;
} // end of GetNext
+/* -------------------------- class ZIPFAM --------------------------- */
+
+/***********************************************************************/
+/* Constructor. */
+/***********************************************************************/
+ZIPFAM::ZIPFAM(PDOSDEF tdp) : DOSFAM(tdp)
+{
+ zutp = NULL;
+ target = tdp->GetEntry();
+ append = tdp->GetAppend();
+} // end of ZIPFAM standard constructor
+
+/***********************************************************************/
+/* OpenTableFile: Open a DOS/UNIX table file from a ZIP file. */
+/***********************************************************************/
+bool ZIPFAM::OpenTableFile(PGLOBAL g)
+{
+ char filename[_MAX_PATH];
+ MODE mode = Tdbp->GetMode();
+
+ /*********************************************************************/
+ /* Allocate the ZIP utility class. */
+ /*********************************************************************/
+ zutp = new(g) ZIPUTIL(target);
+
+ // We used the file name relative to recorded datapath
+ PlugSetPath(filename, To_File, Tdbp->GetPath());
+
+ if (!zutp->OpenTable(g, mode, filename, append)) {
+ To_Fb = zutp->fp; // Useful when closing
+ } else
+ return true;
+
+ return AllocateBuffer(g);
+} // end of OpenTableFile
+
+/***********************************************************************/
+/* ReadBuffer: Read one line for a ZIP file. */
+/***********************************************************************/
+int ZIPFAM::ReadBuffer(PGLOBAL g)
+{
+ strcpy(g->Message, "ReadBuffer should not been called when zipping");
+ return RC_FX;
+} // end of ReadBuffer
+
+/***********************************************************************/
+/* WriteBuffer: Deflate the buffer to the zip file. */
+/***********************************************************************/
+int ZIPFAM::WriteBuffer(PGLOBAL g)
+{
+ int len;
+
+ // Prepare to write the new line
+ strcat(strcpy(To_Buf, Tdbp->GetLine()), (Bin) ? CrLf : "\n");
+ len = strchr(To_Buf, '\n') - To_Buf + 1;
+ return zutp->writeEntry(g, To_Buf, len);
+} // end of WriteBuffer
+
+/***********************************************************************/
+/* Table file close routine for ZIP access method. */
+/***********************************************************************/
+void ZIPFAM::CloseTableFile(PGLOBAL g, bool)
+{
+ To_Fb->Count = 0;
+ zutp->close();
+} // end of CloseTableFile
+
+/* -------------------------- class ZPXFAM --------------------------- */
+
+/***********************************************************************/
+/* Constructor. */
+/***********************************************************************/
+ZPXFAM::ZPXFAM(PDOSDEF tdp) : FIXFAM(tdp)
+{
+ zutp = NULL;
+ target = tdp->GetEntry();
+ append = tdp->GetAppend();
+ //Lrecl = tdp->GetLrecl();
+} // end of UZXFAM standard constructor
+
+/***********************************************************************/
+/* OpenTableFile: Open a DOS/UNIX table file from a ZIP file. */
+/***********************************************************************/
+bool ZPXFAM::OpenTableFile(PGLOBAL g)
+{
+ char filename[_MAX_PATH];
+ MODE mode = Tdbp->GetMode();
+
+ /*********************************************************************/
+ /* Allocate the ZIP utility class. */
+ /*********************************************************************/
+ zutp = new(g) ZIPUTIL(target);
+
+ // We used the file name relative to recorded datapath
+ PlugSetPath(filename, To_File, Tdbp->GetPath());
+
+ if (!zutp->OpenTable(g, mode, filename, append)) {
+ To_Fb = zutp->fp; // Useful when closing
+ } else
+ return true;
+
+ return AllocateBuffer(g);
+} // end of OpenTableFile
+
+/***********************************************************************/
+/* WriteBuffer: Deflate the buffer to the zip file. */
+/***********************************************************************/
+int ZPXFAM::WriteBuffer(PGLOBAL g)
+{
+ /*********************************************************************/
+ /* In Insert mode, we write only full blocks. */
+ /*********************************************************************/
+ if (++CurNum != Rbuf) {
+ Tdbp->IncLine(Lrecl); // Used by DOSCOL functions
+ return RC_OK;
+ } // endif CurNum
+
+ // Now start the compress process.
+ if (zutp->writeEntry(g, To_Buf, Lrecl * Rbuf) != RC_OK) {
+ Closing = true;
+ return RC_FX;
+ } // endif writeEntry
+
+ CurBlk++;
+ CurNum = 0;
+ Tdbp->SetLine(To_Buf);
+ return RC_OK;
+} // end of WriteBuffer
+
+/***********************************************************************/
+/* Table file close routine for ZIP access method. */
+/***********************************************************************/
+void ZPXFAM::CloseTableFile(PGLOBAL g, bool)
+{
+ if (CurNum && !Closing) {
+ // Some more inserted lines remain to be written
+ Rbuf = CurNum--;
+ WriteBuffer(g);
+ } // endif Curnum
+
+ To_Fb->Count = 0;
+ zutp->close();
+} // end of CloseTableFile
diff --git a/storage/connect/filamzip.h b/storage/connect/filamzip.h
index 9312fb2f70e..3160703bd20 100644
--- a/storage/connect/filamzip.h
+++ b/storage/connect/filamzip.h
@@ -1,7 +1,7 @@
/************** filamzip H Declares Source Code File (.H) **************/
-/* Name: filamzip.h Version 1.0 */
+/* Name: filamzip.h Version 1.1 */
/* */
-/* (C) Copyright to the author Olivier BERTRAND 2016 */
+/* (C) Copyright to the author Olivier BERTRAND 2016-2017 */
/* */
/* This file contains the ZIP file access method classes declares. */
/***********************************************************************/
@@ -10,10 +10,14 @@
#include "block.h"
#include "filamap.h"
+#include "filamfix.h"
+#include "zip.h"
#include "unzip.h"
#define DLLEXPORT extern "C"
+typedef class UNZFAM *PUNZFAM;
+typedef class UZXFAM *PUZXFAM;
typedef class ZIPFAM *PZIPFAM;
typedef class ZPXFAM *PZPXFAM;
@@ -21,16 +25,50 @@ typedef class ZPXFAM *PZPXFAM;
/* This is the ZIP utility fonctions class. */
/***********************************************************************/
class DllExport ZIPUTIL : public BLOCK {
-public:
+ public:
// Constructor
- ZIPUTIL(PSZ tgt, bool mul);
-//ZIPUTIL(ZIPUTIL *zutp);
+ ZIPUTIL(PSZ tgt);
+ //ZIPUTIL(ZIPUTIL *zutp);
// Implementation
-//PTXF Duplicate(PGLOBAL g) { return (PTXF) new(g)ZIPFAM(this); }
+ //PTXF Duplicate(PGLOBAL g) { return (PTXF) new(g)UNZFAM(this); }
// Methods
- virtual bool OpenTable(PGLOBAL g, MODE mode, char *fn);
+ bool OpenTable(PGLOBAL g, MODE mode, char *fn, bool append);
+ bool open(PGLOBAL g, char *fn, bool append);
+ bool addEntry(PGLOBAL g, char *entry);
+ void close(void);
+ void closeEntry(void);
+ int writeEntry(PGLOBAL g, char *buf, int len);
+ void getTime(tm_zip& tmZip);
+
+ // Members
+ zipFile zipfile; // The ZIP container file
+ PSZ target; // The target file name
+//unz_file_info finfo; // The current file info
+ PFBLOCK fp;
+//char *memory;
+//uint size;
+//int multiple; // Multiple targets
+ bool entryopen; // True when open current entry
+//char fn[FILENAME_MAX]; // The current entry file name
+//char mapCaseTable[256];
+}; // end of ZIPUTIL
+
+/***********************************************************************/
+/* This is the unZIP utility fonctions class. */
+/***********************************************************************/
+class DllExport UNZIPUTL : public BLOCK {
+ public:
+ // Constructor
+ UNZIPUTL(PSZ tgt, bool mul);
+//UNZIPUTL(UNZIPUTL *zutp);
+
+ // Implementation
+//PTXF Duplicate(PGLOBAL g) { return (PTXF) new(g)UNZFAM(this); }
+
+ // Methods
+ bool OpenTable(PGLOBAL g, MODE mode, char *fn);
bool open(PGLOBAL g, char *fn);
bool openEntry(PGLOBAL g);
void close(void);
@@ -50,68 +88,120 @@ public:
bool entryopen; // True when open current entry
char fn[FILENAME_MAX]; // The current entry file name
char mapCaseTable[256];
-}; // end of ZIPFAM
+}; // end of UNZIPUTL
/***********************************************************************/
-/* This is the ZIP file access method. */
+/* This is the unzip file access method. */
/***********************************************************************/
-class DllExport ZIPFAM : public MAPFAM {
- friend class ZPXFAM;
-public:
+class DllExport UNZFAM : public MAPFAM {
+//friend class UZXFAM;
+ public:
// Constructors
- ZIPFAM(PDOSDEF tdp);
- ZIPFAM(PZIPFAM txfp);
- ZIPFAM(PDOSDEF tdp, PZPXFAM txfp);
+ UNZFAM(PDOSDEF tdp);
+ UNZFAM(PUNZFAM txfp);
// Implementation
- virtual AMT GetAmType(void) { return TYPE_AM_ZIP; }
- virtual PTXF Duplicate(PGLOBAL g) { return (PTXF) new(g)ZIPFAM(this); }
+ virtual AMT GetAmType(void) {return TYPE_AM_ZIP;}
+ virtual PTXF Duplicate(PGLOBAL g) {return (PTXF) new(g) UNZFAM(this);}
// Methods
virtual int Cardinality(PGLOBAL g);
virtual int GetFileLength(PGLOBAL g);
-//virtual int MaxBlkSize(PGLOBAL g, int s) {return s;}
+ //virtual int MaxBlkSize(PGLOBAL g, int s) {return s;}
virtual bool OpenTableFile(PGLOBAL g);
virtual bool DeferReading(void) { return false; }
virtual int GetNext(PGLOBAL g);
-//virtual int ReadBuffer(PGLOBAL g);
-//virtual int WriteBuffer(PGLOBAL g);
-//virtual int DeleteRecords(PGLOBAL g, int irc);
-//virtual void CloseTableFile(PGLOBAL g, bool abort);
+ //virtual int ReadBuffer(PGLOBAL g);
+ //virtual int WriteBuffer(PGLOBAL g);
+ //virtual int DeleteRecords(PGLOBAL g, int irc);
+ //virtual void CloseTableFile(PGLOBAL g, bool abort);
-protected:
+ protected:
// Members
- ZIPUTIL *zutp;
- PSZ target;
- bool mul;
-}; // end of ZIPFAM
+ UNZIPUTL *zutp;
+ PSZ target;
+ bool mul;
+}; // end of UNZFAM
/***********************************************************************/
-/* This is the fixed ZIP file access method. */
+/* This is the fixed unzip file access method. */
/***********************************************************************/
-class DllExport ZPXFAM : public MPXFAM {
- friend class ZIPFAM;
-public:
+class DllExport UZXFAM : public MPXFAM {
+//friend class UNZFAM;
+ public:
// Constructors
- ZPXFAM(PDOSDEF tdp);
- ZPXFAM(PZPXFAM txfp);
+ UZXFAM(PDOSDEF tdp);
+ UZXFAM(PUZXFAM txfp);
// Implementation
virtual AMT GetAmType(void) { return TYPE_AM_ZIP; }
- virtual PTXF Duplicate(PGLOBAL g) { return (PTXF) new(g)ZPXFAM(this); }
+ virtual PTXF Duplicate(PGLOBAL g) { return (PTXF) new(g)UZXFAM(this); }
// Methods
virtual int GetFileLength(PGLOBAL g);
virtual int Cardinality(PGLOBAL g);
virtual bool OpenTableFile(PGLOBAL g);
virtual int GetNext(PGLOBAL g);
-//virtual int ReadBuffer(PGLOBAL g);
+ //virtual int ReadBuffer(PGLOBAL g);
+
+ protected:
+ // Members
+ UNZIPUTL *zutp;
+ PSZ target;
+ bool mul;
+}; // end of UZXFAM
+
+/***********************************************************************/
+/* This is the zip file access method. */
+/***********************************************************************/
+class DllExport ZIPFAM : public DOSFAM {
+ public:
+ // Constructors
+ ZIPFAM(PDOSDEF tdp);
+
+ // Implementation
+ virtual AMT GetAmType(void) {return TYPE_AM_ZIP;}
+
+ // Methods
+ virtual int Cardinality(PGLOBAL g) {return 0;}
+ virtual int GetFileLength(PGLOBAL g) {return g ? 0 : 1;}
+ //virtual int MaxBlkSize(PGLOBAL g, int s) {return s;}
+ virtual bool OpenTableFile(PGLOBAL g);
+ virtual int ReadBuffer(PGLOBAL g);
+ virtual int WriteBuffer(PGLOBAL g);
+ //virtual int DeleteRecords(PGLOBAL g, int irc);
+ virtual void CloseTableFile(PGLOBAL g, bool abort);
+
+ protected:
+ // Members
+ ZIPUTIL *zutp;
+ PSZ target;
+ bool append;
+}; // end of ZIPFAM
+
+/***********************************************************************/
+/* This is the fixed zip file access method. */
+/***********************************************************************/
+class DllExport ZPXFAM : public FIXFAM {
+ public:
+ // Constructors
+ ZPXFAM(PDOSDEF tdp);
+
+ // Implementation
+ virtual AMT GetAmType(void) {return TYPE_AM_ZIP;}
+
+ // Methods
+ virtual int Cardinality(PGLOBAL g) {return 0;}
+ virtual int GetFileLength(PGLOBAL g) {return g ? 0 : 1;}
+ virtual bool OpenTableFile(PGLOBAL g);
+ virtual int WriteBuffer(PGLOBAL g);
+ virtual void CloseTableFile(PGLOBAL g, bool abort);
-protected:
+ protected:
// Members
ZIPUTIL *zutp;
PSZ target;
- bool mul;
+ bool append;
}; // end of ZPXFAM
#endif // __FILAMZIP_H
diff --git a/storage/connect/ha_connect.cc b/storage/connect/ha_connect.cc
index b542ca180c5..f2727ba15f7 100644
--- a/storage/connect/ha_connect.cc
+++ b/storage/connect/ha_connect.cc
@@ -1,4 +1,4 @@
-/* Copyright (C) Olivier Bertrand 2004 - 2016
+/* Copyright (C) Olivier Bertrand 2004 - 2017
This program is free software; you can redistribute it and/or modify
it under the terms of the GNU General Public License as published by
@@ -11,7 +11,7 @@
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 */
+ Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02111-1301 USA */
/**
@file ha_connect.cc
@@ -125,6 +125,8 @@
#endif // UNIX
#include "global.h"
#include "plgdbsem.h"
+#include "xtable.h"
+#include "tabext.h"
#if defined(ODBC_SUPPORT)
#include "odbccat.h"
#endif // ODBC_SUPPORT
@@ -132,12 +134,11 @@
#include "tabjdbc.h"
#include "jdbconn.h"
#endif // JDBC_SUPPORT
-#include "xtable.h"
#include "tabmysql.h"
#include "filamdbf.h"
#include "tabxcl.h"
#include "tabfmt.h"
-#include "reldef.h"
+//#include "reldef.h"
#include "tabcol.h"
#include "xindex.h"
#if defined(__WIN__)
@@ -171,9 +172,9 @@
#define JSONMAX 10 // JSON Default max grp size
extern "C" {
- char version[]= "Version 1.05.0001 December 13, 2016";
+ char version[]= "Version 1.05.0003 February 27, 2017";
#if defined(__WIN__)
- char compver[]= "Version 1.05.0001 " __DATE__ " " __TIME__;
+ char compver[]= "Version 1.05.0003 " __DATE__ " " __TIME__;
char slash= '\\';
#else // !__WIN__
char slash= '/';
@@ -214,6 +215,7 @@ int TranslateJDBCType(int stp, char *tn, int prec, int& len, char& v);
void PushWarning(PGLOBAL g, THD *thd, int level);
bool CheckSelf(PGLOBAL g, TABLE_SHARE *s, const char *host,
const char *db, char *tab, const char *src, int port);
+bool ZipLoadFile(PGLOBAL, char*, char*, char*, bool, bool);
bool ExactInfo(void);
USETEMP UseTemp(void);
int GetConvSize(void);
@@ -556,7 +558,7 @@ ha_create_table_option connect_index_option_list[]=
/***********************************************************************/
/* Push G->Message as a MySQL warning. */
/***********************************************************************/
-bool PushWarning(PGLOBAL g, PTDBASE tdbp, int level)
+bool PushWarning(PGLOBAL g, PTDB tdbp, int level)
{
PHC phc;
THD *thd;
@@ -1024,7 +1026,7 @@ char *GetListOption(PGLOBAL g, const char *opname,
char key[16], val[256];
char *pk, *pv, *pn;
- char *opval= (char*) def;
+ char *opval= (char*)def;
int n;
for (pk= (char*)oplist; pk; pk= ++pn) {
@@ -1032,26 +1034,17 @@ char *GetListOption(PGLOBAL g, const char *opname,
pv= strchr(pk, '=');
if (pv && (!pn || pv < pn)) {
- n= pv - pk;
+ n= MY_MIN(static_cast<size_t>(pv - pk), sizeof(key) - 1);
memcpy(key, pk, n);
key[n]= 0;
pv++;
-
- if (pn) {
- n= pn - pv;
- memcpy(val, pv, n);
- val[n]= 0;
- } else
- strcpy(val, pv);
-
+ n= MY_MIN((pn ? pn - pv : strlen(pv)), sizeof(val) - 1);
+ memcpy(val, pv, n);
+ val[n]= 0;
} else {
- if (pn) {
- n= MY_MIN(pn - pk, 15);
- memcpy(key, pk, n);
- key[n]= 0;
- } else
- strcpy(key, pk);
-
+ n= MY_MIN((pn ? pn - pk : strlen(pk)), sizeof(key) - 1);
+ memcpy(key, pk, n);
+ key[n]= 0;
val[0]= 0;
} // endif pv
@@ -1105,7 +1098,7 @@ char *GetStringTableOption(PGLOBAL g, PTOS options, char *opname, char *sdef)
else if (!stricmp(opname, "Data_charset"))
opval= options->data_charset;
- if (!opval && options && options->oplist)
+ if (!opval && options->oplist)
opval= GetListOption(g, opname, options->oplist);
return opval ? (char*)opval : sdef;
@@ -2113,7 +2106,7 @@ int ha_connect::ScanRecord(PGLOBAL g, uchar *)
PCOL colp;
PVAL value, sdvalin;
Field *fp;
- PTDBASE tp= (PTDBASE)tdbp;
+//PTDBASE tp= (PTDBASE)tdbp;
String attribute(attr_buffer, sizeof(attr_buffer),
table->s->table_charset);
my_bitmap_map *bmap= dbug_tmp_use_all_columns(table, table->read_set);
@@ -2131,7 +2124,7 @@ int ha_connect::ScanRecord(PGLOBAL g, uchar *)
&& tdbp->GetAmType() != TYPE_AM_ODBC
&& tdbp->GetAmType() != TYPE_AM_JDBC) ||
bitmap_is_set(table->write_set, fp->field_index)) {
- for (colp= tp->GetSetCols(); colp; colp= colp->GetNext())
+ for (colp= tdbp->GetSetCols(); colp; colp= colp->GetNext())
if (!stricmp(colp->GetName(), fp->field_name))
break;
@@ -2218,7 +2211,7 @@ int ha_connect::ScanRecord(PGLOBAL g, uchar *)
} else if (xmod == MODE_UPDATE) {
PCOL cp;
- for (cp= tp->GetColumns(); cp; cp= cp->GetNext())
+ for (cp= tdbp->GetColumns(); cp; cp= cp->GetNext())
if (!stricmp(colp->GetName(), cp->GetName()))
break;
@@ -2685,7 +2678,8 @@ PCFIL ha_connect::CheckCond(PGLOBAL g, PCFIL filp, const Item *cond)
{
AMT tty = filp->Type;
char *body= filp->Body;
- unsigned int i;
+ char *havg= filp->Having;
+ unsigned int i;
bool ismul= false, x= (tty == TYPE_AM_MYX || tty == TYPE_AM_XDBC);
bool nonul= ((tty == TYPE_AM_ODBC || tty == TYPE_AM_JDBC) &&
(tdbp->GetMode() == MODE_INSERT || tdbp->GetMode() == MODE_DELETE));
@@ -2698,7 +2692,8 @@ PCFIL ha_connect::CheckCond(PGLOBAL g, PCFIL filp, const Item *cond)
htrc("Cond type=%d\n", cond->type());
if (cond->type() == COND::COND_ITEM) {
- char *p1, *p2;
+ char *pb0, *pb1, *pb2, *ph0, *ph1, *ph2;
+ bool bb = false, bh = false;
Item_cond *cond_item= (Item_cond *)cond;
if (x)
@@ -2718,38 +2713,78 @@ PCFIL ha_connect::CheckCond(PGLOBAL g, PCFIL filp, const Item *cond)
List_iterator<Item> li(*arglist);
const Item *subitem;
- p1= body + strlen(body);
- strcpy(p1, "(");
- p2= p1 + 1;
+ pb0= pb1= body + strlen(body);
+ strcpy(pb0, "(");
+ pb2= pb1 + 1;
+
+ if (havg) {
+ ph0= ph1= havg + strlen(havg);
+ strcpy(ph0, "(");
+ ph2= ph1 + 1;
+ } // endif havg
for (i= 0; i < arglist->elements; i++)
if ((subitem= li++)) {
if (!CheckCond(g, filp, subitem)) {
if (vop == OP_OR || nonul)
return NULL;
- else
- *p2= 0;
+ else {
+ *pb2= 0;
+ if (havg) *ph2= 0;
+ } // endelse
} else {
- p1= p2 + strlen(p2);
- strcpy(p1, GetValStr(vop, false));
- p2= p1 + strlen(p1);
+ if (filp->Bd) {
+ pb1= pb2 + strlen(pb2);
+ strcpy(pb1, GetValStr(vop, false));
+ pb2= pb1 + strlen(pb1);
+ } // endif Bd
+
+ if (filp->Hv) {
+ ph1= ph2 + strlen(ph2);
+ strcpy(ph1, GetValStr(vop, false));
+ ph2= ph1 + strlen(ph1);
+ } // endif Hv
+
} // endif CheckCond
+ bb |= filp->Bd;
+ bh |= filp->Hv;
+ filp->Bd = filp->Hv = false;
} else
return NULL;
- if (*p1 != '(')
- strcpy(p1, ")");
- else
- return NULL;
+ if (bb) {
+ strcpy(pb1, ")");
+ filp->Bd = bb;
+ } else
+ *pb0= 0;
+
+ if (havg) {
+ if (bb && bh && vop == OP_OR) {
+ // Cannot or'ed a where clause with a having clause
+ bb= bh= 0;
+ *pb0 = 0;
+ *ph0 = 0;
+ } else if (bh) {
+ strcpy(ph1, ")");
+ filp->Hv= bh;
+ } else
+ *ph0 = 0;
+
+ } // endif havg
+
+ if (!bb && !bh)
+ return NULL;
} else if (cond->type() == COND::FUNC_ITEM) {
unsigned int i;
- bool iscol, neg= FALSE;
+ bool iscol, ishav= false, neg= false;
Item_func *condf= (Item_func *)cond;
Item* *args= condf->arguments();
+ filp->Bd = filp->Hv = false;
+
if (trace)
htrc("Func type=%d argnum=%d\n", condf->functype(),
condf->argument_count());
@@ -2798,8 +2833,9 @@ PCFIL ha_connect::CheckCond(PGLOBAL g, PCFIL filp, const Item *cond)
ha_field_option_struct *fop;
Item_field *pField= (Item_field *)args[i];
- if (x && i)
- return NULL;
+ // IN and BETWEEN clauses should be col VOP list
+ if (i && (x || ismul))
+ return NULL; // IN and BETWEEN clauses should be col VOP list
else if (pField->field->table != table)
return NULL; // Field does not belong to this table
else if (tty != TYPE_AM_WMI && IsIndexed(pField->field))
@@ -2815,10 +2851,19 @@ PCFIL ha_connect::CheckCond(PGLOBAL g, PCFIL filp, const Item *cond)
else
return NULL;
- } else if (tty == TYPE_AM_TBL)
- return NULL;
- else
- fnm= pField->field->field_name;
+ } else if (tty == TYPE_AM_TBL) {
+ return NULL;
+ } else {
+ bool h;
+
+ fnm = filp->Chk(pField->field->field_name, &h);
+
+ if (h && i && !ishav)
+ return NULL; // Having should be col VOP arg
+ else
+ ishav = h;
+
+ } // endif's
if (trace) {
htrc("Field index=%d\n", pField->field->field_index);
@@ -2827,11 +2872,7 @@ PCFIL ha_connect::CheckCond(PGLOBAL g, PCFIL filp, const Item *cond)
htrc("Field_type=%d\n", args[i]->field_type());
} // endif trace
- // IN and BETWEEN clauses should be col VOP list
- if (i && ismul)
- return NULL;
-
- strcat(body, fnm);
+ strcat((ishav ? havg : body), fnm);
} else if (args[i]->type() == COND::FUNC_ITEM) {
if (tty == TYPE_AM_MYSQL) {
if (!CheckCond(g, filp, args[i]))
@@ -2870,32 +2911,34 @@ PCFIL ha_connect::CheckCond(PGLOBAL g, PCFIL filp, const Item *cond)
return NULL;
if (!x) {
+ char *s = (ishav) ? havg : body;
+
// Append the value to the filter
switch (args[i]->field_type()) {
case MYSQL_TYPE_TIMESTAMP:
case MYSQL_TYPE_DATETIME:
if (tty == TYPE_AM_ODBC) {
- strcat(body, "{ts '");
- strncat(body, res->ptr(), res->length());
+ strcat(s, "{ts '");
+ strncat(s, res->ptr(), res->length());
if (res->length() < 19)
- strcat(body, &"1970-01-01 00:00:00"[res->length()]);
+ strcat(s, &"1970-01-01 00:00:00"[res->length()]);
- strcat(body, "'}");
+ strcat(s, "'}");
break;
} // endif ODBC
case MYSQL_TYPE_DATE:
if (tty == TYPE_AM_ODBC) {
- strcat(body, "{d '");
- strcat(strncat(body, res->ptr(), res->length()), "'}");
+ strcat(s, "{d '");
+ strcat(strncat(s, res->ptr(), res->length()), "'}");
break;
} // endif ODBC
case MYSQL_TYPE_TIME:
if (tty == TYPE_AM_ODBC) {
- strcat(body, "{t '");
- strcat(strncat(body, res->ptr(), res->length()), "'}");
+ strcat(s, "{t '");
+ strcat(strncat(s, res->ptr(), res->length()), "'}");
break;
} // endif ODBC
@@ -2904,39 +2947,39 @@ PCFIL ha_connect::CheckCond(PGLOBAL g, PCFIL filp, const Item *cond)
switch (args[0]->field_type()) {
case MYSQL_TYPE_TIMESTAMP:
case MYSQL_TYPE_DATETIME:
- strcat(body, "{ts '");
- strncat(body, res->ptr(), res->length());
+ strcat(s, "{ts '");
+ strncat(s, res->ptr(), res->length());
if (res->length() < 19)
- strcat(body, &"1970-01-01 00:00:00"[res->length()]);
+ strcat(s, &"1970-01-01 00:00:00"[res->length()]);
- strcat(body, "'}");
+ strcat(s, "'}");
break;
case MYSQL_TYPE_DATE:
- strcat(body, "{d '");
- strncat(body, res->ptr(), res->length());
- strcat(body, "'}");
+ strcat(s, "{d '");
+ strncat(s, res->ptr(), res->length());
+ strcat(s, "'}");
break;
case MYSQL_TYPE_TIME:
- strcat(body, "{t '");
- strncat(body, res->ptr(), res->length());
- strcat(body, "'}");
+ strcat(s, "{t '");
+ strncat(s, res->ptr(), res->length());
+ strcat(s, "'}");
break;
default:
- strcat(body, "'");
- strncat(body, res->ptr(), res->length());
- strcat(body, "'");
+ strcat(s, "'");
+ strncat(s, res->ptr(), res->length());
+ strcat(s, "'");
} // endswitch field type
} else {
- strcat(body, "'");
- strncat(body, res->ptr(), res->length());
- strcat(body, "'");
+ strcat(s, "'");
+ strncat(s, res->ptr(), res->length());
+ strcat(s, "'");
} // endif tty
break;
default:
- strncat(body, res->ptr(), res->length());
+ strncat(s, res->ptr(), res->length());
} // endswitch field type
} else {
@@ -2952,22 +2995,28 @@ PCFIL ha_connect::CheckCond(PGLOBAL g, PCFIL filp, const Item *cond)
} // endif x
- } // endif
+ } // endif's Type
if (!x) {
- if (!i)
- strcat(body, GetValStr(vop, neg));
+ char *s = (ishav) ? havg : body;
+
+ if (!i)
+ strcat(s, GetValStr(vop, neg));
else if (vop == OP_XX && i == 1)
- strcat(body, " AND ");
+ strcat(s, " AND ");
else if (vop == OP_IN)
- strcat(body, (i == condf->argument_count() - 1) ? ")" : ",");
+ strcat(s, (i == condf->argument_count() - 1) ? ")" : ",");
} // endif x
} // endfor i
- if (x)
- filp->Op= vop;
+ if (x)
+ filp->Op = vop;
+ else if (ishav)
+ filp->Hv = true;
+ else
+ filp->Bd = true;
} else {
if (trace)
@@ -3024,16 +3073,28 @@ const COND *ha_connect::cond_push(const COND *cond)
if (b) {
PCFIL filp;
+ int rc;
if ((filp= tdbp->GetCondFil()) && filp->Cond == cond &&
filp->Idx == active_index && filp->Type == tty)
goto fin; // Already done
filp= new(g) CONDFIL(cond, active_index, tty);
- filp->Body= (char*)PlugSubAlloc(g, NULL, (x) ? 128 : 0);
- *filp->Body= 0;
+ rc = filp->Init(g, this);
+
+ if (rc == RC_INFO) {
+ filp->Having = (char*)PlugSubAlloc(g, NULL, 256);
+ *filp->Having = 0;
+ } else if (rc == RC_FX)
+ goto fin;
+
+ filp->Body = (char*)PlugSubAlloc(g, NULL, (x) ? 128 : 0);
+ *filp->Body = 0;
if (CheckCond(g, filp, cond)) {
+ if (filp->Having && strlen(filp->Having) > 255)
+ goto fin; // Memory collapse
+
if (trace)
htrc("cond_push: %s\n", filp->Body);
@@ -3206,9 +3267,9 @@ int ha_connect::optimize(THD* thd, HA_CHECK_OPT*)
tdbp= GetTDB(g);
dup->Check |= CHK_OPT;
- if (tdbp) {
+ if (tdbp && !tdbp->IsRemote()) {
bool dop= IsTypeIndexable(GetRealType(NULL));
- bool dox= (((PTDBASE)tdbp)->GetDef()->Indexable() == 1);
+ bool dox= (tdbp->GetDef()->Indexable() == 1);
if ((rc= ((PTDBASE)tdbp)->ResetTableOpt(g, dop, dox))) {
if (rc == RC_INFO) {
@@ -3219,7 +3280,7 @@ int ha_connect::optimize(THD* thd, HA_CHECK_OPT*)
} // endif rc
- } else
+ } else if (!tdbp)
rc= HA_ERR_INTERNAL_ERROR;
return rc;
@@ -3462,9 +3523,9 @@ int ha_connect::index_init(uint idx, bool sorted)
htrc("index_init CONNECT: %s\n", g->Message);
active_index= MAX_KEY;
rc= HA_ERR_INTERNAL_ERROR;
- } else if (((PTDBDOX)tdbp)->To_Kindex) {
+ } else if (tdbp->GetKindex()) {
if (((PTDBDOX)tdbp)->To_Kindex->GetNum_K()) {
- if (((PTDBASE)tdbp)->GetFtype() != RECFM_NAF)
+ if (tdbp->GetFtype() != RECFM_NAF)
((PTDBDOX)tdbp)->GetTxfp()->ResetBuffer(g);
active_index= idx;
@@ -3878,11 +3939,10 @@ int ha_connect::rnd_next(uchar *buf)
void ha_connect::position(const uchar *)
{
DBUG_ENTER("ha_connect::position");
-//if (((PTDBASE)tdbp)->GetDef()->Indexable())
- my_store_ptr(ref, ref_length, (my_off_t)((PTDBASE)tdbp)->GetRecpos());
+ my_store_ptr(ref, ref_length, (my_off_t)tdbp->GetRecpos());
if (trace > 1)
- htrc("position: pos=%d\n", ((PTDBASE)tdbp)->GetRecpos());
+ htrc("position: pos=%d\n", tdbp->GetRecpos());
DBUG_VOID_RETURN;
} // end of position
@@ -3907,14 +3967,14 @@ void ha_connect::position(const uchar *)
int ha_connect::rnd_pos(uchar *buf, uchar *pos)
{
int rc;
- PTDBASE tp= (PTDBASE)tdbp;
+//PTDBASE tp= (PTDBASE)tdbp;
DBUG_ENTER("ha_connect::rnd_pos");
- if (!tp->SetRecpos(xp->g, (int)my_get_ptr(pos, ref_length))) {
+ if (!tdbp->SetRecpos(xp->g, (int)my_get_ptr(pos, ref_length))) {
if (trace)
- htrc("rnd_pos: %d\n", tp->GetRecpos());
+ htrc("rnd_pos: %d\n", tdbp->GetRecpos());
- tp->SetFilter(NULL);
+ tdbp->SetFilter(NULL);
rc= rnd_next(buf);
} else
rc= HA_ERR_KEY_NOT_FOUND;
@@ -4092,7 +4152,7 @@ int ha_connect::delete_all_rows()
if (tdbp && tdbp->GetUse() == USE_OPEN &&
tdbp->GetAmType() != TYPE_AM_XML &&
- ((PTDBASE)tdbp)->GetFtype() != RECFM_NAF)
+ tdbp->GetFtype() != RECFM_NAF)
// Close and reopen the table so it will be deleted
rc= CloseTable(g);
@@ -4470,12 +4530,12 @@ int ha_connect::external_lock(THD *thd, int lock_type)
if (!tdbp) {
if (!(tdbp= GetTDB(g)))
DBUG_RETURN(HA_ERR_INTERNAL_ERROR);
- else if (!((PTDBASE)tdbp)->GetDef()->Indexable()) {
+ else if (!tdbp->GetDef()->Indexable()) {
sprintf(g->Message, "external_lock: Table %s is not indexable", tdbp->GetName());
// DBUG_RETURN(HA_ERR_INTERNAL_ERROR); causes assert error
push_warning(thd, Sql_condition::WARN_LEVEL_WARN, 0, g->Message);
DBUG_RETURN(0);
- } else if (((PTDBASE)tdbp)->GetDef()->Indexable() == 1) {
+ } else if (tdbp->GetDef()->Indexable() == 1) {
bool oldsep= ((PCHK)g->Xchk)->oldsep;
bool newsep= ((PCHK)g->Xchk)->newsep;
PTDBDOS tdp= (PTDBDOS)tdbp;
@@ -4556,7 +4616,7 @@ int ha_connect::external_lock(THD *thd, int lock_type)
rc= 0;
} // endif MakeIndex
- } else if (((PTDBASE)tdbp)->GetDef()->Indexable() == 3) {
+ } else if (tdbp->GetDef()->Indexable() == 3) {
if (CheckVirtualIndex(NULL)) {
// Make it a warning to avoid crash
push_warning(thd, Sql_condition::WARN_LEVEL_WARN,
@@ -5172,7 +5232,7 @@ static int connect_assisted_discovery(handlerton *, THD* thd,
TABLE_SHARE *table_s,
HA_CREATE_INFO *create_info)
{
- char v=0, spc= ',', qch= 0;
+ char v=0;
const char *fncn= "?";
const char *user, *fn, *db, *host, *pwd, *sep, *tbl, *src;
const char *col, *ocl, *rnk, *pic, *fcl, *skc, *zfn;
@@ -5224,8 +5284,6 @@ static int connect_assisted_discovery(handlerton *, THD* thd,
fncn= topt->catfunc;
fnc= GetFuncID(fncn);
sep= topt->separator;
- spc= (!sep) ? ',' : *sep;
- qch= topt->qchar ? *topt->qchar : (signed)topt->quoted >= 0 ? '"' : 0;
mul = (int)topt->multiple;
tbl= topt->tablist;
col= topt->colist;
@@ -5425,8 +5483,8 @@ static int connect_assisted_discovery(handlerton *, THD* thd,
if (mydef->GetPassword())
pwd= mydef->GetPassword();
- if (mydef->GetDatabase())
- db= mydef->GetDatabase();
+ if (mydef->GetTabschema())
+ db = mydef->GetTabschema();
if (mydef->GetTabname())
tab= mydef->GetTabname();
@@ -6052,8 +6110,8 @@ int ha_connect::create(const char *name, TABLE *table_arg,
if (mydef->GetHostname())
host= mydef->GetHostname();
- if (mydef->GetDatabase())
- db= mydef->GetDatabase();
+ if (mydef->GetTabschema())
+ db = mydef->GetTabschema();
if (mydef->GetTabname())
tab= mydef->GetTabname();
@@ -6266,21 +6324,26 @@ int ha_connect::create(const char *name, TABLE *table_arg,
// Check for incompatible options
if (options->sepindex) {
my_message(ER_UNKNOWN_ERROR,
- "SEPINDEX is incompatible with unspecified file name",
- MYF(0));
+ "SEPINDEX is incompatible with unspecified file name", MYF(0));
DBUG_RETURN(HA_ERR_UNSUPPORTED);
- } else if (GetTypeID(options->type) == TAB_VEC)
- if (!table->s->max_rows || options->split) {
- my_printf_error(ER_UNKNOWN_ERROR,
- "%s tables whose file name is unspecified cannot be split",
- MYF(0), options->type);
- DBUG_RETURN(HA_ERR_UNSUPPORTED);
- } else if (options->header == 2) {
- my_printf_error(ER_UNKNOWN_ERROR,
- "header=2 is not allowed for %s tables whose file name is unspecified",
- MYF(0), options->type);
- DBUG_RETURN(HA_ERR_UNSUPPORTED);
- } // endif's
+ } else if (GetTypeID(options->type) == TAB_VEC) {
+ if (!table->s->max_rows || options->split) {
+ my_printf_error(ER_UNKNOWN_ERROR,
+ "%s tables whose file name is unspecified cannot be split",
+ MYF(0), options->type);
+ DBUG_RETURN(HA_ERR_UNSUPPORTED);
+ } else if (options->header == 2) {
+ my_printf_error(ER_UNKNOWN_ERROR,
+ "header=2 is not allowed for %s tables whose file name is unspecified",
+ MYF(0), options->type);
+ DBUG_RETURN(HA_ERR_UNSUPPORTED);
+ } // endif's
+
+ } else if (options->zipped) {
+ my_message(ER_UNKNOWN_ERROR,
+ "ZIPPED is incompatible with unspecified file name", MYF(0));
+ DBUG_RETURN(HA_ERR_UNSUPPORTED);
+ } // endif's options
// Fold type to lower case
for (int i= 0; i < 12; i++)
@@ -6333,6 +6396,36 @@ int ha_connect::create(const char *name, TABLE *table_arg,
if (trace)
htrc("xchk=%p createas=%d\n", g->Xchk, g->Createas);
+ if (options->zipped) {
+ // Check whether the zip entry must be made from a file
+ char *fn = GetListOption(g, "Load", options->oplist, NULL);
+
+ if (fn) {
+ char zbuf[_MAX_PATH], buf[_MAX_PATH], dbpath[_MAX_PATH];
+ char *entry = GetListOption(g, "Entry", options->oplist, NULL);
+ char *a = GetListOption(g, "Append", options->oplist, "NO");
+ bool append = *a == '1' || *a == 'Y' || *a == 'y' || !stricmp(a, "ON");
+ char *m = GetListOption(g, "Mulentries", options->oplist, "NO");
+ bool mul = *m == '1' || *m == 'Y' || *m == 'y' || !stricmp(m, "ON");
+
+ if (!entry && !mul) {
+ my_message(ER_UNKNOWN_ERROR, "Missing entry name", MYF(0));
+ DBUG_RETURN(HA_ERR_INTERNAL_ERROR);
+ } // endif entry
+
+ strcat(strcat(strcpy(dbpath, "./"), table->s->db.str), "/");
+ PlugSetPath(zbuf, options->filename, dbpath);
+ PlugSetPath(buf, fn, dbpath);
+
+ if (ZipLoadFile(g, zbuf, buf, entry, append, mul)) {
+ my_message(ER_UNKNOWN_ERROR, g->Message, MYF(0));
+ DBUG_RETURN(HA_ERR_INTERNAL_ERROR);
+ } // endif LoadFile
+
+ } // endif fn
+
+ } // endif zipped
+
// To check whether indexes have to be made or remade
if (!g->Xchk) {
PIXDEF xdp;
@@ -6951,10 +7044,10 @@ maria_declare_plugin(connect)
PLUGIN_LICENSE_GPL,
connect_init_func, /* Plugin Init */
connect_done_func, /* Plugin Deinit */
- 0x0104, /* version number (1.04) */
+ 0x0105, /* version number (1.05) */
NULL, /* status variables */
connect_system_variables, /* system variables */
- "1.05.0001", /* string version */
+ "1.05.0003", /* string version */
MariaDB_PLUGIN_MATURITY_GAMMA /* maturity */
}
maria_declare_plugin_end;
diff --git a/storage/connect/ha_connect.h b/storage/connect/ha_connect.h
index 3d9ff967618..cb15d371b5c 100644
--- a/storage/connect/ha_connect.h
+++ b/storage/connect/ha_connect.h
@@ -11,7 +11,7 @@
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 */
+ Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02111-1301 USA */
/** @file ha_connect.h
diff --git a/storage/connect/inihandl.c b/storage/connect/inihandl.c
index 896431b855f..e5eb3567779 100644
--- a/storage/connect/inihandl.c
+++ b/storage/connect/inihandl.c
@@ -16,7 +16,7 @@
*
* You should have received a copy of the GNU Lesser General Public
* License along with this library; if not, write to the Free Software
- * Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA
+ * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02111-1301 USA
*/
#include "my_global.h"
diff --git a/storage/connect/ioapi.c b/storage/connect/ioapi.c
index 7f5c191b2af..a49da91f7f0 100644
--- a/storage/connect/ioapi.c
+++ b/storage/connect/ioapi.c
@@ -27,6 +27,7 @@
#include "ioapi.h"
+#include "my_attribute.h"
voidpf call_zopen64 (const zlib_filefunc64_32_def* pfilefunc,const void*filename,int mode)
{
@@ -92,7 +93,7 @@ static long ZCALLBACK fseek64_file_func OF((voidpf opaque, voidpf stream, ZPO
static int ZCALLBACK fclose_file_func OF((voidpf opaque, voidpf stream));
static int ZCALLBACK ferror_file_func OF((voidpf opaque, voidpf stream));
-static voidpf ZCALLBACK fopen_file_func (voidpf opaque, const char* filename, int mode)
+static voidpf ZCALLBACK fopen_file_func (voidpf opaque __attribute__((unused)), const char* filename, int mode)
{
FILE* file = NULL;
const char* mode_fopen = NULL;
@@ -110,7 +111,7 @@ static voidpf ZCALLBACK fopen_file_func (voidpf opaque, const char* filename, in
return file;
}
-static voidpf ZCALLBACK fopen64_file_func (voidpf opaque, const void* filename, int mode)
+static voidpf ZCALLBACK fopen64_file_func (voidpf opaque __attribute__((unused)), const void* filename, int mode)
{
FILE* file = NULL;
const char* mode_fopen = NULL;
@@ -129,21 +130,21 @@ static voidpf ZCALLBACK fopen64_file_func (voidpf opaque, const void* filename,
}
-static uLong ZCALLBACK fread_file_func (voidpf opaque, voidpf stream, void* buf, uLong size)
+static uLong ZCALLBACK fread_file_func (voidpf opaque __attribute__((unused)), voidpf stream, void* buf, uLong size)
{
uLong ret;
ret = (uLong)fread(buf, 1, (size_t)size, (FILE *)stream);
return ret;
}
-static uLong ZCALLBACK fwrite_file_func (voidpf opaque, voidpf stream, const void* buf, uLong size)
+static uLong ZCALLBACK fwrite_file_func (voidpf opaque __attribute__((unused)), voidpf stream, const void* buf, uLong size)
{
uLong ret;
ret = (uLong)fwrite(buf, 1, (size_t)size, (FILE *)stream);
return ret;
}
-static long ZCALLBACK ftell_file_func (voidpf opaque, voidpf stream)
+static long ZCALLBACK ftell_file_func (voidpf opaque __attribute__((unused)), voidpf stream)
{
long ret;
ret = ftell((FILE *)stream);
@@ -151,14 +152,14 @@ static long ZCALLBACK ftell_file_func (voidpf opaque, voidpf stream)
}
-static ZPOS64_T ZCALLBACK ftell64_file_func (voidpf opaque, voidpf stream)
+static ZPOS64_T ZCALLBACK ftell64_file_func (voidpf opaque __attribute__((unused)), voidpf stream)
{
ZPOS64_T ret;
ret = FTELLO_FUNC((FILE *)stream);
return ret;
}
-static long ZCALLBACK fseek_file_func (voidpf opaque, voidpf stream, uLong offset, int origin)
+static long ZCALLBACK fseek_file_func (voidpf opaque __attribute__((unused)), voidpf stream, uLong offset, int origin)
{
int fseek_origin=0;
long ret;
@@ -181,7 +182,7 @@ static long ZCALLBACK fseek_file_func (voidpf opaque, voidpf stream, uLong offs
return ret;
}
-static long ZCALLBACK fseek64_file_func (voidpf opaque, voidpf stream, ZPOS64_T offset, int origin)
+static long ZCALLBACK fseek64_file_func (voidpf opaque __attribute__((unused)), voidpf stream, ZPOS64_T offset, int origin)
{
int fseek_origin=0;
long ret;
@@ -207,14 +208,14 @@ static long ZCALLBACK fseek64_file_func (voidpf opaque, voidpf stream, ZPOS64_T
}
-static int ZCALLBACK fclose_file_func (voidpf opaque, voidpf stream)
+static int ZCALLBACK fclose_file_func (voidpf opaque __attribute__((unused)), voidpf stream)
{
int ret;
ret = fclose((FILE *)stream);
return ret;
}
-static int ZCALLBACK ferror_file_func (voidpf opaque, voidpf stream)
+static int ZCALLBACK ferror_file_func (voidpf opaque __attribute__((unused)), voidpf stream)
{
int ret;
ret = ferror((FILE *)stream);
diff --git a/storage/connect/jdbconn.cpp b/storage/connect/jdbconn.cpp
index a69f84a94a1..c1d077406b7 100644
--- a/storage/connect/jdbconn.cpp
+++ b/storage/connect/jdbconn.cpp
@@ -1,7 +1,7 @@
/************ Jdbconn C++ Functions Source Code File (.CPP) ************/
-/* Name: JDBCONN.CPP Version 1.0 */
+/* Name: JDBCONN.CPP Version 1.1 */
/* */
-/* (C) Copyright to the author Olivier BERTRAND 2016 */
+/* (C) Copyright to the author Olivier BERTRAND 2016-2017 */
/* */
/* This file contains the JDBC connection classes functions. */
/***********************************************************************/
@@ -45,9 +45,9 @@
#include "plgdbsem.h"
#include "xobject.h"
#include "xtable.h"
+#include "tabext.h"
#include "tabjdbc.h"
//#include "jdbconn.h"
-//#include "plgcnx.h" // For DB types
#include "resource.h"
#include "valblk.h"
#include "osutil.h"
@@ -318,13 +318,21 @@ PQRYRES JDBCColumns(PGLOBAL g, char *db, char *table, char *colpat,
/**************************************************************************/
PQRYRES JDBCSrcCols(PGLOBAL g, char *src, PJPARM sjp)
{
+ char *sqry;
PQRYRES qrp;
JDBConn *jcp = new(g)JDBConn(g, NULL);
if (jcp->Open(sjp))
return NULL;
- qrp = jcp->GetMetaData(g, src);
+ if (strstr(src, "%s")) {
+ // Place holder for an eventual where clause
+ sqry = (char*)PlugSubAlloc(g, NULL, strlen(src) + 2);
+ sprintf(sqry, src, "1=1"); // dummy where clause
+ } else
+ sqry = src;
+
+ qrp = jcp->GetMetaData(g, sqry);
jcp->Close();
return qrp;
} // end of JDBCSrcCols
@@ -818,6 +826,11 @@ int JDBConn::Open(PJPARM sop)
jpop->Append(GetPluginDir());
jpop->Append("JdbcInterface.jar");
+ // All wrappers are pre-compiled in JavaWrappers.jar in the plugin dir
+ jpop->Append(sep);
+ jpop->Append(GetPluginDir());
+ jpop->Append("JavaWrappers.jar");
+
//================== prepare loading of Java VM ============================
JavaVMInitArgs vm_args; // Initialization arguments
JavaVMOption* options = new JavaVMOption[N]; // JVM invocation options
@@ -1157,6 +1170,9 @@ void JDBConn::Close()
jint rc;
jmethodID did = nullptr;
+ // Could have been detached in case of join
+ rc = jvm->AttachCurrentThread((void**)&env, nullptr);
+
if (gmID(m_G, did, "JdbcDisconnect", "()I"))
printf("%s\n", Msg);
else if (Check(env->CallIntMethod(job, did)))
diff --git a/storage/connect/json.cpp b/storage/connect/json.cpp
index c45630129f1..b473871e9f7 100644
--- a/storage/connect/json.cpp
+++ b/storage/connect/json.cpp
@@ -1,7 +1,7 @@
/*************** json CPP Declares Source Code File (.H) ***************/
-/* Name: json.cpp Version 1.2 */
+/* Name: json.cpp Version 1.3 */
/* */
-/* (C) Copyright to the author Olivier BERTRAND 2014 - 2015 */
+/* (C) Copyright to the author Olivier BERTRAND 2014 - 2017 */
/* */
/* This file contains the JSON classes functions. */
/***********************************************************************/
@@ -27,8 +27,33 @@
#define EL "\r\n"
#else
#define EL "\n"
+#undef SE_CATCH // Does not work for Linux
#endif
+#if defined(SE_CATCH)
+/**************************************************************************/
+/* This is the support of catching C interrupts to prevent crashes. */
+/**************************************************************************/
+#include <eh.h>
+
+class SE_Exception {
+public:
+ SE_Exception(unsigned int n, PEXCEPTION_RECORD p) : nSE(n), eRec(p) {}
+ ~SE_Exception() {}
+
+ unsigned int nSE;
+ PEXCEPTION_RECORD eRec;
+}; // end of class SE_Exception
+
+void trans_func(unsigned int u, _EXCEPTION_POINTERS* pExp)
+{
+ throw SE_Exception(u, pExp->ExceptionRecord);
+} // end of trans_func
+
+char *GetExceptionDesc(PGLOBAL g, unsigned int e);
+#endif // SE_CATCH
+
+
/***********************************************************************/
/* Parse a json string. */
/* Note: when pretty is not known, the caller set pretty to 3. */
@@ -40,6 +65,9 @@ PJSON ParseJson(PGLOBAL g, char *s, int len, int *ptyp, bool *comma)
PJSON jsp = NULL;
STRG src;
+ if (trace)
+ htrc("ParseJson: s=%.10s len=%d\n", s, len);
+
if (!s || !len) {
strcpy(g->Message, "Void JSON object");
return NULL;
@@ -53,15 +81,37 @@ PJSON ParseJson(PGLOBAL g, char *s, int len, int *ptyp, bool *comma)
if (s[0] == '[' && (s[1] == '\n' || (s[1] == '\r' && s[2] == '\n')))
pty[0] = false;
+
// Save stack and allocation environment and prepare error return
if (g->jump_level == MAX_JUMP) {
strcpy(g->Message, MSG(TOO_MANY_JUMPS));
return NULL;
} // endif jump_level
- if ((rc= setjmp(g->jumper[++g->jump_level])) != 0) {
- goto err;
- } // endif rc
+#if defined(SE_CATCH)
+ // Let's try to recover from any kind of interrupt
+ _se_translator_function f = _set_se_translator(trans_func);
+
+ try {
+#endif // SE_CATCH --------------------- try section --------------------
+ if ((rc = setjmp(g->jumper[++g->jump_level])) != 0) {
+ goto err;
+ } // endif rc
+
+#if defined(SE_CATCH) // ------------- end of try section -----------------
+ } catch (SE_Exception e) {
+ sprintf(g->Message, "ParseJson: exception doing setjmp: %s (rc=%hd)",
+ GetExceptionDesc(g, e.nSE), e.nSE);
+ _set_se_translator(f);
+ goto err;
+ } catch (...) {
+ strcpy(g->Message, "Exception doing setjmp");
+ _set_se_translator(f);
+ goto err;
+ } // end of try-catches
+
+ _set_se_translator(f);
+#endif // SE_CATCH
for (i = 0; i < len; i++)
switch (s[i]) {
@@ -140,7 +190,7 @@ tryit:
strcpy(g->Message, "More than one item in file");
err:
- g->jump_level--;
+ g->jump_level--;
return NULL;
} // end of ParseJson
@@ -390,14 +440,14 @@ char *ParseString(PGLOBAL g, int& i, STRG& src)
// if (charset == utf8) {
char xs[5];
uint hex;
-
+
xs[0] = s[++i];
xs[1] = s[++i];
xs[2] = s[++i];
xs[3] = s[++i];
xs[4] = 0;
hex = strtoul(xs, NULL, 16);
-
+
if (hex < 0x80) {
p[n] = (uchar)hex;
} else if (hex < 0x800) {
@@ -414,7 +464,7 @@ char *ParseString(PGLOBAL g, int& i, STRG& src)
} else {
char xs[3];
UINT hex;
-
+
i += 2;
xs[0] = s[++i];
xs[1] = s[++i];
@@ -468,7 +518,7 @@ PVAL ParseNumeric(PGLOBAL g, int& i, STRG& src)
case '.':
if (!found_digit || has_dot || has_e)
goto err;
-
+
has_dot = true;
break;
case 'e':
@@ -769,7 +819,7 @@ bool JOUTSTR::Escape(const char *s)
for (unsigned int i = 0; s[i]; i++)
switch (s[i]) {
- case '"':
+ case '"':
case '\\':
case '\t':
case '\n':
@@ -1057,7 +1107,7 @@ void JARRAY::InitArray(PGLOBAL g)
int i;
PJVAL jvp, *pjvp = &First;
- for (Size = 0, jvp = First; jvp; jvp = jvp->Next)
+ for (Size = 0, jvp = First; jvp; jvp = jvp->Next)
if (!jvp->Del)
Size++;
@@ -1191,8 +1241,8 @@ bool JARRAY::IsNull(void)
/***********************************************************************/
JVALUE::JVALUE(PGLOBAL g, PVAL valp) : JSON()
{
- Jsp = NULL;
- Value = AllocateValue(g, valp);
+ Jsp = NULL;
+ Value = AllocateValue(g, valp);
Next = NULL;
Del = false;
} // end of JVALUE constructor
@@ -1297,7 +1347,7 @@ PSZ JVALUE::GetText(PGLOBAL g, PSZ text)
} // end of GetText
void JVALUE::SetValue(PJSON jsp)
-{
+{
if (jsp && jsp->GetType() == TYPE_JVAL) {
Jsp = jsp->GetJsp();
Value = jsp->GetValue();
diff --git a/storage/connect/jsonudf.cpp b/storage/connect/jsonudf.cpp
index bc7f231814d..f07a1ac818f 100644
--- a/storage/connect/jsonudf.cpp
+++ b/storage/connect/jsonudf.cpp
@@ -1,6 +1,6 @@
/****************** jsonudf C++ Program Source Code File (.CPP) ******************/
-/* PROGRAM NAME: jsonudf Version 1.4 */
-/* (C) Copyright to the author Olivier BERTRAND 2015-2016 */
+/* PROGRAM NAME: jsonudf Version 1.5 */
+/* (C) Copyright to the author Olivier BERTRAND 2015-2017 */
/* This program are the JSON User Defined Functions . */
/*********************************************************************************/
@@ -242,13 +242,16 @@ my_bool JSNX::ParseJpath(PGLOBAL g)
// Jpath = Name;
return true;
- pbuf = PlugDup(g, Jpath);
+ if (!(pbuf = PlgDBDup(g, Jpath)))
+ return true;
// The Jpath must be analyzed
for (i = 0, p = pbuf; (p = strchr(p, ':')); i++, p++)
Nod++; // One path node found
- Nodes = (PJNODE)PlugSubAlloc(g, NULL, (++Nod) * sizeof(JNODE));
+ if (!(Nodes = (PJNODE)PlgDBSubAlloc(g, NULL, (++Nod) * sizeof(JNODE))))
+ return true;
+
memset(Nodes, 0, (Nod)* sizeof(JNODE));
// Analyze the Jpath for this column
@@ -1086,9 +1089,10 @@ inline void JsonFreeMem(PGLOBAL g)
/*********************************************************************************/
static my_bool JsonInit(UDF_INIT *initid, UDF_ARGS *args,
char *message, my_bool mbn,
- unsigned long reslen, unsigned long memlen)
+ unsigned long reslen, unsigned long memlen,
+ unsigned long more = 0)
{
- PGLOBAL g = PlugInit(NULL, memlen);
+ PGLOBAL g = PlugInit(NULL, memlen + more);
if (!g) {
strcpy(message, "Allocation error");
@@ -1100,6 +1104,7 @@ static my_bool JsonInit(UDF_INIT *initid, UDF_ARGS *args,
} // endif g
g->Mrr = (args->arg_count && args->args[0]) ? 1 : 0;
+ g->ActivityStart = (PACTIVITY)more;
initid->maybe_null = mbn;
initid->max_length = reslen;
initid->ptr = (char*)g;
@@ -1443,6 +1448,8 @@ static my_bool CheckMemory(PGLOBAL g, UDF_INIT *initid, UDF_ARGS *args, uint n,
} // endif b
+ ml += (unsigned long)g->ActivityStart; // more
+
if (ml > g->Sarea_Size) {
free(g->Sarea);
@@ -2757,7 +2764,7 @@ void json_item_merge_deinit(UDF_INIT* initid)
/*********************************************************************************/
my_bool json_get_item_init(UDF_INIT *initid, UDF_ARGS *args, char *message)
{
- unsigned long reslen, memlen;
+ unsigned long reslen, memlen, more;
int n = IsJson(args, 0);
if (args->arg_count < 2) {
@@ -2766,7 +2773,7 @@ my_bool json_get_item_init(UDF_INIT *initid, UDF_ARGS *args, char *message)
} else if (!n && args->arg_type[0] != STRING_RESULT) {
strcpy(message, "First argument must be a json item");
return true;
- } else if (args->arg_type[1] != STRING_RESULT) {
+ } else if (args->arg_type[1] != STRING_RESULT) {
strcpy(message, "Second argument is not a string (jpath)");
return true;
} else
@@ -2779,11 +2786,13 @@ my_bool json_get_item_init(UDF_INIT *initid, UDF_ARGS *args, char *message)
memcpy(fn, args->args[0], args->lengths[0]);
fn[args->lengths[0]] = 0;
fl = GetFileLength(fn);
- memlen += fl * 3;
- } else if (n != 3)
- memlen += args->lengths[0] * 3;
+ more = fl * 3;
+ } else if (n != 3) {
+ more = args->lengths[0] * 3;
+ } else
+ more = 0;
- return JsonInit(initid, args, message, true, reslen, memlen);
+ return JsonInit(initid, args, message, true, reslen, memlen, more);
} // end of json_get_item_init
char *json_get_item(UDF_INIT *initid, UDF_ARGS *args, char *result,
@@ -2884,7 +2893,7 @@ my_bool jsonget_string_init(UDF_INIT *initid, UDF_ARGS *args, char *message)
} // endif's
CalcLen(args, false, reslen, memlen);
- memlen += more;
+//memlen += more;
if (n == 2 && args->args[0]) {
char fn[_MAX_PATH];
@@ -2893,11 +2902,11 @@ my_bool jsonget_string_init(UDF_INIT *initid, UDF_ARGS *args, char *message)
memcpy(fn, args->args[0], args->lengths[0]);
fn[args->lengths[0]] = 0;
fl = GetFileLength(fn);
- memlen += fl * 3;
+ more += fl * 3;
} else if (n != 3)
- memlen += args->lengths[0] * 3;
+ more += args->lengths[0] * 3;
- return JsonInit(initid, args, message, true, reslen, memlen);
+ return JsonInit(initid, args, message, true, reslen, memlen, more);
} // end of jsonget_string_init
char *jsonget_string(UDF_INIT *initid, UDF_ARGS *args, char *result,
@@ -2993,7 +3002,7 @@ void jsonget_string_deinit(UDF_INIT* initid)
/*********************************************************************************/
my_bool jsonget_int_init(UDF_INIT *initid, UDF_ARGS *args, char *message)
{
- unsigned long reslen, memlen;
+ unsigned long reslen, memlen, more;
if (args->arg_count != 2) {
strcpy(message, "This function must have 2 arguments");
@@ -3007,10 +3016,10 @@ my_bool jsonget_int_init(UDF_INIT *initid, UDF_ARGS *args, char *message)
} else
CalcLen(args, false, reslen, memlen);
- if (IsJson(args, 0) != 3)
- memlen += 1000; // TODO: calculate this
+ // TODO: calculate this
+ more = (IsJson(args, 0) != 3) ? 1000 : 0;
- return JsonInit(initid, args, message, true, reslen, memlen);
+ return JsonInit(initid, args, message, true, reslen, memlen, more);
} // end of jsonget_int_init
long long jsonget_int(UDF_INIT *initid, UDF_ARGS *args,
@@ -3099,7 +3108,7 @@ void jsonget_int_deinit(UDF_INIT* initid)
/*********************************************************************************/
my_bool jsonget_real_init(UDF_INIT *initid, UDF_ARGS *args, char *message)
{
- unsigned long reslen, memlen;
+ unsigned long reslen, memlen, more;
if (args->arg_count < 2) {
strcpy(message, "At least 2 arguments required");
@@ -3122,10 +3131,10 @@ my_bool jsonget_real_init(UDF_INIT *initid, UDF_ARGS *args, char *message)
CalcLen(args, false, reslen, memlen);
- if (IsJson(args, 0) != 3)
- memlen += 1000; // TODO: calculate this
+ // TODO: calculate this
+ more = (IsJson(args, 0) != 3) ? 1000 : 0;
- return JsonInit(initid, args, message, true, reslen, memlen);
+ return JsonInit(initid, args, message, true, reslen, memlen, more);
} // end of jsonget_real_init
double jsonget_real(UDF_INIT *initid, UDF_ARGS *args,
@@ -3233,10 +3242,11 @@ my_bool jsonlocate_init(UDF_INIT *initid, UDF_ARGS *args, char *message)
CalcLen(args, false, reslen, memlen);
- if (IsJson(args, 0) != 3)
- memlen += more; // TODO: calculate this
+ // TODO: calculate this
+ if (IsJson(args, 0) == 3)
+ more = 0;
- return JsonInit(initid, args, message, true, reslen, memlen);
+ return JsonInit(initid, args, message, true, reslen, memlen, more);
} // end of jsonlocate_init
char *jsonlocate(UDF_INIT *initid, UDF_ARGS *args, char *result,
@@ -3357,10 +3367,11 @@ my_bool json_locate_all_init(UDF_INIT *initid, UDF_ARGS *args, char *message)
CalcLen(args, false, reslen, memlen);
- if (IsJson(args, 0) != 3)
- memlen += more; // TODO: calculate this
+ // TODO: calculate this
+ if (IsJson(args, 0) == 3)
+ more = 0;
- return JsonInit(initid, args, message, true, reslen, memlen);
+ return JsonInit(initid, args, message, true, reslen, memlen, more);
} // end of json_locate_all_init
char *json_locate_all(UDF_INIT *initid, UDF_ARGS *args, char *result,
@@ -3484,12 +3495,12 @@ my_bool jsoncontains_init(UDF_INIT *initid, UDF_ARGS *args, char *message)
} // endif's
CalcLen(args, false, reslen, memlen);
- memlen += more;
+//memlen += more;
- if (IsJson(args, 0) != 3)
- memlen += 1000; // TODO: calculate this
+ // TODO: calculate this
+ more += (IsJson(args, 0) != 3 ? 1000 : 0);
- return JsonInit(initid, args, message, false, reslen, memlen);
+ return JsonInit(initid, args, message, false, reslen, memlen, more);
} // end of jsoncontains_init
long long jsoncontains(UDF_INIT *initid, UDF_ARGS *args, char *result,
@@ -3536,12 +3547,12 @@ my_bool jsoncontains_path_init(UDF_INIT *initid, UDF_ARGS *args, char *message)
} // endif's
CalcLen(args, false, reslen, memlen);
- memlen += more;
+//memlen += more;
- if (IsJson(args, 0) != 3)
- memlen += 1000; // TODO: calculate this
+ // TODO: calculate this
+ more += (IsJson(args, 0) != 3 ? 1000 : 0);
- return JsonInit(initid, args, message, true, reslen, memlen);
+ return JsonInit(initid, args, message, true, reslen, memlen, more);
} // end of jsoncontains_path_init
long long jsoncontains_path(UDF_INIT *initid, UDF_ARGS *args, char *result,
@@ -3735,7 +3746,7 @@ fin:
/*********************************************************************************/
my_bool json_set_item_init(UDF_INIT *initid, UDF_ARGS *args, char *message)
{
- unsigned long reslen, memlen;
+ unsigned long reslen, memlen, more = 0;
int n = IsJson(args, 0);
if (!(args->arg_count % 2)) {
@@ -3754,11 +3765,11 @@ my_bool json_set_item_init(UDF_INIT *initid, UDF_ARGS *args, char *message)
memcpy(fn, args->args[0], args->lengths[0]);
fn[args->lengths[0]] = 0;
fl = GetFileLength(fn);
- memlen += fl * 3;
+ more += fl * 3;
} else if (n != 3)
- memlen += args->lengths[0] * 3;
+ more += args->lengths[0] * 3;
- if (!JsonInit(initid, args, message, true, reslen, memlen)) {
+ if (!JsonInit(initid, args, message, true, reslen, memlen, more)) {
PGLOBAL g = (PGLOBAL)initid->ptr;
// This is a constant function
@@ -3953,7 +3964,7 @@ void json_file_deinit(UDF_INIT* initid)
/*********************************************************************************/
my_bool jfile_make_init(UDF_INIT *initid, UDF_ARGS *args, char *message)
{
- unsigned long reslen, memlen, more = 1024;
+ unsigned long reslen, memlen;
if (args->arg_count < 1 || args->arg_count > 3) {
strcpy(message, "Wrong number of arguments");
@@ -4992,7 +5003,7 @@ fin:
/*********************************************************************************/
my_bool jbin_set_item_init(UDF_INIT *initid, UDF_ARGS *args, char *message)
{
- unsigned long reslen, memlen;
+ unsigned long reslen, memlen, more = 0;
int n = IsJson(args, 0);
if (!(args->arg_count % 2)) {
@@ -5011,11 +5022,11 @@ my_bool jbin_set_item_init(UDF_INIT *initid, UDF_ARGS *args, char *message)
memcpy(fn, args->args[0], args->lengths[0]);
fn[args->lengths[0]] = 0;
fl = GetFileLength(fn);
- memlen += fl * 3;
+ more = fl * 3;
} else if (n != 3)
- memlen += args->lengths[0] * 3;
+ more = args->lengths[0] * 3;
- return JsonInit(initid, args, message, true, reslen, memlen);
+ return JsonInit(initid, args, message, true, reslen, memlen, more);
} // end of jbin_set_item_init
char *jbin_set_item(UDF_INIT *initid, UDF_ARGS *args, char *result,
@@ -5103,8 +5114,8 @@ my_bool jbin_file_init(UDF_INIT *initid, UDF_ARGS *args, char *message)
fl = GetFileLength(args->args[0]);
reslen += fl;
more += fl * M;
- memlen += more;
- return JsonInit(initid, args, message, true, reslen, memlen);
+//memlen += more;
+ return JsonInit(initid, args, message, true, reslen, memlen, more);
} // end of jbin_file_init
char *jbin_file(UDF_INIT *initid, UDF_ARGS *args, char *result,
diff --git a/storage/connect/mycat.cc b/storage/connect/mycat.cc
index 497fe5e1aa8..1fcd8ac78da 100644
--- a/storage/connect/mycat.cc
+++ b/storage/connect/mycat.cc
@@ -1,4 +1,4 @@
-/* Copyright (C) Olivier Bertrand 2004 - 2016
+/* Copyright (C) Olivier Bertrand 2004 - 2017
This program is free software; you can redistribute it and/or modify
it under the terms of the GNU General Public License as published by
@@ -11,14 +11,14 @@
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 */
+ Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02111-1301 USA */
/*************** Mycat CC Program Source Code File (.CC) ***************/
/* PROGRAM NAME: MYCAT */
/* ------------- */
-/* Version 1.5 */
+/* Version 1.6 */
/* */
-/* Author: Olivier Bertrand 2012 - 2016 */
+/* Author: Olivier Bertrand 2012 - 2017 */
/* */
/* WHAT THIS PROGRAM DOES: */
/* ----------------------- */
@@ -58,9 +58,10 @@
#endif // UNIX
#include "global.h"
#include "plgdbsem.h"
-#include "reldef.h"
-#include "tabcol.h"
+//#include "reldef.h"
#include "xtable.h"
+#include "tabext.h"
+#include "tabcol.h"
#include "filamtxt.h"
#include "tabdos.h"
#include "tabfmt.h"
@@ -559,13 +560,13 @@ PRELDEF MYCAT::MakeTableDesc(PGLOBAL g, PTABLE tablep, LPCSTR am)
case TAB_XML: tdp= new(g) XMLDEF; break;
#endif // XML_SUPPORT
#if defined(VCT_SUPPORT)
- case TAB_VEC: tdp = new(g)VCTDEF; break;
+ case TAB_VEC: tdp = new(g) VCTDEF; break;
#endif // VCT_SUPPORT
#if defined(ODBC_SUPPORT)
case TAB_ODBC: tdp= new(g) ODBCDEF; break;
#endif // ODBC_SUPPORT
#if defined(JDBC_SUPPORT)
- case TAB_JDBC: tdp= new(g)JDBCDEF; break;
+ case TAB_JDBC: tdp= new(g) JDBCDEF; break;
#endif // JDBC_SUPPORT
#if defined(__WIN__)
case TAB_MAC: tdp= new(g) MACDEF; break;
diff --git a/storage/connect/mycat.h b/storage/connect/mycat.h
index 663b68fd4b9..a3682b31f17 100644
--- a/storage/connect/mycat.h
+++ b/storage/connect/mycat.h
@@ -11,7 +11,7 @@
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 */
+ Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02111-1301 USA */
/**************** MYCAT H Declares Source Code File (.H) ***************/
/* Name: MYCAT.H Version 2.3 */
diff --git a/storage/connect/myconn.cpp b/storage/connect/myconn.cpp
index 644ca019e4a..d05254a32a6 100644
--- a/storage/connect/myconn.cpp
+++ b/storage/connect/myconn.cpp
@@ -1,11 +1,11 @@
/************** MyConn C++ Program Source Code File (.CPP) **************/
/* PROGRAM NAME: MYCONN */
/* ------------- */
-/* Version 1.8 */
+/* Version 1.9 */
/* */
/* COPYRIGHT: */
/* ---------- */
-/* (C) Copyright to the author Olivier BERTRAND 2007-2016 */
+/* (C) Copyright to the author Olivier BERTRAND 2007-2017 */
/* */
/* WHAT THIS PROGRAM DOES: */
/* ----------------------- */
@@ -375,10 +375,18 @@ PQRYRES SrcColumns(PGLOBAL g, const char *host, const char *db,
if (!port)
port = mysqld_port;
- if (!strnicmp(srcdef, "select ", 7)) {
- query = (char *)PlugSubAlloc(g, NULL, strlen(srcdef) + 9);
- strcat(strcpy(query, srcdef), " LIMIT 0");
- } else
+ if (!strnicmp(srcdef, "select ", 7) || strstr(srcdef, "%s")) {
+ query = (char *)PlugSubAlloc(g, NULL, strlen(srcdef) + 10);
+
+ if (strstr(srcdef, "%s"))
+ sprintf(query, srcdef, "1=1"); // dummy where clause
+ else
+ strcpy(query, srcdef);
+
+ if (!strnicmp(srcdef, "select ", 7))
+ strcat(query, " LIMIT 0");
+
+ } else
query = (char *)srcdef;
// Open a MySQL connection for this table
diff --git a/storage/connect/mysql-test/connect/r/xml_zip.result b/storage/connect/mysql-test/connect/r/xml_zip.result
new file mode 100644
index 00000000000..f176149c53f
--- /dev/null
+++ b/storage/connect/mysql-test/connect/r/xml_zip.result
@@ -0,0 +1,98 @@
+Warnings:
+Warning 1105 No file name. Table will use t1.xml
+#
+# Testing zipped XML tables
+#
+CREATE TABLE t1 (
+ISBN CHAR(13) NOT NULL FIELD_FORMAT='@',
+LANG CHAR(2) NOT NULL FIELD_FORMAT='@',
+SUBJECT CHAR(12) NOT NULL FIELD_FORMAT='@',
+AUTHOR_FIRSTNAME CHAR(15) NOT NULL FIELD_FORMAT='AUTHOR/FIRSTNAME',
+AUTHOR_LASTNAME CHAR(8) NOT NULL FIELD_FORMAT='AUTHOR/LASTNAME',
+TRANSLATOR_PREFIX CHAR(24) DEFAULT NULL FIELD_FORMAT='TRANSLATOR/@PREFIX',
+TRANSLATOR_FIRSTNAME CHAR(6) DEFAULT NULL FIELD_FORMAT='TRANSLATOR/FIRSTNAME',
+TRANSLATOR_LASTNAME CHAR(6) DEFAULT NULL FIELD_FORMAT='TRANSLATOR/LASTNAME',
+TITLE CHAR(30) NOT NULL,
+PUBLISHER_NAME CHAR(15) NOT NULL FIELD_FORMAT='PUBLISHER/NAME',
+PUBLISHER_PLACE CHAR(5) NOT NULL FIELD_FORMAT='PUBLISHER/PLACE',
+DATEPUB CHAR(4) NOT NULL
+) ENGINE=CONNECT TABLE_TYPE=XML FILE_NAME='xsample2.zip' ZIPPED=YES
+OPTION_LIST='entry=xsample2.xml,load=xsample2.xml,rownode=BOOK,xmlsup=libxml2,expand=1,mulnode=AUTHOR';
+SELECT * FROM t1;
+ISBN 9782212090819
+LANG fr
+SUBJECT applications
+AUTHOR_FIRSTNAME Jean-Christophe
+AUTHOR_LASTNAME Bernadac
+TRANSLATOR_PREFIX NULL
+TRANSLATOR_FIRSTNAME NULL
+TRANSLATOR_LASTNAME NULL
+TITLE Construire une application XML
+PUBLISHER_NAME Eyrolles
+PUBLISHER_PLACE Paris
+DATEPUB 1999
+ISBN 9782212090819
+LANG fr
+SUBJECT applications
+AUTHOR_FIRSTNAME François
+AUTHOR_LASTNAME Knab
+TRANSLATOR_PREFIX NULL
+TRANSLATOR_FIRSTNAME NULL
+TRANSLATOR_LASTNAME NULL
+TITLE Construire une application XML
+PUBLISHER_NAME Eyrolles
+PUBLISHER_PLACE Paris
+DATEPUB 1999
+ISBN 9782840825685
+LANG fr
+SUBJECT applications
+AUTHOR_FIRSTNAME William J.
+AUTHOR_LASTNAME Pardi
+TRANSLATOR_PREFIX adapté de l'anglais par
+TRANSLATOR_FIRSTNAME James
+TRANSLATOR_LASTNAME Guerin
+TITLE XML en Action
+PUBLISHER_NAME Microsoft Press
+PUBLISHER_PLACE Paris
+DATEPUB 1999
+ISBN 9782212090529
+LANG fr
+SUBJECT général
+AUTHOR_FIRSTNAME Alain
+AUTHOR_LASTNAME Michard
+TRANSLATOR_PREFIX NULL
+TRANSLATOR_FIRSTNAME NULL
+TRANSLATOR_LASTNAME NULL
+TITLE XML, Langage et Applications
+PUBLISHER_NAME Eyrolles
+PUBLISHER_PLACE Paris
+DATEPUB 2003
+CREATE TABLE t2
+ENGINE=CONNECT TABLE_TYPE=XML FILE_NAME='xsample2.zip' ZIPPED=YES
+OPTION_LIST='xmlsup=libxml2';
+SELECT * FROM t2;
+ISBN 9782212090819
+LANG fr
+SUBJECT applications
+AUTHOR Jean-Christophe Bernadac
+TRANSLATOR NULL
+TITLE Construire une application XML
+PUBLISHER Eyrolles Paris
+DATEPUB 1999
+ISBN 9782840825685
+LANG fr
+SUBJECT applications
+AUTHOR William J. Pardi
+TRANSLATOR James Guerin
+TITLE XML en Action
+PUBLISHER Microsoft Press Paris
+DATEPUB 1999
+ISBN 9782212090529
+LANG fr
+SUBJECT général
+AUTHOR Alain Michard
+TRANSLATOR NULL
+TITLE XML, Langage et Applications
+PUBLISHER Eyrolles Paris
+DATEPUB 2003
+DROP TABLE t1,t2;
diff --git a/storage/connect/mysql-test/connect/r/zip.result b/storage/connect/mysql-test/connect/r/zip.result
new file mode 100644
index 00000000000..c03b27bd428
--- /dev/null
+++ b/storage/connect/mysql-test/connect/r/zip.result
@@ -0,0 +1,240 @@
+#
+# Testing zipped DOS tables
+#
+CREATE TABLE t1 (
+digit INT(3) NOT NULL,
+letter CHAR(16) NOT NULL)
+ENGINE=CONNECT TABLE_TYPE=DOS FILE_NAME='newdos.zip'
+OPTION_LIST='ENTRY=new1.dos' ZIPPED=1;
+INSERT INTO t1 VALUES(1,'One'),(2,'Two'),(3,'Three'),(4,'Four'),(5,'Five'),(6,'Six'),(7,'Seven'),(8,'Eight'),(9,'Nine'),(10,'Ten');
+SELECT * FROM t1;
+digit letter
+1 One
+2 Two
+3 Three
+4 Four
+5 Five
+6 Six
+7 Seven
+8 Eight
+9 Nine
+10 Ten
+CREATE TABLE t2 (
+digit INT(3) NOT NULL,
+letter CHAR(16) NOT NULL)
+ENGINE=CONNECT TABLE_TYPE=DOS FILE_NAME='newdos.zip'
+OPTION_LIST='ENTRY=new2.dos,APPEND=1' ZIPPED=1;
+INSERT INTO t2 VALUES(11,'Eleven'),(12,'Twelve'),(13,'Thirteen'),(14,'Fourteen'),(15,'Fiften'),(16,'Sixteen'),(17,'Seventeen'),(18,'Eighteen'),(19,'Nineteen'),(20,'Twenty');
+SELECT * FROM t2;
+digit letter
+11 Eleven
+12 Twelve
+13 Thirteen
+14 Fourteen
+15 Fiften
+16 Sixteen
+17 Seventeen
+18 Eighteen
+19 Nineteen
+20 Twenty
+CREATE TABLE t3 (
+digit INT(3) NOT NULL,
+letter CHAR(16) NOT NULL)
+ENGINE=CONNECT TABLE_TYPE=DOS FILE_NAME='newdos.zip'
+OPTION_LIST='MULENTRIES=1' ZIPPED=1;
+SELECT * FROM t3;
+digit letter
+1 One
+2 Two
+3 Three
+4 Four
+5 Five
+6 Six
+7 Seven
+8 Eight
+9 Nine
+10 Ten
+11 Eleven
+12 Twelve
+13 Thirteen
+14 Fourteen
+15 Fiften
+16 Sixteen
+17 Seventeen
+18 Eighteen
+19 Nineteen
+20 Twenty
+CREATE TABLE t4 (
+fn VARCHAR(256)NOT NULL,
+cmpsize BIGINT NOT NULL FLAG=1,
+uncsize BIGINT NOT NULL FLAG=2,
+method INT NOT NULL FLAG=3)
+ENGINE=CONNECT TABLE_TYPE=ZIP FILE_NAME='newdos.zip';
+SELECT * FROM t4;
+fn cmpsize uncsize method
+new1.dos 67 79 8
+new2.dos 77 112 8
+DROP TABLE t1,t2,t3,t4;
+#
+# Testing zipped CSV tables
+#
+CREATE TABLE t1 (
+digit INT(3) NOT NULL,
+letter CHAR(16) NOT NULL)
+ENGINE=CONNECT TABLE_TYPE=CSV FILE_NAME='newcsv.zip'
+OPTION_LIST='ENTRY=new1.csv' HEADER=1 ZIPPED=1;
+INSERT INTO t1 VALUES(1,'One'),(2,'Two'),(3,'Three'),(4,'Four'),(5,'Five'),(6,'Six'),(7,'Seven'),(8,'Eight'),(9,'Nine'),(10,'Ten');
+SELECT * FROM t1;
+digit letter
+1 One
+2 Two
+3 Three
+4 Four
+5 Five
+6 Six
+7 Seven
+8 Eight
+9 Nine
+10 Ten
+CREATE TABLE td1
+ENGINE=CONNECT TABLE_TYPE=CSV FILE_NAME='newcsv.zip'
+OPTION_LIST='ENTRY=new1.csv' HEADER=1 ZIPPED=1;
+SELECT * FROM td1;
+digit letter
+1 One
+2 Two
+3 Three
+4 Four
+5 Five
+6 Six
+7 Seven
+8 Eight
+9 Nine
+10 Ten
+DROP TABLE td1;
+CREATE TABLE t2 (
+digit INT(3) NOT NULL,
+letter CHAR(16) NOT NULL)
+ENGINE=CONNECT TABLE_TYPE=CSV FILE_NAME='newcsv.zip'
+OPTION_LIST='ENTRY=new2.csv,APPEND=1' HEADER=1 ZIPPED=1;
+INSERT INTO t2 VALUES(11,'Eleven'),(12,'Twelve'),(13,'Thirteen'),(14,'Fourteen'),(15,'Fiften'),(16,'Sixteen'),(17,'Seventeen'),(18,'Eighteen'),(19,'Nineteen'),(20,'Twenty');
+SELECT * FROM t2;
+digit letter
+11 Eleven
+12 Twelve
+13 Thirteen
+14 Fourteen
+15 Fiften
+16 Sixteen
+17 Seventeen
+18 Eighteen
+19 Nineteen
+20 Twenty
+CREATE TABLE t3
+ENGINE=CONNECT TABLE_TYPE=CSV FILE_NAME='newcsv.zip'
+OPTION_LIST='MULENTRIES=1' HEADER=1 ZIPPED=1;
+SELECT * FROM t3;
+digit letter
+1 One
+2 Two
+3 Three
+4 Four
+5 Five
+6 Six
+7 Seven
+8 Eight
+9 Nine
+10 Ten
+11 Eleven
+12 Twelve
+13 Thirteen
+14 Fourteen
+15 Fiften
+16 Sixteen
+17 Seventeen
+18 Eighteen
+19 Nineteen
+20 Twenty
+CREATE TABLE t4 (
+fn VARCHAR(256)NOT NULL,
+cmpsize BIGINT NOT NULL FLAG=1,
+uncsize BIGINT NOT NULL FLAG=2,
+method INT NOT NULL FLAG=3)
+ENGINE=CONNECT TABLE_TYPE=ZIP FILE_NAME='newcsv.zip';
+SELECT * FROM t4;
+fn cmpsize uncsize method
+new1.csv 79 83 8
+new2.csv 94 125 8
+DROP TABLE t1,t2,t3,t4;
+#
+# Testing zipped JSON tables
+#
+CREATE TABLE t1 (
+_id INT(2) NOT NULL,
+name_first CHAR(9) NOT NULL FIELD_FORMAT='name:first',
+name_aka CHAR(4) DEFAULT NULL FIELD_FORMAT='name:aka',
+name_last CHAR(10) NOT NULL FIELD_FORMAT='name:last',
+title CHAR(12) DEFAULT NULL,
+birth CHAR(20) DEFAULT NULL,
+death CHAR(20) DEFAULT NULL,
+contribs CHAR(7) NOT NULL FIELD_FORMAT='contribs:',
+awards_award CHAR(42) DEFAULT NULL FIELD_FORMAT='awards::award',
+awards_year CHAR(4) DEFAULT NULL FIELD_FORMAT='awards::year',
+awards_by CHAR(38) DEFAULT NULL FIELD_FORMAT='awards::by'
+) ENGINE=CONNECT TABLE_TYPE=JSON FILE_NAME='bios.zip' OPTION_LIST='ENTRY=bios.json,LOAD=bios.json' ZIPPED=YES;
+SELECT * FROM t1;
+_id name_first name_aka name_last title birth death contribs awards_award awards_year awards_by
+1 John NULL Backus NULL 1924-12-03T05:00:00Z 2007-03-17T04:00:00Z Fortran W.W. McDowell Award 1967 IEEE Computer Society
+2 John NULL McCarthy NULL 1927-09-04T04:00:00Z 2011-12-24T05:00:00Z Lisp Turing Award 1971 ACM
+3 Grace NULL Hopper Rear Admiral 1906-12-09T05:00:00Z 1992-01-01T05:00:00Z UNIVAC Computer Sciences Man of the Year 1969 Data Processing Management Association
+4 Kristen NULL Nygaard NULL 1926-08-27T04:00:00Z 2002-08-10T04:00:00Z OOP Rosing Prize 1999 Norwegian Data Association
+5 Ole-Johan NULL Dahl NULL 1931-10-12T04:00:00Z 2002-06-29T04:00:00Z OOP Rosing Prize 1999 Norwegian Data Association
+6 Guido NULL van Rossum NULL 1956-01-31T05:00:00Z NULL Python Award for the Advancement of Free Software 2001 Free Software Foundation
+7 Dennis NULL Ritchie NULL 1941-09-09T04:00:00Z 2011-10-12T04:00:00Z UNIX Turing Award 1983 ACM
+8 Yukihiro Matz Matsumoto NULL 1965-04-14T04:00:00Z NULL Ruby Award for the Advancement of Free Software 2011 Free Software Foundation
+9 James NULL Gosling NULL 1955-05-19T04:00:00Z NULL Java The Economist Innovation Award 2002 The Economist
+10 Martin NULL Odersky NULL NULL NULL Scala NULL NULL NULL
+CREATE TABLE t2
+ENGINE=CONNECT TABLE_TYPE=JSON FILE_NAME='bios.zip' ZIPPED=1
+OPTION_LIST='LEVEL=5';
+SELECT * FROM t2;
+_id name_first name_aka name_last title birth death contribs awards_award awards_year awards_by
+1 John NULL Backus NULL 1924-12-03T05:00:00Z 2007-03-17T04:00:00Z Fortran W.W. McDowell Award 1967 IEEE Computer Society
+2 John NULL McCarthy NULL 1927-09-04T04:00:00Z 2011-12-24T05:00:00Z Lisp Turing Award 1971 ACM
+3 Grace NULL Hopper Rear Admiral 1906-12-09T05:00:00Z 1992-01-01T05:00:00Z UNIVAC Computer Sciences Man of the Year 1969 Data Processing Management Association
+4 Kristen NULL Nygaard NULL 1926-08-27T04:00:00Z 2002-08-10T04:00:00Z OOP Rosing Prize 1999 Norwegian Data Association
+5 Ole-Johan NULL Dahl NULL 1931-10-12T04:00:00Z 2002-06-29T04:00:00Z OOP Rosing Prize 1999 Norwegian Data Association
+6 Guido NULL van Rossum NULL 1956-01-31T05:00:00Z NULL Python Award for the Advancement of Free Software 2001 Free Software Foundation
+7 Dennis NULL Ritchie NULL 1941-09-09T04:00:00Z 2011-10-12T04:00:00Z UNIX Turing Award 1983 ACM
+8 Yukihiro Matz Matsumoto NULL 1965-04-14T04:00:00Z NULL Ruby Award for the Advancement of Free Software 2011 Free Software Foundation
+9 James NULL Gosling NULL 1955-05-19T04:00:00Z NULL Java The Economist Innovation Award 2002 The Economist
+10 Martin NULL Odersky NULL NULL NULL Scala NULL NULL NULL
+CREATE TABLE t3 (
+_id INT(2) NOT NULL,
+firstname CHAR(9) NOT NULL FIELD_FORMAT='name:first',
+aka CHAR(4) DEFAULT NULL FIELD_FORMAT='name:aka',
+lastname CHAR(10) NOT NULL FIELD_FORMAT='name:last',
+title CHAR(12) DEFAULT NULL,
+birth date DEFAULT NULL date_format="YYYY-DD-MM'T'hh:mm:ss'Z'",
+death date DEFAULT NULL date_format="YYYY-DD-MM'T'hh:mm:ss'Z'",
+contribs CHAR(64) NOT NULL FIELD_FORMAT='contribs:[", "]',
+award CHAR(42) DEFAULT NULL FIELD_FORMAT='awards:[x]:award',
+year CHAR(4) DEFAULT NULL FIELD_FORMAT='awards:[x]:year',
+`by` CHAR(38) DEFAULT NULL FIELD_FORMAT='awards:[x]:by'
+) ENGINE=CONNECT TABLE_TYPE='json' FILE_NAME='bios.zip' ZIPPED=YES;
+SELECT * FROM t3 WHERE _id = 1;
+_id firstname aka lastname title birth death contribs award year by
+1 John NULL Backus NULL 1924-03-12 2008-05-03 Fortran, ALGOL, Backus-Naur Form, FP W.W. McDowell Award 1967 IEEE Computer Society
+1 John NULL Backus NULL 1924-03-12 2008-05-03 Fortran, ALGOL, Backus-Naur Form, FP National Medal of Science 1975 National Science Foundation
+1 John NULL Backus NULL 1924-03-12 2008-05-03 Fortran, ALGOL, Backus-Naur Form, FP Turing Award 1977 ACM
+1 John NULL Backus NULL 1924-03-12 2008-05-03 Fortran, ALGOL, Backus-Naur Form, FP Draper Prize 1993 National Academy of Engineering
+CREATE TABLE t4 (
+fn VARCHAR(256)NOT NULL,
+cmpsize BIGINT NOT NULL FLAG=1,
+uncsize BIGINT NOT NULL FLAG=2,
+method INT NOT NULL FLAG=3)
+ENGINE=CONNECT TABLE_TYPE=ZIP FILE_NAME='bios.zip';
+SELECT * FROM t4;
+fn cmpsize uncsize method
+bios.json 1096 6848 8
+DROP TABLE t1,t2,t3,t4;
diff --git a/storage/connect/mysql-test/connect/std_data/bios.json b/storage/connect/mysql-test/connect/std_data/bios.json
new file mode 100644
index 00000000000..85e4ecb933f
--- /dev/null
+++ b/storage/connect/mysql-test/connect/std_data/bios.json
@@ -0,0 +1,273 @@
+[
+ {
+ "_id" : 1,
+ "name" : {
+ "first" : "John",
+ "last" : "Backus"
+ },
+ "birth" : "1924-12-03T05:00:00Z",
+ "death" : "2007-03-17T04:00:00Z",
+ "contribs" : [
+ "Fortran",
+ "ALGOL",
+ "Backus-Naur Form",
+ "FP"
+ ],
+ "awards" : [
+ {
+ "award" : "W.W. McDowell Award",
+ "year" : 1967,
+ "by" : "IEEE Computer Society"
+ },
+ {
+ "award" : "National Medal of Science",
+ "year" : 1975,
+ "by" : "National Science Foundation"
+ },
+ {
+ "award" : "Turing Award",
+ "year" : 1977,
+ "by" : "ACM"
+ },
+ {
+ "award" : "Draper Prize",
+ "year" : 1993,
+ "by" : "National Academy of Engineering"
+ }
+ ]
+ },
+ {
+ "_id" : 2,
+ "name" : {
+ "first" : "John",
+ "last" : "McCarthy"
+ },
+ "birth" : "1927-09-04T04:00:00Z",
+ "death" : "2011-12-24T05:00:00Z",
+ "contribs" : [
+ "Lisp",
+ "Artificial Intelligence",
+ "ALGOL"
+ ],
+ "awards" : [
+ {
+ "award" : "Turing Award",
+ "year" : 1971,
+ "by" : "ACM"
+ },
+ {
+ "award" : "Kyoto Prize",
+ "year" : 1988,
+ "by" : "Inamori Foundation"
+ },
+ {
+ "award" : "National Medal of Science",
+ "year" : 1990,
+ "by" : "National Science Foundation"
+ }
+ ]
+ },
+ {
+ "_id" : 3,
+ "name" : {
+ "first" : "Grace",
+ "last" : "Hopper"
+ },
+ "title" : "Rear Admiral",
+ "birth" : "1906-12-09T05:00:00Z",
+ "death" : "1992-01-01T05:00:00Z",
+ "contribs" : [
+ "UNIVAC",
+ "compiler",
+ "FLOW-MATIC",
+ "COBOL"
+ ],
+ "awards" : [
+ {
+ "award" : "Computer Sciences Man of the Year",
+ "year" : 1969,
+ "by" : "Data Processing Management Association"
+ },
+ {
+ "award" : "Distinguished Fellow",
+ "year" : 1973,
+ "by" : " British Computer Society"
+ },
+ {
+ "award" : "W. W. McDowell Award",
+ "year" : 1976,
+ "by" : "IEEE Computer Society"
+ },
+ {
+ "award" : "National Medal of Technology",
+ "year" : 1991,
+ "by" : "United States"
+ }
+ ]
+ },
+ {
+ "_id" : 4,
+ "name" : {
+ "first" : "Kristen",
+ "last" : "Nygaard"
+ },
+ "birth" : "1926-08-27T04:00:00Z",
+ "death" : "2002-08-10T04:00:00Z",
+ "contribs" : [
+ "OOP",
+ "Simula"
+ ],
+ "awards" : [
+ {
+ "award" : "Rosing Prize",
+ "year" : 1999,
+ "by" : "Norwegian Data Association"
+ },
+ {
+ "award" : "Turing Award",
+ "year" : 2001,
+ "by" : "ACM"
+ },
+ {
+ "award" : "IEEE John von Neumann Medal",
+ "year" : 2001,
+ "by" : "IEEE"
+ }
+ ]
+ },
+ {
+ "_id" : 5,
+ "name" : {
+ "first" : "Ole-Johan",
+ "last" : "Dahl"
+ },
+ "birth" : "1931-10-12T04:00:00Z",
+ "death" : "2002-06-29T04:00:00Z",
+ "contribs" : [
+ "OOP",
+ "Simula"
+ ],
+ "awards" : [
+ {
+ "award" : "Rosing Prize",
+ "year" : 1999,
+ "by" : "Norwegian Data Association"
+ },
+ {
+ "award" : "Turing Award",
+ "year" : 2001,
+ "by" : "ACM"
+ },
+ {
+ "award" : "IEEE John von Neumann Medal",
+ "year" : 2001,
+ "by" : "IEEE"
+ }
+ ]
+ },
+ {
+ "_id" : 6,
+ "name" : {
+ "first" : "Guido",
+ "last" : "van Rossum"
+ },
+ "birth" : "1956-01-31T05:00:00Z",
+ "contribs" : [
+ "Python"
+ ],
+ "awards" : [
+ {
+ "award" : "Award for the Advancement of Free Software",
+ "year" : 2001,
+ "by" : "Free Software Foundation"
+ },
+ {
+ "award" : "NLUUG Award",
+ "year" : 2003,
+ "by" : "NLUUG"
+ }
+ ]
+ },
+ {
+ "_id" : 7,
+ "name" : {
+ "first" : "Dennis",
+ "last" : "Ritchie"
+ },
+ "birth" : "1941-09-09T04:00:00Z",
+ "death" : "2011-10-12T04:00:00Z",
+ "contribs" : [
+ "UNIX",
+ "C"
+ ],
+ "awards" : [
+ {
+ "award" : "Turing Award",
+ "year" : 1983,
+ "by" : "ACM"
+ },
+ {
+ "award" : "National Medal of Technology",
+ "year" : 1998,
+ "by" : "United States"
+ },
+ {
+ "award" : "Japan Prize",
+ "year" : 2011,
+ "by" : "The Japan Prize Foundation"
+ }
+ ]
+ },
+ {
+ "_id" : 8,
+ "name" : {
+ "first" : "Yukihiro",
+ "aka" : "Matz",
+ "last" : "Matsumoto"
+ },
+ "birth" : "1965-04-14T04:00:00Z",
+ "contribs" : [
+ "Ruby"
+ ],
+ "awards" : [
+ {
+ "award" : "Award for the Advancement of Free Software",
+ "year" : "2011",
+ "by" : "Free Software Foundation"
+ }
+ ]
+ },
+ {
+ "_id" : 9,
+ "name" : {
+ "first" : "James",
+ "last" : "Gosling"
+ },
+ "birth" : "1955-05-19T04:00:00Z",
+ "contribs" : [
+ "Java"
+ ],
+ "awards" : [
+ {
+ "award" : "The Economist Innovation Award",
+ "year" : 2002,
+ "by" : "The Economist"
+ },
+ {
+ "award" : "Officer of the Order of Canada",
+ "year" : 2007,
+ "by" : "Canada"
+ }
+ ]
+ },
+ {
+ "_id" : 10,
+ "name" : {
+ "first" : "Martin",
+ "last" : "Odersky"
+ },
+ "contribs" : [
+ "Scala"
+ ]
+ }
+]
diff --git a/storage/connect/mysql-test/connect/std_data/xsample2.xml b/storage/connect/mysql-test/connect/std_data/xsample2.xml
new file mode 100644
index 00000000000..35295844370
--- /dev/null
+++ b/storage/connect/mysql-test/connect/std_data/xsample2.xml
@@ -0,0 +1,47 @@
+<?xml version="1.0" encoding="UTF-8"?>
+<BIBLIO SUBJECT="XML">
+ <BOOK ISBN="9782212090819" LANG="fr" SUBJECT="applications">
+ <AUTHOR>
+ <FIRSTNAME>Jean-Christophe</FIRSTNAME>
+ <LASTNAME>Bernadac</LASTNAME>
+ </AUTHOR>
+ <AUTHOR>
+ <FIRSTNAME>François</FIRSTNAME>
+ <LASTNAME>Knab</LASTNAME>
+ </AUTHOR>
+ <TITLE>Construire une application XML</TITLE>
+ <PUBLISHER>
+ <NAME>Eyrolles</NAME>
+ <PLACE>Paris</PLACE>
+ </PUBLISHER>
+ <DATEPUB>1999</DATEPUB>
+ </BOOK>
+ <BOOK ISBN="9782840825685" LANG="fr" SUBJECT="applications">
+ <AUTHOR>
+ <FIRSTNAME>William J.</FIRSTNAME>
+ <LASTNAME>Pardi</LASTNAME>
+ </AUTHOR>
+ <TRANSLATOR PREFIX="adapté de l'anglais par">
+ <FIRSTNAME>James</FIRSTNAME>
+ <LASTNAME>Guerin</LASTNAME>
+ </TRANSLATOR>
+ <TITLE>XML en Action</TITLE>
+ <PUBLISHER>
+ <NAME>Microsoft Press</NAME>
+ <PLACE>Paris</PLACE>
+ </PUBLISHER>
+ <DATEPUB>1999</DATEPUB>
+ </BOOK>
+ <BOOK ISBN="9782212090529" LANG="fr" SUBJECT="général">
+ <AUTHOR>
+ <FIRSTNAME>Alain</FIRSTNAME>
+ <LASTNAME>Michard</LASTNAME>
+ </AUTHOR>
+ <TITLE>XML, Langage et Applications</TITLE>
+ <PUBLISHER>
+ <NAME>Eyrolles</NAME>
+ <PLACE>Paris</PLACE>
+ </PUBLISHER>
+ <DATEPUB>2003</DATEPUB>
+ </BOOK>
+</BIBLIO>
diff --git a/storage/connect/mysql-test/connect/t/have_zip.inc b/storage/connect/mysql-test/connect/t/have_zip.inc
new file mode 100644
index 00000000000..d1283fc1d38
--- /dev/null
+++ b/storage/connect/mysql-test/connect/t/have_zip.inc
@@ -0,0 +1,19 @@
+--disable_query_log
+--error 0,ER_UNKNOWN_ERROR
+CREATE TABLE t1 (a CHAR(10)) ENGINE=CONNECT TABLE_TYPE=ZIP FILE_NAME='test.zip';
+if ($mysql_errno)
+{
+ Skip No ZIP support;
+}
+#if (!`SELECT count(*) FROM INFORMATION_SCHEMA.TABLES
+# WHERE TABLE_SCHEMA='test' AND TABLE_NAME='t1'
+# AND ENGINE='CONNECT'
+# AND CREATE_OPTIONS LIKE '%`table_type`=ZIP%'
+# AND CREATE OPTIONS LIKE "%`file_name`='test.zip'%"`)
+#{
+# DROP TABLE IF EXISTS t1;
+# Skip Need ZIP support;
+#}
+DROP TABLE t1;
+--enable_query_log
+
diff --git a/storage/connect/mysql-test/connect/t/xml_zip.test b/storage/connect/mysql-test/connect/t/xml_zip.test
new file mode 100644
index 00000000000..d8c7894f861
--- /dev/null
+++ b/storage/connect/mysql-test/connect/t/xml_zip.test
@@ -0,0 +1,41 @@
+--source have_zip.inc
+--source have_libxml2.inc
+
+let $MYSQLD_DATADIR= `select @@datadir`;
+
+--vertical_results
+
+--copy_file $MTR_SUITE_DIR/std_data/xsample2.xml $MYSQLD_DATADIR/test/xsample2.xml
+
+--echo #
+--echo # Testing zipped XML tables
+--echo #
+CREATE TABLE t1 (
+ISBN CHAR(13) NOT NULL FIELD_FORMAT='@',
+LANG CHAR(2) NOT NULL FIELD_FORMAT='@',
+SUBJECT CHAR(12) NOT NULL FIELD_FORMAT='@',
+AUTHOR_FIRSTNAME CHAR(15) NOT NULL FIELD_FORMAT='AUTHOR/FIRSTNAME',
+AUTHOR_LASTNAME CHAR(8) NOT NULL FIELD_FORMAT='AUTHOR/LASTNAME',
+TRANSLATOR_PREFIX CHAR(24) DEFAULT NULL FIELD_FORMAT='TRANSLATOR/@PREFIX',
+TRANSLATOR_FIRSTNAME CHAR(6) DEFAULT NULL FIELD_FORMAT='TRANSLATOR/FIRSTNAME',
+TRANSLATOR_LASTNAME CHAR(6) DEFAULT NULL FIELD_FORMAT='TRANSLATOR/LASTNAME',
+TITLE CHAR(30) NOT NULL,
+PUBLISHER_NAME CHAR(15) NOT NULL FIELD_FORMAT='PUBLISHER/NAME',
+PUBLISHER_PLACE CHAR(5) NOT NULL FIELD_FORMAT='PUBLISHER/PLACE',
+DATEPUB CHAR(4) NOT NULL
+) ENGINE=CONNECT TABLE_TYPE=XML FILE_NAME='xsample2.zip' ZIPPED=YES
+OPTION_LIST='entry=xsample2.xml,load=xsample2.xml,rownode=BOOK,xmlsup=libxml2,expand=1,mulnode=AUTHOR';
+SELECT * FROM t1;
+
+#testing discovery
+CREATE TABLE t2
+ENGINE=CONNECT TABLE_TYPE=XML FILE_NAME='xsample2.zip' ZIPPED=YES
+OPTION_LIST='xmlsup=libxml2';
+SELECT * FROM t2;
+DROP TABLE t1,t2;
+
+#
+# Clean up
+#
+--remove_file $MYSQLD_DATADIR/test/xsample2.xml
+--remove_file $MYSQLD_DATADIR/test/xsample2.zip
diff --git a/storage/connect/mysql-test/connect/t/zip.test b/storage/connect/mysql-test/connect/t/zip.test
new file mode 100644
index 00000000000..a4892e9ed4e
--- /dev/null
+++ b/storage/connect/mysql-test/connect/t/zip.test
@@ -0,0 +1,136 @@
+--source have_zip.inc
+let $MYSQLD_DATADIR= `select @@datadir`;
+
+--copy_file $MTR_SUITE_DIR/std_data/bios.json $MYSQLD_DATADIR/test/bios.json
+
+--echo #
+--echo # Testing zipped DOS tables
+--echo #
+CREATE TABLE t1 (
+digit INT(3) NOT NULL,
+letter CHAR(16) NOT NULL)
+ENGINE=CONNECT TABLE_TYPE=DOS FILE_NAME='newdos.zip'
+OPTION_LIST='ENTRY=new1.dos' ZIPPED=1;
+INSERT INTO t1 VALUES(1,'One'),(2,'Two'),(3,'Three'),(4,'Four'),(5,'Five'),(6,'Six'),(7,'Seven'),(8,'Eight'),(9,'Nine'),(10,'Ten');
+SELECT * FROM t1;
+
+CREATE TABLE t2 (
+digit INT(3) NOT NULL,
+letter CHAR(16) NOT NULL)
+ENGINE=CONNECT TABLE_TYPE=DOS FILE_NAME='newdos.zip'
+OPTION_LIST='ENTRY=new2.dos,APPEND=1' ZIPPED=1;
+INSERT INTO t2 VALUES(11,'Eleven'),(12,'Twelve'),(13,'Thirteen'),(14,'Fourteen'),(15,'Fiften'),(16,'Sixteen'),(17,'Seventeen'),(18,'Eighteen'),(19,'Nineteen'),(20,'Twenty');
+SELECT * FROM t2;
+
+CREATE TABLE t3 (
+digit INT(3) NOT NULL,
+letter CHAR(16) NOT NULL)
+ENGINE=CONNECT TABLE_TYPE=DOS FILE_NAME='newdos.zip'
+OPTION_LIST='MULENTRIES=1' ZIPPED=1;
+SELECT * FROM t3;
+
+CREATE TABLE t4 (
+fn VARCHAR(256)NOT NULL,
+cmpsize BIGINT NOT NULL FLAG=1,
+uncsize BIGINT NOT NULL FLAG=2,
+method INT NOT NULL FLAG=3)
+ENGINE=CONNECT TABLE_TYPE=ZIP FILE_NAME='newdos.zip';
+SELECT * FROM t4;
+DROP TABLE t1,t2,t3,t4;
+
+--echo #
+--echo # Testing zipped CSV tables
+--echo #
+CREATE TABLE t1 (
+digit INT(3) NOT NULL,
+letter CHAR(16) NOT NULL)
+ENGINE=CONNECT TABLE_TYPE=CSV FILE_NAME='newcsv.zip'
+OPTION_LIST='ENTRY=new1.csv' HEADER=1 ZIPPED=1;
+INSERT INTO t1 VALUES(1,'One'),(2,'Two'),(3,'Three'),(4,'Four'),(5,'Five'),(6,'Six'),(7,'Seven'),(8,'Eight'),(9,'Nine'),(10,'Ten');
+SELECT * FROM t1;
+
+# Test discovery
+CREATE TABLE td1
+ENGINE=CONNECT TABLE_TYPE=CSV FILE_NAME='newcsv.zip'
+OPTION_LIST='ENTRY=new1.csv' HEADER=1 ZIPPED=1;
+SELECT * FROM td1;
+DROP TABLE td1;
+
+CREATE TABLE t2 (
+digit INT(3) NOT NULL,
+letter CHAR(16) NOT NULL)
+ENGINE=CONNECT TABLE_TYPE=CSV FILE_NAME='newcsv.zip'
+OPTION_LIST='ENTRY=new2.csv,APPEND=1' HEADER=1 ZIPPED=1;
+INSERT INTO t2 VALUES(11,'Eleven'),(12,'Twelve'),(13,'Thirteen'),(14,'Fourteen'),(15,'Fiften'),(16,'Sixteen'),(17,'Seventeen'),(18,'Eighteen'),(19,'Nineteen'),(20,'Twenty');
+SELECT * FROM t2;
+
+CREATE TABLE t3
+ENGINE=CONNECT TABLE_TYPE=CSV FILE_NAME='newcsv.zip'
+OPTION_LIST='MULENTRIES=1' HEADER=1 ZIPPED=1;
+SELECT * FROM t3;
+
+CREATE TABLE t4 (
+fn VARCHAR(256)NOT NULL,
+cmpsize BIGINT NOT NULL FLAG=1,
+uncsize BIGINT NOT NULL FLAG=2,
+method INT NOT NULL FLAG=3)
+ENGINE=CONNECT TABLE_TYPE=ZIP FILE_NAME='newcsv.zip';
+SELECT * FROM t4;
+DROP TABLE t1,t2,t3,t4;
+
+--echo #
+--echo # Testing zipped JSON tables
+--echo #
+CREATE TABLE t1 (
+_id INT(2) NOT NULL,
+name_first CHAR(9) NOT NULL FIELD_FORMAT='name:first',
+name_aka CHAR(4) DEFAULT NULL FIELD_FORMAT='name:aka',
+name_last CHAR(10) NOT NULL FIELD_FORMAT='name:last',
+title CHAR(12) DEFAULT NULL,
+birth CHAR(20) DEFAULT NULL,
+death CHAR(20) DEFAULT NULL,
+contribs CHAR(7) NOT NULL FIELD_FORMAT='contribs:',
+awards_award CHAR(42) DEFAULT NULL FIELD_FORMAT='awards::award',
+awards_year CHAR(4) DEFAULT NULL FIELD_FORMAT='awards::year',
+awards_by CHAR(38) DEFAULT NULL FIELD_FORMAT='awards::by'
+) ENGINE=CONNECT TABLE_TYPE=JSON FILE_NAME='bios.zip' OPTION_LIST='ENTRY=bios.json,LOAD=bios.json' ZIPPED=YES;
+SELECT * FROM t1;
+
+# Test discovery
+CREATE TABLE t2
+ENGINE=CONNECT TABLE_TYPE=JSON FILE_NAME='bios.zip' ZIPPED=1
+OPTION_LIST='LEVEL=5';
+SELECT * FROM t2;
+
+CREATE TABLE t3 (
+_id INT(2) NOT NULL,
+firstname CHAR(9) NOT NULL FIELD_FORMAT='name:first',
+aka CHAR(4) DEFAULT NULL FIELD_FORMAT='name:aka',
+lastname CHAR(10) NOT NULL FIELD_FORMAT='name:last',
+title CHAR(12) DEFAULT NULL,
+birth date DEFAULT NULL date_format="YYYY-DD-MM'T'hh:mm:ss'Z'",
+death date DEFAULT NULL date_format="YYYY-DD-MM'T'hh:mm:ss'Z'",
+contribs CHAR(64) NOT NULL FIELD_FORMAT='contribs:[", "]',
+award CHAR(42) DEFAULT NULL FIELD_FORMAT='awards:[x]:award',
+year CHAR(4) DEFAULT NULL FIELD_FORMAT='awards:[x]:year',
+`by` CHAR(38) DEFAULT NULL FIELD_FORMAT='awards:[x]:by'
+) ENGINE=CONNECT TABLE_TYPE='json' FILE_NAME='bios.zip' ZIPPED=YES;
+SELECT * FROM t3 WHERE _id = 1;
+
+CREATE TABLE t4 (
+fn VARCHAR(256)NOT NULL,
+cmpsize BIGINT NOT NULL FLAG=1,
+uncsize BIGINT NOT NULL FLAG=2,
+method INT NOT NULL FLAG=3)
+ENGINE=CONNECT TABLE_TYPE=ZIP FILE_NAME='bios.zip';
+SELECT * FROM t4;
+DROP TABLE t1,t2,t3,t4;
+
+#
+# Clean up
+#
+--remove_file $MYSQLD_DATADIR/test/newdos.zip
+--remove_file $MYSQLD_DATADIR/test/newcsv.zip
+--remove_file $MYSQLD_DATADIR/test/bios.zip
+--remove_file $MYSQLD_DATADIR/test/bios.json
+
diff --git a/storage/connect/odbconn.cpp b/storage/connect/odbconn.cpp
index 7320f4cc1d9..433e392eace 100644
--- a/storage/connect/odbconn.cpp
+++ b/storage/connect/odbconn.cpp
@@ -35,8 +35,8 @@
#include "global.h"
#include "plgdbsem.h"
#include "xobject.h"
-//#include "kindex.h"
#include "xtable.h"
+#include "tabext.h"
#include "odbccat.h"
#include "tabodbc.h"
#include "plgcnx.h" // For DB types
@@ -413,12 +413,20 @@ PQRYRES ODBCColumns(PGLOBAL g, char *dsn, char *db, char *table,
/**************************************************************************/
PQRYRES ODBCSrcCols(PGLOBAL g, char *dsn, char *src, POPARM sop)
{
+ char *sqry;
ODBConn *ocp = new(g) ODBConn(g, NULL);
if (ocp->Open(dsn, sop, 10) < 1) // openReadOnly + noOdbcDialog
return NULL;
- return ocp->GetMetaData(g, dsn, src);
+ if (strstr(src, "%s")) {
+ // Place holder for an eventual where clause
+ sqry = (char*)PlugSubAlloc(g, NULL, strlen(src) + 3);
+ sprintf(sqry, src, "1=1", "1=1"); // dummy where clause
+ } else
+ sqry = src;
+
+ return ocp->GetMetaData(g, dsn, sqry);
} // end of ODBCSrcCols
#if 0
@@ -1417,7 +1425,7 @@ int ODBConn::ExecDirectSQL(char *sql, ODBCCOL *tocols)
b = true;
if (trace)
- htrc("ExecDirect hstmt=%p %.64s\n", hstmt, sql);
+ htrc("ExecDirect hstmt=%p %.256s\n", hstmt, sql);
if (m_Tdb->Srcdef) {
// Be sure this is a query returning a result set
diff --git a/storage/connect/plgdbsem.h b/storage/connect/plgdbsem.h
index cb408494319..800b1098d50 100644
--- a/storage/connect/plgdbsem.h
+++ b/storage/connect/plgdbsem.h
@@ -1,7 +1,7 @@
/************** PlgDBSem H Declares Source Code File (.H) **************/
/* Name: PLGDBSEM.H Version 3.7 */
/* */
-/* (C) Copyright to the author Olivier BERTRAND 1998-2016 */
+/* (C) Copyright to the author Olivier BERTRAND 1998-2017 */
/* */
/* This file contains the CONNECT storage engine definitions. */
/***********************************************************************/
@@ -57,7 +57,7 @@ enum TABTYPE {TAB_UNDEF = 0, /* Table of undefined type */
TAB_FIX = 2, /* Fixed column offset, fixed LRECL */
TAB_BIN = 3, /* Like FIX but can have binary fields */
TAB_CSV = 4, /* DOS files with CSV records */
- TAB_FMT = 5, /* DOS files with formatted recordss */
+ TAB_FMT = 5, /* DOS files with formatted records */
TAB_DBF = 6, /* DBF Dbase or Foxpro files */
TAB_XML = 7, /* XML or HTML files */
TAB_INI = 8, /* INI or CFG files */
@@ -212,11 +212,24 @@ enum OPVAL {OP_EQ = 1, /* Filtering operator = */
OP_SUB = 17, /* Expression Substract operator */
OP_MULT = 18, /* Expression Multiply operator */
OP_DIV = 19, /* Expression Divide operator */
- OP_NOP = 21, /* Scalar function is nopped */
OP_NUM = 22, /* Scalar function Op Num */
- OP_ABS = 23, /* Scalar function Op Abs */
OP_MAX = 24, /* Scalar function Op Max */
OP_MIN = 25, /* Scalar function Op Min */
+ OP_EXP = 36, /* Scalar function Op Exp */
+ OP_FDISK = 94, /* Operator Disk of fileid */
+ OP_FPATH = 95, /* Operator Path of fileid */
+ OP_FNAME = 96, /* Operator Name of fileid */
+ OP_FTYPE = 97, /* Operator Type of fileid */
+ OP_LAST = 82, /* Index operator Find Last */
+ OP_FIRST = 106, /* Index operator Find First */
+ OP_NEXT = 107, /* Index operator Find Next */
+ OP_SAME = 108, /* Index operator Find Next Same */
+ OP_FSTDIF = 109, /* Index operator Find First dif */
+ OP_NXTDIF = 110, /* Index operator Find Next dif */
+ OP_PREV = 116}; /* Index operator Find Previous */
+#if 0
+ OP_NOP = 21, /* Scalar function is nopped */
+ OP_ABS = 23, /* Scalar function Op Abs */
OP_CEIL = 26, /* Scalar function Op Ceil */
OP_FLOOR = 27, /* Scalar function Op Floor */
OP_MOD = 28, /* Scalar function Op Mod */
@@ -312,6 +325,7 @@ enum OPVAL {OP_EQ = 1, /* Filtering operator = */
OP_REMOVE = 201, /* Scalar function Op Remove */
OP_RENAME = 202, /* Scalar function Op Rename */
OP_FCOMP = 203}; /* Scalar function Op Compare */
+#endif // 0
enum TUSE {USE_NO = 0, /* Table is not yet linearized */
USE_LIN = 1, /* Table is linearized */
@@ -356,6 +370,7 @@ typedef class XOBJECT *PXOB;
typedef class COLBLK *PCOL;
typedef class TDB *PTDB;
typedef class TDBASE *PTDBASE;
+typedef class TDBEXT *PTDBEXT;
typedef class TDBDOS *PTDBDOS;
typedef class TDBFIX *PTDBFIX;
typedef class TDBFMT *PTDBFMT;
@@ -374,6 +389,7 @@ typedef class KXYCOL *PXCOL;
typedef class CATALOG *PCATLG;
typedef class RELDEF *PRELDEF;
typedef class TABDEF *PTABDEF;
+typedef class EXTDEF *PEXTBDEF;
typedef class DOSDEF *PDOSDEF;
typedef class CSVDEF *PCSVDEF;
typedef class VCTDEF *PVCTDEF;
@@ -619,4 +635,4 @@ int global_open(GLOBAL *g, int msgid, const char *filename, int flags, int mode)
DllExport LPCSTR PlugSetPath(LPSTR to, LPCSTR name, LPCSTR dir);
char *MakeEscape(PGLOBAL g, char* str, char q);
-DllExport bool PushWarning(PGLOBAL, PTDBASE, int level = 1);
+DllExport bool PushWarning(PGLOBAL, PTDB, int level = 1);
diff --git a/storage/connect/plgdbutl.cpp b/storage/connect/plgdbutl.cpp
index 83975c6d8fa..1910cdcdec8 100644
--- a/storage/connect/plgdbutl.cpp
+++ b/storage/connect/plgdbutl.cpp
@@ -1,11 +1,11 @@
/********** PlgDBUtl Fpe C++ Program Source Code File (.CPP) ***********/
/* PROGRAM NAME: PLGDBUTL */
/* ------------- */
-/* Version 3.9 */
+/* Version 4.0 */
/* */
/* COPYRIGHT: */
/* ---------- */
-/* (C) Copyright to the author Olivier BERTRAND 1998-2016 */
+/* (C) Copyright to the author Olivier BERTRAND 1998-2017 */
/* */
/* WHAT THIS PROGRAM DOES: */
/* ----------------------- */
@@ -939,7 +939,11 @@ int PlugCloseFile(PGLOBAL g __attribute__((unused)), PFBLOCK fp, bool all)
#endif // LIBXML2_SUPPORT
#ifdef ZIP_SUPPORT
case TYPE_FB_ZIP:
- ((ZIPUTIL*)fp->File)->close();
+ if (fp->Mode == MODE_INSERT)
+ ((ZIPUTIL*)fp->File)->close();
+ else
+ ((UNZIPUTL*)fp->File)->close();
+
fp->Memory = NULL;
fp->Mode = MODE_ANY;
fp->Count = 0;
@@ -1119,7 +1123,7 @@ char *GetAmName(PGLOBAL g, AMT am, void *memp)
return amn;
} // end of GetAmName
-#if defined(__WIN__) && !defined(NOCATCH)
+#if defined(SE_CATCH)
/***********************************************************************/
/* GetExceptionDesc: return the description of an exception code. */
/***********************************************************************/
@@ -1207,7 +1211,7 @@ char *GetExceptionDesc(PGLOBAL g, unsigned int e)
return p;
} // end of GetExceptionDesc
-#endif // __WIN__ && !NOCATCH
+#endif // SE_CATCH
/***********************************************************************/
/* PlgDBalloc: allocates or suballocates memory conditionally. */
diff --git a/storage/connect/plgxml.cpp b/storage/connect/plgxml.cpp
index 71b72621b06..eb31e24235b 100644
--- a/storage/connect/plgxml.cpp
+++ b/storage/connect/plgxml.cpp
@@ -1,6 +1,6 @@
/******************************************************************/
/* Implementation of XML document processing using PdbXML. */
-/* Author: Olivier Bertrand 2007-2012 */
+/* Author: Olivier Bertrand 2007-2017 */
/******************************************************************/
#include "my_global.h"
#include "global.h"
@@ -49,7 +49,7 @@ bool XMLDOCUMENT::InitZip(PGLOBAL g, char *entry)
{
#if defined(ZIP_SUPPORT)
bool mul = (entry) ? strchr(entry, '*') || strchr(entry, '?') : false;
- zip = new(g) ZIPUTIL(entry, mul);
+ zip = new(g) UNZIPUTL(entry, mul);
return zip == NULL;
#else // !ZIP_SUPPORT
sprintf(g->Message, MSG(NO_FEAT_SUPPORT), "ZIP");
diff --git a/storage/connect/plgxml.h b/storage/connect/plgxml.h
index db7dfa6bda5..6870764c503 100644
--- a/storage/connect/plgxml.h
+++ b/storage/connect/plgxml.h
@@ -101,7 +101,7 @@ class XMLDOCUMENT : public BLOCK {
// Members
#if defined(ZIP_SUPPORT)
- ZIPUTIL *zip; /* Used for zipped file */
+ UNZIPUTL *zip; /* Used for zipped file */
#else // !ZIP_SUPPORT
bool zip; /* Always false */
#endif // !ZIP_SUPPORT
diff --git a/storage/connect/plugutil.c b/storage/connect/plugutil.c
index 2551b603349..bfac8a5fd99 100644
--- a/storage/connect/plugutil.c
+++ b/storage/connect/plugutil.c
@@ -244,6 +244,9 @@ LPCSTR PlugSetPath(LPSTR pBuff, LPCSTR prefix, LPCSTR FileName, LPCSTR defpath)
char *drive = NULL, *defdrv = NULL;
#endif
+ if (trace > 1)
+ htrc("prefix=%s fn=%s path=%s\n", prefix, FileName, defpath);
+
if (!strncmp(FileName, "//", 2) || !strncmp(FileName, "\\\\", 2)) {
strcpy(pBuff, FileName); // Remote file
return pBuff;
diff --git a/storage/connect/reldef.cpp b/storage/connect/reldef.cpp
index ef91414a9ab..c6878737f1d 100644
--- a/storage/connect/reldef.cpp
+++ b/storage/connect/reldef.cpp
@@ -621,8 +621,8 @@ bool OEMDEF::DefineAM(PGLOBAL g, LPCSTR, int)
/***********************************************************************/
PTDB OEMDEF::GetTable(PGLOBAL g, MODE mode)
{
- RECFM rfm;
- PTDBASE tdbp = NULL;
+ RECFM rfm;
+ PTDB tdbp = NULL;
// If define block not here yet, get it now
if (!Pxdef && !(Pxdef = GetXdef(g)))
@@ -632,7 +632,7 @@ PTDB OEMDEF::GetTable(PGLOBAL g, MODE mode)
/* Allocate a TDB of the proper type. */
/* Column blocks will be allocated only when needed. */
/*********************************************************************/
- if (!(tdbp = (PTDBASE)Pxdef->GetTable(g, mode)))
+ if (!(tdbp = Pxdef->GetTable(g, mode)))
return NULL;
else
rfm = tdbp->GetFtype();
diff --git a/storage/connect/reldef.h b/storage/connect/reldef.h
index bc1bd2ddd74..52a131dbf3d 100644
--- a/storage/connect/reldef.h
+++ b/storage/connect/reldef.h
@@ -64,15 +64,16 @@ class DllExport RELDEF : public BLOCK { // Relation definition block
}; // end of RELDEF
/***********************************************************************/
-/* These classes correspond to the data base description contained in */
-/* a .XDB file the A.M. DOS, FIX, CSV, MAP, BIN, VCT, PLG, ODBC, DOM. */
+/* This class corresponds to the data base description for tables */
+/* of type DOS, FIX, CSV, DBF, BIN, VCT, JSON, XML... */
/***********************************************************************/
class DllExport TABDEF : public RELDEF { /* Logical table descriptor */
friend class CATALOG;
friend class PLUGCAT;
friend class MYCAT;
- friend class TDBASE;
- public:
+ friend class TDB;
+ friend class TDBEXT;
+public:
// Constructor
TABDEF(void); // Constructor
@@ -112,11 +113,11 @@ class DllExport TABDEF : public RELDEF { /* Logical table descriptor */
int Sort; /* Table already sorted ??? */
int Multiple; /* 0: No 1: DIR 2: Section 3: filelist */
int Degree; /* Number of columns in the table */
- int Pseudo; /* Bit: 1 ROWID Ok, 2 FILEID Ok */
+ int Pseudo; /* Bit: 1 ROWID }Ok, 2 FILEID Ok */
bool Read_Only; /* true for read only tables */
const CHARSET_INFO *m_data_charset;
const char *csname; /* Table charset name */
- }; // end of TABDEF
+}; // end of TABDEF
/***********************************************************************/
/* Externally defined OEM tables. */
@@ -190,11 +191,12 @@ class DllExport COLCRT : public BLOCK { /* Column description block
/***********************************************************************/
/* Column definition block. */
/***********************************************************************/
-class DllExport COLDEF : public COLCRT { /* Column description block */
+class DllExport COLDEF : public COLCRT { /* Column description block */
friend class TABDEF;
friend class COLBLK;
friend class DBFFAM;
- friend class TDBASE;
+ friend class TDB;
+ friend class TDBASE;
friend class TDBDOS;
public:
COLDEF(void); // Constructor
diff --git a/storage/connect/tabdos.cpp b/storage/connect/tabdos.cpp
index 16cc6c33b44..d2bb3d7a4af 100644
--- a/storage/connect/tabdos.cpp
+++ b/storage/connect/tabdos.cpp
@@ -102,6 +102,7 @@ DOSDEF::DOSDEF(void)
Mapped = false;
Zipped = false;
Mulentries = false;
+ Append = false;
Padded = false;
Huge = false;
Accept = false;
@@ -132,10 +133,13 @@ bool DOSDEF::DefineAM(PGLOBAL g, LPCSTR am, int)
: (am && (*am == 'B' || *am == 'b')) ? "B"
: (am && !stricmp(am, "DBF")) ? "D" : "V";
- if ((Zipped = GetBoolCatInfo("Zipped", false)))
- Mulentries = ((Entry = GetStringCatInfo(g, "Entry", NULL)))
- ? strchr(Entry, '*') || strchr(Entry, '?')
- : GetBoolCatInfo("Mulentries", false);
+ if ((Zipped = GetBoolCatInfo("Zipped", false))) {
+ Entry = GetStringCatInfo(g, "Entry", NULL);
+ Mulentries = (Entry && *Entry) ? strchr(Entry, '*') || strchr(Entry, '?')
+ : false;
+ Mulentries = GetBoolCatInfo("Mulentries", Mulentries);
+ Append = GetBoolCatInfo("Append", false);
+ }
Desc = Fn = GetStringCatInfo(g, "Filename", NULL);
Ofn = GetStringCatInfo(g, "Optname", Fn);
@@ -347,10 +351,26 @@ PTDB DOSDEF::GetTable(PGLOBAL g, MODE mode)
if (Zipped) {
#if defined(ZIP_SUPPORT)
if (Recfm == RECFM_VAR) {
- txfp = new(g)ZIPFAM(this);
- tdbp = new(g)TDBDOS(this, txfp);
+ if (mode == MODE_READ || mode == MODE_ANY) {
+ txfp = new(g) UNZFAM(this);
+ } else if (mode == MODE_INSERT) {
+ txfp = new(g) ZIPFAM(this);
+ } else {
+ strcpy(g->Message, "UPDATE/DELETE not supported for ZIP");
+ return NULL;
+ } // endif's mode
+
+ tdbp = new(g) TDBDOS(this, txfp);
} else {
- txfp = new(g)ZPXFAM(this);
+ if (mode == MODE_READ || mode == MODE_ANY) {
+ txfp = new(g) UZXFAM(this);
+ } else if (mode == MODE_INSERT) {
+ txfp = new(g) ZPXFAM(this);
+ } else {
+ strcpy(g->Message, "UPDATE/DELETE not supported for ZIP");
+ return NULL;
+ } // endif's mode
+
tdbp = new(g)TDBFIX(this, txfp);
} // endif Recfm
@@ -376,7 +396,7 @@ PTDB DOSDEF::GetTable(PGLOBAL g, MODE mode)
txfp = new(g) MPXFAM(this);
else if (Compressed) {
#if defined(GZ_SUPPORT)
- txfp = new(g) ZIXFAM(this);
+ txfp = new(g) GZXFAM(this);
#else // !GZ_SUPPORT
sprintf(g->Message, MSG(NO_FEAT_SUPPORT), "GZ");
return NULL;
@@ -484,7 +504,7 @@ TDBDOS::TDBDOS(PGLOBAL g, PTDBDOS tdbp) : TDBASE(tdbp)
} // end of TDBDOS copy constructor
// Method
-PTDB TDBDOS::CopyOne(PTABS t)
+PTDB TDBDOS::Clone(PTABS t)
{
PTDB tp;
PDOSCOL cp1, cp2;
@@ -498,7 +518,7 @@ PTDB TDBDOS::CopyOne(PTABS t)
} // endfor cp1
return tp;
- } // end of CopyOne
+ } // end of Clone
/***********************************************************************/
/* Allocate DOS column description block. */
diff --git a/storage/connect/tabdos.h b/storage/connect/tabdos.h
index 4c8eb438a26..922d52ee399 100644
--- a/storage/connect/tabdos.h
+++ b/storage/connect/tabdos.h
@@ -28,7 +28,7 @@ class DllExport DOSDEF : public TABDEF { /* Logical table description */
friend class TDBFIX;
friend class TXTFAM;
friend class DBFBASE;
- friend class ZIPUTIL;
+ friend class UNZIPUTL;
public:
// Constructor
DOSDEF(void);
@@ -43,7 +43,8 @@ class DllExport DOSDEF : public TABDEF { /* Logical table description */
PSZ GetOfn(void) {return Ofn;}
PSZ GetEntry(void) {return Entry;}
bool GetMul(void) {return Mulentries;}
- void SetBlock(int block) {Block = block;}
+ bool GetAppend(void) {return Append;}
+ void SetBlock(int block) { Block = block; }
int GetBlock(void) {return Block;}
int GetLast(void) {return Last;}
void SetLast(int last) {Last = last;}
@@ -81,6 +82,7 @@ class DllExport DOSDEF : public TABDEF { /* Logical table description */
bool Mapped; /* 0: disk file, 1: memory mapped file */
bool Zipped; /* true for zipped table file */
bool Mulentries; /* true for multiple entries */
+ bool Append; /* Used when creating zipped table */
bool Padded; /* true for padded table file */
bool Huge; /* true for files larger than 2GB */
bool Accept; /* true if wrong lines are accepted */
@@ -140,7 +142,7 @@ class DllExport TDBDOS : public TDBASE {
{return (PTDB)new(g) TDBDOS(g, this);}
// Methods
- virtual PTDB CopyOne(PTABS t);
+ virtual PTDB Clone(PTABS t);
virtual void ResetDB(void) {Txfp->Reset();}
virtual bool IsUsingTemp(PGLOBAL g);
virtual bool IsIndexed(void) {return Indxd;}
diff --git a/storage/connect/tabext.cpp b/storage/connect/tabext.cpp
new file mode 100644
index 00000000000..e3518126a49
--- /dev/null
+++ b/storage/connect/tabext.cpp
@@ -0,0 +1,640 @@
+/************* Tabext C++ Functions Source Code File (.CPP) ************/
+/* Name: TABEXT.CPP Version 1.0 */
+/* */
+/* (C) Copyright to the author Olivier BERTRAND 2017 */
+/* */
+/* This file contains the TBX, TDB and OPJOIN classes functions. */
+/***********************************************************************/
+
+/***********************************************************************/
+/* Include relevant MariaDB header file. */
+/***********************************************************************/
+#define MYSQL_SERVER 1
+#include "my_global.h"
+#include "sql_class.h"
+#include "sql_servers.h"
+#include "sql_string.h"
+#if !defined(__WIN__)
+#include "osutil.h"
+#endif
+
+/***********************************************************************/
+/* Include required application header files */
+/* global.h is header containing all global Plug declarations. */
+/* plgdbsem.h is header containing the DB applic. declarations. */
+/* xobject.h is header containing XOBJECT derived classes declares. */
+/***********************************************************************/
+#include "global.h"
+#include "plgdbsem.h"
+#include "xtable.h"
+#include "tabext.h"
+#include "ha_connect.h"
+
+/* -------------------------- Class CONDFIL -------------------------- */
+
+/***********************************************************************/
+/* CONDFIL Constructor. */
+/***********************************************************************/
+CONDFIL::CONDFIL(const Item *cond, uint idx, AMT type)
+{
+ Cond = cond;
+ Idx = idx;
+ Type = type;
+ Op = OP_XX;
+ Cmds = NULL;
+ Alist = NULL;
+ All = true;
+ Bd = false;
+ Hv = false;
+ Body = NULL,
+ Having = NULL;
+} // end of CONDFIL constructor
+
+/***********************************************************************/
+/* Make and allocate the alias list. */
+/***********************************************************************/
+int CONDFIL::Init(PGLOBAL g, PHC hc)
+{
+ PTOS options = hc->GetTableOptionStruct();
+ char *p, *cn, *cal, *alt = NULL;
+ int rc = RC_OK;
+ bool h;
+
+ if (options)
+ alt = GetListOption(g, "Alias", options->oplist, NULL);
+
+ while (alt) {
+ if (!(p = strchr(alt, '='))) {
+ strcpy(g->Message, "Invalid alias list");
+ rc = RC_FX;
+ break;
+ } // endif !p
+
+ cal = alt; // Alias
+ *p++ = 0;
+
+ if ((h = *p == '*')) {
+ rc = RC_INFO;
+ p++;
+ } // endif h
+
+ cn = p; // Remote column name
+
+ if ((alt = strchr(p, ';')))
+ *alt++ = 0;
+
+ if (*cn == 0)
+ cn = alt;
+
+ Alist = new(g) ALIAS(Alist, cn, cal, h);
+ } // endwhile alt
+
+ return rc;
+} // end of Init
+
+/***********************************************************************/
+/* Make and allocate the alias list. */
+/***********************************************************************/
+const char *CONDFIL::Chk(const char *fln, bool *h)
+{
+ for (PAL pal = Alist; pal; pal = pal->Next)
+ if (!stricmp(fln, pal->Alias)) {
+ *h = pal->Having;
+ return pal->Name;
+ } // endif fln
+
+ *h = false;
+ return fln;
+} // end of Chk
+
+/* --------------------------- Class EXTDEF -------------------------- */
+
+/***********************************************************************/
+/* EXTDEF Constructor. */
+/***********************************************************************/
+EXTDEF::EXTDEF(void)
+{
+ Tabname = Tabschema = Username = Password = Tabcat = Tabtyp = NULL;
+ Colpat = Srcdef = Qchar = Qrystr = Sep = Phpos = NULL;
+ Options = Cto = Qto = Quoted = Maxerr = Maxres = Memory = 0;
+ Scrollable = Xsrc = false;
+} // end of EXTDEF constructor
+
+/***********************************************************************/
+/* DefineAM: define specific AM block values from XDB file. */
+/***********************************************************************/
+bool EXTDEF::DefineAM(PGLOBAL g, LPCSTR am, int poff)
+{
+ Desc = NULL;
+ Tabname = GetStringCatInfo(g, "Name",
+ (Catfunc & (FNC_TABLE | FNC_COL)) ? NULL : Name);
+ Tabname = GetStringCatInfo(g, "Tabname", Tabname);
+ Tabschema = GetStringCatInfo(g, "Dbname", NULL);
+ Tabschema = GetStringCatInfo(g, "Schema", Tabschema);
+ Tabcat = GetStringCatInfo(g, "Qualifier", NULL);
+ Tabcat = GetStringCatInfo(g, "Catalog", Tabcat);
+ Username = GetStringCatInfo(g, "User", NULL);
+ Password = GetStringCatInfo(g, "Password", NULL);
+
+ if ((Srcdef = GetStringCatInfo(g, "Srcdef", NULL)))
+ Read_Only = true;
+
+ Qrystr = GetStringCatInfo(g, "Query_String", "?");
+ Sep = GetStringCatInfo(g, "Separator", NULL);
+//Alias = GetStringCatInfo(g, "Alias", NULL);
+ Phpos = GetStringCatInfo(g, "Phpos", NULL);
+ Xsrc = GetBoolCatInfo("Execsrc", FALSE);
+ Maxerr = GetIntCatInfo("Maxerr", 0);
+ Maxres = GetIntCatInfo("Maxres", 0);
+ Quoted = GetIntCatInfo("Quoted", 0);
+ Options = 0;
+ Cto = 0;
+ Qto = 0;
+
+ if ((Scrollable = GetBoolCatInfo("Scrollable", false)) && !Elemt)
+ Elemt = 1; // Cannot merge SQLFetch and SQLExtendedFetch
+
+ if (Catfunc == FNC_COL)
+ Colpat = GetStringCatInfo(g, "Colpat", NULL);
+
+ if (Catfunc == FNC_TABLE)
+ Tabtyp = GetStringCatInfo(g, "Tabtype", NULL);
+
+ // Memory was Boolean, it is now integer
+ if (!(Memory = GetIntCatInfo("Memory", 0)))
+ Memory = GetBoolCatInfo("Memory", false) ? 1 : 0;
+
+ Pseudo = 2; // FILID is Ok but not ROWID
+ return false;
+} // end of DefineAM
+
+/* ---------------------------TDBEXT class --------------------------- */
+
+/***********************************************************************/
+/* Implementation of the TDBEXT class. */
+/***********************************************************************/
+TDBEXT::TDBEXT(EXTDEF *tdp) : TDB(tdp)
+{
+ Qrp = NULL;
+
+ if (tdp) {
+ TableName = tdp->Tabname;
+ Schema = tdp->Tabschema;
+ User = tdp->Username;
+ Pwd = tdp->Password;
+ Catalog = tdp->Tabcat;
+ Srcdef = tdp->Srcdef;
+ Qrystr = tdp->Qrystr;
+ Sep = tdp->GetSep();
+ Options = tdp->Options;
+ Cto = tdp->Cto;
+ Qto = tdp->Qto;
+ Quoted = MY_MAX(0, tdp->GetQuoted());
+ Rows = tdp->GetElemt();
+ Memory = tdp->Memory;
+ Scrollable = tdp->Scrollable;
+ } else {
+ TableName = NULL;
+ Schema = NULL;
+ User = NULL;
+ Pwd = NULL;
+ Catalog = NULL;
+ Srcdef = NULL;
+ Qrystr = NULL;
+ Sep = 0;
+ Options = 0;
+ Cto = 0;
+ Qto = 0;
+ Quoted = 0;
+ Rows = 0;
+ Memory = 0;
+ Scrollable = false;
+ } // endif tdp
+
+ Quote = NULL;
+ Query = NULL;
+ Count = NULL;
+ //Where = NULL;
+ MulConn = NULL;
+ DBQ = NULL;
+ Qrp = NULL;
+ Fpos = 0;
+ Curpos = 0;
+ AftRows = 0;
+ CurNum = 0;
+ Rbuf = 0;
+ BufSize = 0;
+ Nparm = 0;
+ Ncol = 0;
+ Placed = false;
+} // end of TDBEXT constructor
+
+TDBEXT::TDBEXT(PTDBEXT tdbp) : TDB(tdbp)
+{
+ Qrp = tdbp->Qrp;
+ TableName = tdbp->TableName;
+ Schema = tdbp->Schema;
+ User = tdbp->User;
+ Pwd = tdbp->Pwd;
+ Catalog = tdbp->Catalog;
+ Srcdef = tdbp->Srcdef;
+ Qrystr = tdbp->Qrystr;
+ Sep = tdbp->Sep;
+ Options = tdbp->Options;
+ Cto = tdbp->Cto;
+ Qto = tdbp->Qto;
+ Quoted = tdbp->Quoted;
+ Rows = tdbp->Rows;
+ Memory = tdbp->Memory;
+ Scrollable = tdbp->Scrollable;
+ Quote = tdbp->Quote;
+ Query = tdbp->Query;
+ Count = tdbp->Count;
+ //Where = tdbp->Where;
+ MulConn = tdbp->MulConn;
+ DBQ = tdbp->DBQ;
+ Fpos = 0;
+ Curpos = 0;
+ AftRows = 0;
+ CurNum = 0;
+ Rbuf = 0;
+ BufSize = tdbp->BufSize;
+ Nparm = tdbp->Nparm;
+ Ncol = tdbp->Ncol;
+ Placed = false;
+} // end of TDBEXT copy constructor
+
+/******************************************************************/
+/* Convert an UTF-8 string to latin characters. */
+/******************************************************************/
+int TDBEXT::Decode(char *txt, char *buf, size_t n)
+{
+ uint dummy_errors;
+ uint32 len = copy_and_convert(buf, n, &my_charset_latin1,
+ txt, strlen(txt),
+ &my_charset_utf8_general_ci,
+ &dummy_errors);
+ buf[len] = '\0';
+ return 0;
+} // end of Decode
+
+/***********************************************************************/
+/* MakeSQL: make the SQL statement use with remote connection. */
+/* TODO: when implementing remote filtering, column only used in */
+/* local filter should be removed from column list. */
+/***********************************************************************/
+bool TDBEXT::MakeSQL(PGLOBAL g, bool cnt)
+{
+ char *schmp = NULL, *catp = NULL, buf[NAM_LEN * 3];
+ int len;
+ bool oom = false, first = true;
+ PTABLE tablep = To_Table;
+ PCOL colp;
+
+ if (Srcdef) {
+ if ((catp = strstr(Srcdef, "%s"))) {
+ char *fil1, *fil2;
+ PSZ ph = ((EXTDEF*)To_Def)->Phpos;
+
+ if (!ph)
+ ph = (strstr(catp + 2, "%s")) ? const_cast<char*>("WH") :
+ const_cast<char*>("W");
+
+ if (stricmp(ph, "H")) {
+ fil1 = (To_CondFil && *To_CondFil->Body)
+ ? To_CondFil->Body : PlugDup(g, "1=1");
+ } // endif ph
+
+ if (stricmp(ph, "W")) {
+ fil2 = (To_CondFil && To_CondFil->Having && *To_CondFil->Having)
+ ? To_CondFil->Having : PlugDup(g, "1=1");
+ } // endif ph
+
+ if (!stricmp(ph, "W")) {
+ Query = new(g)STRING(g, strlen(Srcdef) + strlen(fil1));
+ Query->SetLength(sprintf(Query->GetStr(), Srcdef, fil1));
+ } else if (!stricmp(ph, "WH")) {
+ Query = new(g)STRING(g, strlen(Srcdef) + strlen(fil1) + strlen(fil2));
+ Query->SetLength(sprintf(Query->GetStr(), Srcdef, fil1, fil2));
+ } else if (!stricmp(ph, "H")) {
+ Query = new(g)STRING(g, strlen(Srcdef) + strlen(fil2));
+ Query->SetLength(sprintf(Query->GetStr(), Srcdef, fil2));
+ } else if (!stricmp(ph, "HW")) {
+ Query = new(g)STRING(g, strlen(Srcdef) + strlen(fil1) + strlen(fil2));
+ Query->SetLength(sprintf(Query->GetStr(), Srcdef, fil2, fil1));
+ } else {
+ strcpy(g->Message, "MakeSQL: Wrong place holders specification");
+ return true;
+ } // endif's ph
+
+ } else
+ Query = new(g)STRING(g, 0, Srcdef);
+
+ return false;
+ } // endif Srcdef
+
+ // Allocate the string used to contain the Query
+ Query = new(g)STRING(g, 1023, "SELECT ");
+
+ if (!cnt) {
+ if (Columns) {
+ // Normal SQL statement to retrieve results
+ for (colp = Columns; colp; colp = colp->GetNext())
+ if (!colp->IsSpecial()) {
+ if (!first)
+ oom |= Query->Append(", ");
+ else
+ first = false;
+
+ // Column name can be encoded in UTF-8
+ Decode(colp->GetName(), buf, sizeof(buf));
+
+ if (Quote) {
+ // Put column name between identifier quotes in case in contains blanks
+ oom |= Query->Append(Quote);
+ oom |= Query->Append(buf);
+ oom |= Query->Append(Quote);
+ } else
+ oom |= Query->Append(buf);
+
+ ((PEXTCOL)colp)->SetRank(++Ncol);
+ } // endif colp
+
+ } else
+ // !Columns can occur for queries such that sql count(*) from...
+ // for which we will count the rows from sql * from...
+ oom |= Query->Append('*');
+
+ } else
+ // SQL statement used to retrieve the size of the result
+ oom |= Query->Append("count(*)");
+
+ oom |= Query->Append(" FROM ");
+
+ if (Catalog && *Catalog)
+ catp = Catalog;
+
+ //if (tablep->GetSchema())
+ // schmp = (char*)tablep->GetSchema();
+ //else
+ if (Schema && *Schema)
+ schmp = Schema;
+
+ if (catp) {
+ oom |= Query->Append(catp);
+
+ if (schmp) {
+ oom |= Query->Append('.');
+ oom |= Query->Append(schmp);
+ } // endif schmp
+
+ oom |= Query->Append('.');
+ } else if (schmp) {
+ oom |= Query->Append(schmp);
+ oom |= Query->Append('.');
+ } // endif schmp
+
+ // Table name can be encoded in UTF-8
+ Decode(TableName, buf, sizeof(buf));
+
+ if (Quote) {
+ // Put table name between identifier quotes in case in contains blanks
+ oom |= Query->Append(Quote);
+ oom |= Query->Append(buf);
+ oom |= Query->Append(Quote);
+ } else
+ oom |= Query->Append(buf);
+
+ len = Query->GetLength();
+
+ if (To_CondFil) {
+ if (Mode == MODE_READ) {
+ oom |= Query->Append(" WHERE ");
+ oom |= Query->Append(To_CondFil->Body);
+ len = Query->GetLength() + 1;
+ } else
+ len += (strlen(To_CondFil->Body) + 256);
+
+ } else
+ len += ((Mode == MODE_READX) ? 256 : 1);
+
+ if (oom || Query->Resize(len)) {
+ strcpy(g->Message, "MakeSQL: Out of memory");
+ return true;
+ } // endif oom
+
+ if (trace)
+ htrc("Query=%s\n", Query->GetStr());
+
+ return false;
+} // end of MakeSQL
+
+/***********************************************************************/
+/* MakeCommand: make the Update or Delete statement to send to the */
+/* MySQL server. Limited to remote values and filtering. */
+/***********************************************************************/
+bool TDBEXT::MakeCommand(PGLOBAL g)
+{
+ char *p, *stmt, name[68], *body = NULL;
+ char *qrystr = (char*)PlugSubAlloc(g, NULL, strlen(Qrystr) + 1);
+ bool qtd = Quoted > 0;
+ int i = 0, k = 0;
+
+ // Make a lower case copy of the originale query and change
+ // back ticks to the data source identifier quoting character
+ do {
+ qrystr[i] = (Qrystr[i] == '`') ? *Quote : tolower(Qrystr[i]);
+ } while (Qrystr[i++]);
+
+ if (To_CondFil && (p = strstr(qrystr, " where "))) {
+ p[7] = 0; // Remove where clause
+ Qrystr[(p - qrystr) + 7] = 0;
+ body = To_CondFil->Body;
+ stmt = (char*)PlugSubAlloc(g, NULL, strlen(qrystr)
+ + strlen(body) + 64);
+ } else
+ stmt = (char*)PlugSubAlloc(g, NULL, strlen(Qrystr) + 64);
+
+ // Check whether the table name is equal to a keyword
+ // If so, it must be quoted in the original query
+ strlwr(strcat(strcat(strcpy(name, " "), Name), " "));
+
+ if (strstr(" update delete low_priority ignore quick from ", name)) {
+ strlwr(strcat(strcat(strcpy(name, Quote), Name), Quote));
+ k += 2;
+ } else
+ strlwr(strcpy(name, Name)); // Not a keyword
+
+ if ((p = strstr(qrystr, name))) {
+ for (i = 0; i < p - qrystr; i++)
+ stmt[i] = (Qrystr[i] == '`') ? *Quote : Qrystr[i];
+
+ stmt[i] = 0;
+ k += i + (int)strlen(Name);
+
+ if (qtd && *(p - 1) == ' ')
+ strcat(strcat(strcat(stmt, Quote), TableName), Quote);
+ else
+ strcat(stmt, TableName);
+
+ i = (int)strlen(stmt);
+
+ do {
+ stmt[i++] = (Qrystr[k] == '`') ? *Quote : Qrystr[k];
+ } while (Qrystr[k++]);
+
+ if (body)
+ strcat(stmt, body);
+
+ } else {
+ sprintf(g->Message, "Cannot use this %s command",
+ (Mode == MODE_UPDATE) ? "UPDATE" : "DELETE");
+ return true;
+ } // endif p
+
+ if (trace)
+ htrc("Command=%s\n", stmt);
+
+ Query = new(g)STRING(g, 0, stmt);
+ return (!Query->GetSize());
+} // end of MakeCommand
+
+/***********************************************************************/
+/* GetRecpos: return the position of last read record. */
+/***********************************************************************/
+int TDBEXT::GetRecpos(void)
+{
+ return Fpos;
+} // end of GetRecpos
+
+/***********************************************************************/
+/* ODBC GetMaxSize: returns table size estimate in number of lines. */
+/***********************************************************************/
+int TDBEXT::GetMaxSize(PGLOBAL g)
+{
+ if (MaxSize < 0) {
+ if (Mode == MODE_DELETE)
+ // Return 0 in mode DELETE in case of delete all.
+ MaxSize = 0;
+ else if (!Cardinality(NULL))
+ MaxSize = 10; // To make MySQL happy
+ else if ((MaxSize = Cardinality(g)) < 0)
+ MaxSize = 12; // So we can see an error occurred
+
+ } // endif MaxSize
+
+ return MaxSize;
+} // end of GetMaxSize
+
+/***********************************************************************/
+/* Return max size value. */
+/***********************************************************************/
+int TDBEXT::GetProgMax(PGLOBAL g)
+{
+ return GetMaxSize(g);
+} // end of GetProgMax
+
+/* ---------------------------EXTCOL class --------------------------- */
+
+/***********************************************************************/
+/* EXTCOL public constructor. */
+/***********************************************************************/
+EXTCOL::EXTCOL(PCOLDEF cdp, PTDB tdbp, PCOL cprec, int i, PSZ am)
+ : COLBLK(cdp, tdbp, i)
+{
+ if (cprec) {
+ Next = cprec->GetNext();
+ cprec->SetNext(this);
+ } else {
+ Next = tdbp->GetColumns();
+ tdbp->SetColumns(this);
+ } // endif cprec
+
+ if (trace)
+ htrc(" making new %sCOL C%d %s at %p\n", am, Index, Name, this);
+
+ // Set additional remote access method information for column.
+ Crp = NULL;
+ Long = Precision;
+ To_Val = NULL;
+ Bufp = NULL;
+ Blkp = NULL;
+ Rank = 0; // Not known yet
+} // end of JDBCCOL constructor
+
+/***********************************************************************/
+/* EXTCOL private constructor. */
+/***********************************************************************/
+EXTCOL::EXTCOL(void) : COLBLK()
+{
+ Crp = NULL;
+ Buf_Type = TYPE_INT; // This is a count(*) column
+
+ // Set additional Dos access method information for column.
+ Long = sizeof(int);
+ To_Val = NULL;
+ Bufp = NULL;
+ Blkp = NULL;
+ Rank = 1;
+} // end of EXTCOL constructor
+
+/***********************************************************************/
+/* EXTCOL constructor used for copying columns. */
+/* tdbp is the pointer to the new table descriptor. */
+/***********************************************************************/
+EXTCOL::EXTCOL(PEXTCOL col1, PTDB tdbp) : COLBLK(col1, tdbp)
+{
+ Crp = col1->Crp;
+ Long = col1->Long;
+ To_Val = col1->To_Val;
+ Bufp = col1->Bufp;
+ Blkp = col1->Blkp;
+ Rank = col1->Rank;
+} // end of JDBCCOL copy constructor
+
+/***********************************************************************/
+/* SetBuffer: prepare a column block for write operation. */
+/***********************************************************************/
+bool EXTCOL::SetBuffer(PGLOBAL g, PVAL value, bool ok, bool check)
+{
+ if (!(To_Val = value)) {
+ sprintf(g->Message, MSG(VALUE_ERROR), Name);
+ return true;
+ } else if (Buf_Type == value->GetType()) {
+ // Values are of the (good) column type
+ if (Buf_Type == TYPE_DATE) {
+ // If any of the date values is formatted
+ // output format must be set for the receiving table
+ if (GetDomain() || ((DTVAL *)value)->IsFormatted())
+ goto newval; // This will make a new value;
+
+ } else if (Buf_Type == TYPE_DOUBLE)
+ // Float values must be written with the correct (column) precision
+ // Note: maybe this should be forced by ShowValue instead of this ?
+ value->SetPrec(GetScale());
+
+ Value = value; // Directly access the external value
+ } else {
+ // Values are not of the (good) column type
+ if (check) {
+ sprintf(g->Message, MSG(TYPE_VALUE_ERR), Name,
+ GetTypeName(Buf_Type), GetTypeName(value->GetType()));
+ return true;
+ } // endif check
+
+ newval:
+ if (InitValue(g)) // Allocate the matching value block
+ return true;
+
+ } // endif's Value, Buf_Type
+
+ // Because Colblk's have been made from a copy of the original TDB in
+ // case of Update, we must reset them to point to the original one.
+ if (To_Tdb->GetOrig())
+ To_Tdb = (PTDB)To_Tdb->GetOrig();
+
+ // Set the Column
+ Status = (ok) ? BUF_EMPTY : BUF_NO;
+ return false;
+} // end of SetBuffer
+
diff --git a/storage/connect/tabext.h b/storage/connect/tabext.h
new file mode 100644
index 00000000000..2ef20c89f2c
--- /dev/null
+++ b/storage/connect/tabext.h
@@ -0,0 +1,200 @@
+/*************** Tabext H Declares Source Code File (.H) ***************/
+/* Name: TABEXT.H Version 1.0 */
+/* */
+/* (C) Copyright to the author Olivier BERTRAND 2017 */
+/* */
+/* This is the EXTDEF, TABEXT and EXTCOL classes definitions. */
+/***********************************************************************/
+
+#ifndef __TABEXT_H
+#define __TABEXTF_H
+
+#include "reldef.h"
+
+typedef class ALIAS *PAL;
+
+class ALIAS : public BLOCK {
+ public:
+ ALIAS(PAL x, PSZ n, PSZ a, bool h)
+ {Next = x, Name = n, Alias = a, Having = h;}
+
+ PAL Next;
+ PSZ Name;
+ PSZ Alias;
+ bool Having;
+}; // end of class ALIAS
+
+// Condition filter structure
+class CONDFIL : public BLOCK {
+ public:
+ // Constructor
+ CONDFIL(const Item *cond, uint idx, AMT type);
+
+ // Functions
+ int Init(PGLOBAL g, PHC hc);
+ const char *Chk(const char *cln, bool *h);
+
+ // Members
+ const Item *Cond;
+ AMT Type;
+ uint Idx;
+ OPVAL Op;
+ PCMD Cmds;
+ PAL Alist;
+ bool All;
+ bool Bd;
+ bool Hv;
+ char *Body;
+ char *Having;
+}; // end of class CONDFIL
+
+/***********************************************************************/
+/* This class corresponds to the data base description for external */
+/* tables of type MYSQL, ODBC, JDBC... */
+/***********************************************************************/
+class DllExport EXTDEF : public TABDEF { /* EXT table */
+ friend class TDBEXT;
+public:
+ // Constructor
+ EXTDEF(void); // Constructor
+
+ // Implementation
+ virtual const char *GetType(void) { return "EXT"; }
+ inline PSZ GetTabname(void) { return Tabname; }
+ inline PSZ GetTabschema(void) { return Tabschema; }
+ inline PSZ GetUsername(void) { return Username; };
+ inline PSZ GetPassword(void) { return Password; };
+ inline PSZ GetTabcat(void) { return Tabcat; }
+ inline PSZ GetSrcdef(void) { return Srcdef; }
+ inline char GetSep(void) { return (Sep) ? *Sep : 0; }
+ inline int GetQuoted(void) { return Quoted; }
+ inline int GetOptions(void) { return Options; }
+
+ // Methods
+ virtual int Indexable(void) { return 2; }
+ virtual bool DefineAM(PGLOBAL g, LPCSTR am, int poff);
+
+protected:
+ // Members
+ PSZ Tabname; /* External table name */
+ PSZ Tabschema; /* External table schema */
+ PSZ Username; /* User connect name */
+ PSZ Password; /* Password connect info */
+ PSZ Tabcat; /* External table catalog */
+ PSZ Tabtyp; /* Catalog table type */
+ PSZ Colpat; /* Catalog column pattern */
+ PSZ Srcdef; /* The source table SQL definition */
+ PSZ Qchar; /* Identifier quoting character */
+ PSZ Qrystr; /* The original query */
+ PSZ Sep; /* Decimal separator */
+//PSZ Alias; /* Column alias list */
+ PSZ Phpos; /* Place holer positions */
+ int Options; /* Open connection options */
+ int Cto; /* Open connection timeout */
+ int Qto; /* Query (command) timeout */
+ int Quoted; /* Identifier quoting level */
+ int Maxerr; /* Maxerr for an Exec table */
+ int Maxres; /* Maxres for a catalog table */
+ int Memory; /* Put result set in memory */
+ bool Scrollable; /* Use scrollable cursor */
+ bool Xsrc; /* Execution type */
+}; // end of EXTDEF
+
+/***********************************************************************/
+/* This is the base class for all external tables. */
+/***********************************************************************/
+class DllExport TDBEXT : public TDB {
+public:
+ // Constructors
+ TDBEXT(EXTDEF *tdp);
+ TDBEXT(PTDBEXT tdbp);
+
+ // Implementation
+
+ // Properties
+ virtual bool IsRemote(void) { return true; }
+
+ // Methods
+ virtual PSZ GetServer(void) { return "Remote"; }
+ virtual int GetRecpos(void);
+
+ // Database routines
+ virtual int GetMaxSize(PGLOBAL g);
+ virtual int GetProgMax(PGLOBAL g);
+
+protected:
+ // Internal functions
+ virtual bool MakeSQL(PGLOBAL g, bool cnt);
+ //virtual bool MakeInsert(PGLOBAL g);
+ virtual bool MakeCommand(PGLOBAL g);
+ int Decode(char *utf, char *buf, size_t n);
+
+ // Members
+ PQRYRES Qrp; // Points to storage result
+ PSTRG Query; // Constructed SQL query
+ char *TableName; // Points to ODBC table name
+ char *Schema; // Points to ODBC table Schema
+ char *User; // User connect info
+ char *Pwd; // Password connect info
+ char *Catalog; // Points to ODBC table Catalog
+ char *Srcdef; // The source table SQL definition
+ char *Count; // Points to count(*) SQL statement
+ //char *Where; // Points to local where clause
+ char *Quote; // The identifier quoting character
+ char *MulConn; // Used for multiple ODBC tables
+ char *DBQ; // The address part of Connect string
+ char *Qrystr; // The original query
+ char Sep; // The decimal separator
+ int Options; // Connect options
+ int Cto; // Connect timeout
+ int Qto; // Query timeout
+ int Quoted; // The identifier quoting level
+ int Fpos; // Position of last read record
+ int Curpos; // Cursor position of last fetch
+ int AftRows; // The number of affected rows
+ int Rows; // Rowset size
+ int CurNum; // Current buffer line number
+ int Rbuf; // Number of lines read in buffer
+ int BufSize; // Size of connect string buffer
+ int Nparm; // The number of statement parameters
+ int Memory; // 0: No 1: Alloc 2: Put 3: Get
+ int Ncol; // The column number (JDBC)
+ bool Scrollable; // Use scrollable cursor
+ bool Placed; // True for position reading
+}; // end of class TDBEXT
+
+/***********************************************************************/
+/* Virual class EXTCOL: external column. */
+/***********************************************************************/
+class DllExport EXTCOL : public COLBLK {
+ friend class TDBEXT;
+public:
+ // Constructor
+ EXTCOL(PCOLDEF cdp, PTDB tdbp, PCOL cprec, int i, PSZ am);
+ EXTCOL(PEXTCOL colp, PTDB tdbp); // Constructor used in copy process
+
+ // Implementation
+ inline int GetRank(void) { return Rank; }
+ inline void SetRank(int k) { Rank = k; }
+ //inline PVBLK GetBlkp(void) {return Blkp;}
+ inline void SetCrp(PCOLRES crp) { Crp = crp; }
+
+ // Methods
+ virtual bool SetBuffer(PGLOBAL g, PVAL value, bool ok, bool check);
+ virtual void ReadColumn(PGLOBAL) = 0;
+ virtual void WriteColumn(PGLOBAL) = 0;
+
+protected:
+ // Constructor for count(*) column
+ EXTCOL(void);
+
+ // Members
+ PCOLRES Crp; // To storage result
+ void *Bufp; // To extended buffer
+ PVBLK Blkp; // To Value Block
+ PVAL To_Val; // To value used for Insert
+ int Rank; // Rank (position) number in the query
+ //int Flag; // ???
+}; // end of class EXTCOL
+
+#endif // __TABEXT_H
diff --git a/storage/connect/tabfix.cpp b/storage/connect/tabfix.cpp
index d99f7800f26..bf123cd36c8 100644
--- a/storage/connect/tabfix.cpp
+++ b/storage/connect/tabfix.cpp
@@ -77,7 +77,7 @@ TDBFIX::TDBFIX(PGLOBAL g, PTDBFIX tdbp) : TDBDOS(g, tdbp)
} // end of TDBFIX copy constructor
// Method
-PTDB TDBFIX::CopyOne(PTABS t)
+PTDB TDBFIX::Clone(PTABS t)
{
PTDB tp;
PGLOBAL g = t->G;
@@ -105,7 +105,7 @@ PTDB TDBFIX::CopyOne(PTABS t)
} // endif Ftype
return tp;
- } // end of CopyOne
+ } // end of Clone
/***********************************************************************/
/* Reset read/write position values. */
diff --git a/storage/connect/tabfix.h b/storage/connect/tabfix.h
index 49956ba0711..4b9f9689992 100644
--- a/storage/connect/tabfix.h
+++ b/storage/connect/tabfix.h
@@ -34,7 +34,7 @@ class DllExport TDBFIX : public TDBDOS {
{return (PTDB)new(g) TDBFIX(g, this);}
// Methods
- virtual PTDB CopyOne(PTABS t);
+ virtual PTDB Clone(PTABS t);
virtual void ResetDB(void);
virtual bool IsUsingTemp(PGLOBAL g);
virtual int RowNumber(PGLOBAL g, bool b = false);
diff --git a/storage/connect/tabfmt.cpp b/storage/connect/tabfmt.cpp
index 183bb8f8d65..1a75d572ecd 100644
--- a/storage/connect/tabfmt.cpp
+++ b/storage/connect/tabfmt.cpp
@@ -5,7 +5,7 @@
/* */
/* COPYRIGHT: */
/* ---------- */
-/* (C) Copyright to the author Olivier BERTRAND 2001 - 2016 */
+/* (C) Copyright to the author Olivier BERTRAND 2001 - 2017 */
/* */
/* WHAT THIS PROGRAM DOES: */
/* ----------------------- */
@@ -98,8 +98,9 @@ PQRYRES CSVColumns(PGLOBAL g, char *dp, PTOS topt, bool info)
int num_read = 0, num_max = 10000000; // Statistics
int len[MAXCOL], typ[MAXCOL], prc[MAXCOL];
PCSVDEF tdp;
- PTDBCSV tdbp;
- PQRYRES qrp;
+ PTDBCSV tcvp;
+ PTDBASE tdbp;
+ PQRYRES qrp;
PCOLRES crp;
if (info) {
@@ -108,10 +109,10 @@ PQRYRES CSVColumns(PGLOBAL g, char *dp, PTOS topt, bool info)
goto skipit;
} // endif info
- if (GetIntegerTableOption(g, topt, "Multiple", 0)) {
- strcpy(g->Message, "Cannot find column definition for multiple table");
- return NULL;
- } // endif Multiple
+ //if (GetIntegerTableOption(g, topt, "Multiple", 0)) {
+ // strcpy(g->Message, "Cannot find column definition for multiple table");
+ // return NULL;
+ //} // endif Multiple
// num_max = atoi(p+1); // Max num of record to test
imax = hmax = nerr = 0;
@@ -127,10 +128,20 @@ PQRYRES CSVColumns(PGLOBAL g, char *dp, PTOS topt, bool info)
/* Get the CSV table description block. */
/*********************************************************************/
tdp = new(g) CSVDEF;
+ tdp->Database = dp;
+
+ if ((tdp->Zipped = GetBooleanTableOption(g, topt, "Zipped", false))) {
#if defined(ZIP_SUPPORT)
- tdp->Entry = GetStringTableOption(g, topt, "Entry", NULL);
- tdp->Zipped = GetBooleanTableOption(g, topt, "Zipped", false);
-#endif // ZIP_SUPPORT
+ tdp->Entry = GetStringTableOption(g, topt, "Entry", NULL);
+ tdp->Mulentries = (tdp->Entry)
+ ? strchr(tdp->Entry, '*') || strchr(tdp->Entry, '?')
+ : GetBooleanTableOption(g, topt, "Mulentries", false);
+#else // !ZIP_SUPPORT
+ strcpy(g->Message, "ZIP not supported by this version");
+ return NULL;
+#endif // !ZIP_SUPPORT
+ } // endif // Zipped
+
fn = tdp->Fn = GetStringTableOption(g, topt, "Filename", NULL);
if (!tdp->Fn) {
@@ -141,6 +152,7 @@ PQRYRES CSVColumns(PGLOBAL g, char *dp, PTOS topt, bool info)
if (!(tdp->Lrecl = GetIntegerTableOption(g, topt, "Lrecl", 0)))
tdp->Lrecl = 4096;
+ tdp->Multiple = GetIntegerTableOption(g, topt, "Multiple", 0);
p = GetStringTableOption(g, topt, "Separator", ",");
tdp->Sep = (strlen(p) == 2 && p[0] == '\\' && p[1] == 't') ? '\t' : *p;
@@ -177,17 +189,18 @@ PQRYRES CSVColumns(PGLOBAL g, char *dp, PTOS topt, bool info)
htrc("File %s Sep=%c Qot=%c Header=%d maxerr=%d\n",
SVP(tdp->Fn), tdp->Sep, tdp->Qot, tdp->Header, tdp->Maxerr);
- if (tdp->Zipped) {
-#if defined(ZIP_SUPPORT)
- tdbp = new(g)TDBCSV(tdp, new(g)ZIPFAM(tdp));
-#else // !ZIP_SUPPORT
- sprintf(g->Message, MSG(NO_FEAT_SUPPORT), "ZIP");
- return NULL;
-#endif // !ZIP_SUPPORT
- } else
- tdbp = new(g) TDBCSV(tdp, new(g) DOSFAM(tdp));
+ if (tdp->Zipped)
+ tcvp = new(g)TDBCSV(tdp, new(g)UNZFAM(tdp));
+ else
+ tcvp = new(g) TDBCSV(tdp, new(g) DOSFAM(tdp));
+
+ tcvp->SetMode(MODE_READ);
- tdbp->SetMode(MODE_READ);
+ if (tdp->Multiple) {
+ tdbp = new(g)TDBMUL(tcvp);
+ tdbp->SetMode(MODE_READ);
+ } else
+ tdbp = tcvp;
/*********************************************************************/
/* Open the CSV file. */
@@ -202,7 +215,7 @@ PQRYRES CSVColumns(PGLOBAL g, char *dp, PTOS topt, bool info)
phase = 0;
if ((rc = tdbp->ReadDB(g)) == RC_OK) {
- p = PlgDBDup(g, tdbp->To_Line);
+ p = PlgDBDup(g, tcvp->To_Line);
//skip leading blanks
for (; *p == ' '; p++) ;
@@ -245,6 +258,7 @@ PQRYRES CSVColumns(PGLOBAL g, char *dp, PTOS topt, bool info)
for (i = 0; i < hmax; i++)
length[0] = MY_MAX(length[0], strlen(colname[i]));
+ tcvp->Header = true; // In case of multiple table
} // endif hdr
for (num_read++; num_read <= num_max; num_read++) {
@@ -265,7 +279,7 @@ PQRYRES CSVColumns(PGLOBAL g, char *dp, PTOS topt, bool info)
/*******************************************************************/
i = n = phase = blank = digit = dec = 0;
- for (p = tdbp->To_Line; *p; p++)
+ for (p = tcvp->To_Line; *p; p++)
if (*p == sep) {
if (phase != 1) {
if (i == MAXCOL - 1) {
@@ -503,7 +517,14 @@ PTDB CSVDEF::GetTable(PGLOBAL g, MODE mode)
/*******************************************************************/
if (Zipped) {
#if defined(ZIP_SUPPORT)
- txfp = new(g) ZIPFAM(this);
+ if (mode == MODE_READ || mode == MODE_ANY) {
+ txfp = new(g) UNZFAM(this);
+ } else if (mode == MODE_INSERT) {
+ txfp = new(g) ZIPFAM(this);
+ } else {
+ strcpy(g->Message, "UPDATE/DELETE not supported for ZIP");
+ return NULL;
+ } // endif's mode
#else // !ZIP_SUPPORT
strcpy(g->Message, "ZIP not supported");
return NULL;
@@ -640,7 +661,7 @@ TDBCSV::TDBCSV(PGLOBAL g, PTDBCSV tdbp) : TDBDOS(g, tdbp)
} // end of TDBCSV copy constructor
// Method
-PTDB TDBCSV::CopyOne(PTABS t)
+PTDB TDBCSV::Clone(PTABS t)
{
PTDB tp;
PCSVCOL cp1, cp2;
@@ -654,7 +675,7 @@ PTDB TDBCSV::CopyOne(PTABS t)
} // endfor cp1
return tp;
- } // end of CopyOne
+ } // end of Clone
/***********************************************************************/
/* Allocate CSV column description block. */
@@ -1148,7 +1169,7 @@ TDBFMT::TDBFMT(PGLOBAL g, PTDBFMT tdbp) : TDBCSV(g, tdbp)
} // end of TDBFMT copy constructor
// Method
-PTDB TDBFMT::CopyOne(PTABS t)
+PTDB TDBFMT::Clone(PTABS t)
{
PTDB tp;
PCSVCOL cp1, cp2;
@@ -1165,7 +1186,7 @@ PTDB TDBFMT::CopyOne(PTABS t)
} // endfor cp1
return tp;
- } // end of CopyOne
+ } // end of Clone
/***********************************************************************/
/* Allocate FMT column description block. */
diff --git a/storage/connect/tabfmt.h b/storage/connect/tabfmt.h
index 5ce8d399a64..e5655435be7 100644
--- a/storage/connect/tabfmt.h
+++ b/storage/connect/tabfmt.h
@@ -52,6 +52,7 @@ public:
/***********************************************************************/
class DllExport TDBCSV : public TDBDOS {
friend class CSVCOL;
+ friend class MAPFAM;
friend PQRYRES CSVColumns(PGLOBAL, char *, PTOS, bool);
public:
// Constructor
@@ -64,7 +65,7 @@ public:
{return (PTDB)new(g) TDBCSV(g, this);}
// Methods
- virtual PTDB CopyOne(PTABS t);
+ virtual PTDB Clone(PTABS t);
//virtual bool IsUsingTemp(PGLOBAL g);
virtual int GetBadLines(void) {return (int)Nerr;}
@@ -147,7 +148,7 @@ class DllExport TDBFMT : public TDBCSV {
{return (PTDB)new(g) TDBFMT(g, this);}
// Methods
- virtual PTDB CopyOne(PTABS t);
+ virtual PTDB Clone(PTABS t);
// Database routines
virtual PCOL MakeCol(PGLOBAL g, PCOLDEF cdp, PCOL cprec, int n);
diff --git a/storage/connect/tabjdbc.cpp b/storage/connect/tabjdbc.cpp
index c36aa080956..5431e35e0ec 100644
--- a/storage/connect/tabjdbc.cpp
+++ b/storage/connect/tabjdbc.cpp
@@ -1,11 +1,11 @@
/************* TabJDBC C++ Program Source Code File (.CPP) *************/
/* PROGRAM NAME: TABJDBC */
/* ------------- */
-/* Version 1.1 */
+/* Version 1.2 */
/* */
/* COPYRIGHT: */
/* ---------- */
-/* (C) Copyright to the author Olivier BERTRAND 2016 */
+/* (C) Copyright to the author Olivier BERTRAND 2016-2017 */
/* */
/* WHAT THIS PROGRAM DOES: */
/* ----------------------- */
@@ -69,9 +69,10 @@
#include "plgdbsem.h"
#include "mycat.h"
#include "xtable.h"
+#include "tabext.h"
#include "tabjdbc.h"
#include "tabmul.h"
-#include "reldef.h"
+//#include "reldef.h"
#include "tabcol.h"
#include "valblk.h"
#include "ha_connect.h"
@@ -96,10 +97,7 @@ bool ExactInfo(void);
/***********************************************************************/
JDBCDEF::JDBCDEF(void)
{
- Driver = Url = Wrapname =Tabname = Tabschema = Username = Colpat = NULL;
- Password = Tabcat = Tabtype = Srcdef = Qchar = Qrystr = Sep = NULL;
- Options = Quoted = Maxerr = Maxres = Memory = 0;
- Scrollable = Xsrc = false;
+ Driver = Url = Wrapname = NULL;
} // end of JDBCDEF constructor
/***********************************************************************/
@@ -134,23 +132,26 @@ bool JDBCDEF::SetParms(PJPARM sjp)
int JDBCDEF::ParseURL(PGLOBAL g, char *url, bool b)
{
if (strncmp(url, "jdbc:", 5)) {
+ PSZ p;
+
// No "jdbc:" in connection string. Must be a straight
// "server" or "server/table"
// ok, so we do a little parsing, but not completely!
- if ((Tabname= strchr(url, '/'))) {
+ if ((p = strchr(url, '/'))) {
// If there is a single '/' in the connection string,
// this means the user is specifying a table name
- *Tabname++= '\0';
+ *p++= '\0';
// there better not be any more '/'s !
- if (strchr(Tabname, '/'))
+ if (strchr(p, '/'))
return RC_FX;
- } else if (b) {
- // Otherwise, straight server name,
- Tabname = GetStringCatInfo(g, "Name", NULL);
- Tabname = GetStringCatInfo(g, "Tabname", Tabname);
- } // endelse
+ Tabname = p;
+// } else if (b) {
+// // Otherwise, straight server name,
+// Tabname = GetStringCatInfo(g, "Name", NULL);
+// Tabname = GetStringCatInfo(g, "Tabname", Tabname);
+ } // endif
if (trace)
htrc("server: %s Tabname: %s", url, Tabname);
@@ -204,6 +205,9 @@ bool JDBCDEF::DefineAM(PGLOBAL g, LPCSTR am, int poff)
{
int rc = RC_OK;
+ if (EXTDEF::DefineAM(g, am, poff))
+ return true;
+
Driver = GetStringCatInfo(g, "Driver", NULL);
Desc = Url = GetStringCatInfo(g, "Connect", NULL);
@@ -223,41 +227,41 @@ bool JDBCDEF::DefineAM(PGLOBAL g, LPCSTR am, int poff)
if (rc == RC_FX) // Error
return true;
- else if (rc == RC_OK) { // Url was not a server name
- Tabname = GetStringCatInfo(g, "Name",
- (Catfunc & (FNC_TABLE | FNC_COL)) ? NULL : Name);
- Tabname = GetStringCatInfo(g, "Tabname", Tabname);
- Username = GetStringCatInfo(g, "User", NULL);
- Password = GetStringCatInfo(g, "Password", NULL);
- } // endif rc
+//else if (rc == RC_OK) { // Url was not a server name
+// Tabname = GetStringCatInfo(g, "Name",
+// (Catfunc & (FNC_TABLE | FNC_COL)) ? NULL : Name);
+// Tabname = GetStringCatInfo(g, "Tabname", Tabname);
+// Username = GetStringCatInfo(g, "User", NULL);
+// Password = GetStringCatInfo(g, "Password", NULL);
+//} // endif rc
- if ((Srcdef = GetStringCatInfo(g, "Srcdef", NULL)))
- Read_Only = true;
+//if ((Srcdef = GetStringCatInfo(g, "Srcdef", NULL)))
+// Read_Only = true;
Wrapname = GetStringCatInfo(g, "Wrapper", NULL);
//Prop = GetStringCatInfo(g, "Properties", NULL);
- Tabcat = GetStringCatInfo(g, "Qualifier", NULL);
- Tabcat = GetStringCatInfo(g, "Catalog", Tabcat);
- Tabschema = GetStringCatInfo(g, "Dbname", NULL);
- Tabschema = GetStringCatInfo(g, "Schema", Tabschema);
-
- if (Catfunc == FNC_COL)
- Colpat = GetStringCatInfo(g, "Colpat", NULL);
-
- if (Catfunc == FNC_TABLE)
- Tabtype = GetStringCatInfo(g, "Tabtype", NULL);
-
- Qrystr = GetStringCatInfo(g, "Query_String", "?");
- Sep = GetStringCatInfo(g, "Separator", NULL);
- Xsrc = GetBoolCatInfo("Execsrc", FALSE);
- Maxerr = GetIntCatInfo("Maxerr", 0);
- Maxres = GetIntCatInfo("Maxres", 0);
- Quoted = GetIntCatInfo("Quoted", 0);
-//Cto= GetIntCatInfo("ConnectTimeout", DEFAULT_LOGIN_TIMEOUT);
-//Qto= GetIntCatInfo("QueryTimeout", DEFAULT_QUERY_TIMEOUT);
- Scrollable = GetBoolCatInfo("Scrollable", false);
- Memory = GetIntCatInfo("Memory", 0);
- Pseudo = 2; // FILID is Ok but not ROWID
+//Tabcat = GetStringCatInfo(g, "Qualifier", NULL);
+//Tabcat = GetStringCatInfo(g, "Catalog", Tabcat);
+//Tabschema = GetStringCatInfo(g, "Dbname", NULL);
+//Tabschema = GetStringCatInfo(g, "Schema", Tabschema);
+
+//if (Catfunc == FNC_COL)
+// Colpat = GetStringCatInfo(g, "Colpat", NULL);
+
+//if (Catfunc == FNC_TABLE)
+// Tabtyp = GetStringCatInfo(g, "Tabtype", NULL);
+
+//Qrystr = GetStringCatInfo(g, "Query_String", "?");
+//Sep = GetStringCatInfo(g, "Separator", NULL);
+//Xsrc = GetBoolCatInfo("Execsrc", FALSE);
+//Maxerr = GetIntCatInfo("Maxerr", 0);
+//Maxres = GetIntCatInfo("Maxres", 0);
+//Quoted = GetIntCatInfo("Quoted", 0);
+// Cto= GetIntCatInfo("ConnectTimeout", DEFAULT_LOGIN_TIMEOUT);
+// Qto= GetIntCatInfo("QueryTimeout", DEFAULT_QUERY_TIMEOUT);
+//Scrollable = GetBoolCatInfo("Scrollable", false);
+//Memory = GetIntCatInfo("Memory", 0);
+//Pseudo = 2; // FILID is Ok but not ROWID
return false;
} // end of DefineAM
@@ -266,7 +270,7 @@ bool JDBCDEF::DefineAM(PGLOBAL g, LPCSTR am, int poff)
/***********************************************************************/
PTDB JDBCDEF::GetTable(PGLOBAL g, MODE m)
{
- PTDBASE tdbp = NULL;
+ PTDB tdbp = NULL;
/*********************************************************************/
/* Allocate a TDB of the proper type. */
@@ -326,7 +330,7 @@ int JDBCPARM::CheckSize(int rows)
/***********************************************************************/
/* Implementation of the TDBJDBC class. */
/***********************************************************************/
-TDBJDBC::TDBJDBC(PJDBCDEF tdp) : TDBASE(tdp)
+TDBJDBC::TDBJDBC(PJDBCDEF tdp) : TDBEXT(tdp)
{
Jcp = NULL;
Cnp = NULL;
@@ -335,101 +339,45 @@ TDBJDBC::TDBJDBC(PJDBCDEF tdp) : TDBASE(tdp)
Ops.Driver = tdp->Driver;
Ops.Url = tdp->Url;
WrapName = tdp->Wrapname;
- TableName = tdp->Tabname;
- Schema = tdp->Tabschema;
Ops.User = tdp->Username;
Ops.Pwd = tdp->Password;
// Ops.Properties = tdp->Prop;
- Catalog = tdp->Tabcat;
- Srcdef = tdp->Srcdef;
- Qrystr = tdp->Qrystr;
- Sep = tdp->GetSep();
- Options = tdp->Options;
// Ops.Cto = tdp->Cto;
// Ops.Qto = tdp->Qto;
- Quoted = MY_MAX(0, tdp->GetQuoted());
- Rows = tdp->GetElemt();
- Memory = tdp->Memory;
Ops.Scrollable = tdp->Scrollable;
} else {
WrapName = NULL;
- TableName = NULL;
- Schema = NULL;
Ops.Driver = NULL;
Ops.Url = NULL;
Ops.User = NULL;
Ops.Pwd = NULL;
// Ops.Properties = NULL;
- Catalog = NULL;
- Srcdef = NULL;
- Qrystr = NULL;
- Sep = 0;
- Options = 0;
// Ops.Cto = DEFAULT_LOGIN_TIMEOUT;
// Ops.Qto = DEFAULT_QUERY_TIMEOUT;
- Quoted = 0;
- Rows = 0;
- Memory = 0;
Ops.Scrollable = false;
} // endif tdp
- Quote = NULL;
- Query = NULL;
- Count = NULL;
-//Where = NULL;
- MulConn = NULL;
- DBQ = NULL;
- Qrp = NULL;
- Fpos = 0;
- Curpos = 0;
- AftRows = 0;
- CurNum = 0;
- Rbuf = 0;
- BufSize = 0;
- Ncol = 0;
- Nparm = 0;
- Placed = false;
+//Ncol = 0;
Prepared = false;
Werr = false;
Rerr = false;
Ops.Fsize = Ops.CheckSize(Rows);
} // end of TDBJDBC standard constructor
-TDBJDBC::TDBJDBC(PTDBJDBC tdbp) : TDBASE(tdbp)
+TDBJDBC::TDBJDBC(PTDBJDBC tdbp) : TDBEXT(tdbp)
{
Jcp = tdbp->Jcp; // is that right ?
Cnp = tdbp->Cnp;
WrapName = tdbp->WrapName;
- TableName = tdbp->TableName;
- Schema = tdbp->Schema;
Ops = tdbp->Ops;
- Catalog = tdbp->Catalog;
- Srcdef = tdbp->Srcdef;
- Qrystr = tdbp->Qrystr;
- Memory = tdbp->Memory;
-//Scrollable = tdbp->Scrollable;
- Quote = tdbp->Quote;
- Query = tdbp->Query;
- Count = tdbp->Count;
-//Where = tdbp->Where;
- MulConn = tdbp->MulConn;
- DBQ = tdbp->DBQ;
- Options = tdbp->Options;
- Quoted = tdbp->Quoted;
- Rows = tdbp->Rows;
- Fpos = 0;
- Curpos = 0;
- AftRows = 0;
- CurNum = 0;
- Rbuf = 0;
- BufSize = tdbp->BufSize;
- Nparm = tdbp->Nparm;
- Qrp = tdbp->Qrp;
- Placed = false;
+//Ncol = tdbp->Ncol;
+ Prepared = tdbp->Prepared;
+ Werr = tdbp->Werr;
+ Rerr = tdbp->Rerr;
} // end of TDBJDBC copy constructor
// Method
-PTDB TDBJDBC::CopyOne(PTABS t)
+PTDB TDBJDBC::Clone(PTABS t)
{
PTDB tp;
PJDBCCOL cp1, cp2;
@@ -443,7 +391,7 @@ PTDB TDBJDBC::CopyOne(PTABS t)
} // endfor cp1
return tp;
-} // end of CopyOne
+} // end of Clone
/***********************************************************************/
/* Allocate JDBC column description block. */
@@ -453,134 +401,6 @@ PCOL TDBJDBC::MakeCol(PGLOBAL g, PCOLDEF cdp, PCOL cprec, int n)
return new(g)JDBCCOL(cdp, this, cprec, n);
} // end of MakeCol
-/******************************************************************/
-/* Convert an UTF-8 string to latin characters. */
-/******************************************************************/
-int TDBJDBC::Decode(char *txt, char *buf, size_t n)
-{
- uint dummy_errors;
- uint32 len= copy_and_convert(buf, n, &my_charset_latin1,
- txt, strlen(txt),
- &my_charset_utf8_general_ci,
- &dummy_errors);
- buf[len]= '\0';
- return 0;
-} // end of Decode
-
-/***********************************************************************/
-/* MakeSQL: make the SQL statement use with JDBC connection. */
-/* TODO: when implementing EOM filtering, column only used in local */
-/* filter should be removed from column list. */
-/***********************************************************************/
-bool TDBJDBC::MakeSQL(PGLOBAL g, bool cnt)
-{
- char *schmp = NULL, *catp = NULL, buf[NAM_LEN * 3];
- int len;
- bool oom = false, first = true;
- PTABLE tablep = To_Table;
- PCOL colp;
-
- if (Srcdef) {
- Query = new(g)STRING(g, 0, Srcdef);
- return false;
- } // endif Srcdef
-
- // Allocate the string used to contain the Query
- Query = new(g)STRING(g, 1023, "SELECT ");
-
- if (!cnt) {
- if (Columns) {
- // Normal SQL statement to retrieve results
- for (colp = Columns; colp; colp = colp->GetNext())
- if (!colp->IsSpecial()) {
- if (!first)
- oom |= Query->Append(", ");
- else
- first = false;
-
- // Column name can be encoded in UTF-8
- Decode(colp->GetName(), buf, sizeof(buf));
-
- if (Quote) {
- // Put column name between identifier quotes in case in contains blanks
- oom |= Query->Append(Quote);
- oom |= Query->Append(buf);
- oom |= Query->Append(Quote);
- } else
- oom |= Query->Append(buf);
-
- ((PJDBCCOL)colp)->Rank = ++Ncol;
- } // endif colp
-
- } else
- // !Columns can occur for queries such that sql count(*) from...
- // for which we will count the rows from sql * from...
- oom |= Query->Append('*');
-
- } else
- // SQL statement used to retrieve the size of the result
- oom |= Query->Append("count(*)");
-
- oom |= Query->Append(" FROM ");
-
- if (Catalog && *Catalog)
- catp = Catalog;
-
- //if (tablep->GetSchema())
- // schmp = (char*)tablep->GetSchema();
- //else
- if (Schema && *Schema)
- schmp = Schema;
-
- if (catp) {
- oom |= Query->Append(catp);
-
- if (schmp) {
- oom |= Query->Append('.');
- oom |= Query->Append(schmp);
- } // endif schmp
-
- oom |= Query->Append('.');
- } else if (schmp) {
- oom |= Query->Append(schmp);
- oom |= Query->Append('.');
- } // endif schmp
-
- // Table name can be encoded in UTF-8
- Decode(TableName, buf, sizeof(buf));
-
- if (Quote) {
- // Put table name between identifier quotes in case in contains blanks
- oom |= Query->Append(Quote);
- oom |= Query->Append(buf);
- oom |= Query->Append(Quote);
- } else
- oom |= Query->Append(buf);
-
- len = Query->GetLength();
-
- if (To_CondFil) {
- if (Mode == MODE_READ) {
- oom |= Query->Append(" WHERE ");
- oom |= Query->Append(To_CondFil->Body);
- len = Query->GetLength() + 1;
- } else
- len += (strlen(To_CondFil->Body) + 256);
-
- } else
- len += ((Mode == MODE_READX) ? 256 : 1);
-
- if (oom || Query->Resize(len)) {
- strcpy(g->Message, "MakeSQL: Out of memory");
- return true;
- } // endif oom
-
- if (trace)
- htrc("Query=%s\n", Query->GetStr());
-
- return false;
-} // end of MakeSQL
-
/***********************************************************************/
/* MakeInsert: make the Insert statement used with JDBC connection. */
/***********************************************************************/
@@ -601,7 +421,7 @@ bool TDBJDBC::MakeInsert(PGLOBAL g)
// Column name can be encoded in UTF-8
Decode(colp->GetName(), buf, sizeof(buf));
len += (strlen(buf) + 6); // comma + quotes + valist
- ((PJDBCCOL)colp)->Rank = ++Nparm;
+ ((PEXTCOL)colp)->SetRank(++Nparm);
} // endif colp
// Below 32 is enough to contain the fixed part of the query
@@ -711,76 +531,6 @@ bool TDBJDBC::SetParameters(PGLOBAL g)
} // end of SetParameters
/***********************************************************************/
-/* MakeCommand: make the Update or Delete statement to send to the */
-/* MySQL server. Limited to remote values and filtering. */
-/***********************************************************************/
-bool TDBJDBC::MakeCommand(PGLOBAL g)
-{
- char *p, *stmt, name[68], *body = NULL, *qc = Jcp->GetQuoteChar();
- char *qrystr = (char*)PlugSubAlloc(g, NULL, strlen(Qrystr) + 1);
- bool qtd = Quoted > 0;
- int i = 0, k = 0;
-
- // Make a lower case copy of the originale query and change
- // back ticks to the data source identifier quoting character
- do {
- qrystr[i] = (Qrystr[i] == '`') ? *qc : tolower(Qrystr[i]);
- } while (Qrystr[i++]);
-
- if (To_CondFil && (p = strstr(qrystr, " where "))) {
- p[7] = 0; // Remove where clause
- Qrystr[(p - qrystr) + 7] = 0;
- body = To_CondFil->Body;
- stmt = (char*)PlugSubAlloc(g, NULL, strlen(qrystr)
- + strlen(body) + 64);
- } else
- stmt = (char*)PlugSubAlloc(g, NULL, strlen(Qrystr) + 64);
-
- // Check whether the table name is equal to a keyword
- // If so, it must be quoted in the original query
- strlwr(strcat(strcat(strcpy(name, " "), Name), " "));
-
- if (strstr(" update delete low_priority ignore quick from ", name)) {
- strlwr(strcat(strcat(strcpy(name, qc), Name), qc));
- k += 2;
- } else
- strlwr(strcpy(name, Name)); // Not a keyword
-
- if ((p = strstr(qrystr, name))) {
- for (i = 0; i < p - qrystr; i++)
- stmt[i] = (Qrystr[i] == '`') ? *qc : Qrystr[i];
-
- stmt[i] = 0;
- k += i + (int)strlen(Name);
-
- if (qtd && *(p-1) == ' ')
- strcat(strcat(strcat(stmt, qc), TableName), qc);
- else
- strcat(stmt, TableName);
-
- i = (int)strlen(stmt);
-
- do {
- stmt[i++] = (Qrystr[k] == '`') ? *qc : Qrystr[k];
- } while (Qrystr[k++]);
-
- if (body)
- strcat(stmt, body);
-
- } else {
- sprintf(g->Message, "Cannot use this %s command",
- (Mode == MODE_UPDATE) ? "UPDATE" : "DELETE");
- return 1;
- } // endif p
-
- if (trace)
- htrc("Command=%s\n", stmt);
-
- Query = new(g)STRING(g, 0, stmt);
- return (!Query->GetSize());
-} // end of MakeCommand
-
-/***********************************************************************/
/* ResetSize: call by TDBMUL when calculating size estimate. */
/***********************************************************************/
void TDBJDBC::ResetSize(void)
@@ -834,33 +584,6 @@ int TDBJDBC::Cardinality(PGLOBAL g)
} // end of Cardinality
/***********************************************************************/
-/* JDBC GetMaxSize: returns table size estimate in number of lines. */
-/***********************************************************************/
-int TDBJDBC::GetMaxSize(PGLOBAL g)
-{
- if (MaxSize < 0) {
- if (Mode == MODE_DELETE)
- // Return 0 in mode DELETE in case of delete all.
- MaxSize = 0;
- else if (!Cardinality(NULL))
- MaxSize = 10; // To make MySQL happy
- else if ((MaxSize = Cardinality(g)) < 0)
- MaxSize = 12; // So we can see an error occured
-
- } // endif MaxSize
-
- return MaxSize;
-} // end of GetMaxSize
-
-/***********************************************************************/
-/* Return max size value. */
-/***********************************************************************/
-int TDBJDBC::GetProgMax(PGLOBAL g)
-{
- return GetMaxSize(g);
-} // end of GetProgMax
-
-/***********************************************************************/
/* JDBC Access Method opening routine. */
/* New method now that this routine is called recursively (last table */
/* first in reverse order): index blocks are immediately linked to */
@@ -997,6 +720,7 @@ bool TDBJDBC::OpenDB(PGLOBAL g)
return false;
} // end of OpenDB
+#if 0
/***********************************************************************/
/* GetRecpos: return the position of last read record. */
/***********************************************************************/
@@ -1004,6 +728,7 @@ int TDBJDBC::GetRecpos(void)
{
return Fpos;
} // end of GetRecpos
+#endif // 0
/***********************************************************************/
/* SetRecpos: set the position of next read record. */
@@ -1105,8 +830,7 @@ int TDBJDBC::ReadDB(PGLOBAL g)
int rc;
if (trace > 1)
- htrc("JDBC ReadDB: R%d Mode=%d key=%p link=%p Kindex=%p\n",
- GetTdb_No(), Mode, To_Key_Col, To_Link, To_Kindex);
+ htrc("JDBC ReadDB: R%d Mode=%d\n", GetTdb_No(), Mode);
if (Mode == MODE_UPDATE || Mode == MODE_DELETE) {
if (!Query && MakeCommand(g))
@@ -1125,12 +849,6 @@ int TDBJDBC::ReadDB(PGLOBAL g)
} // endif Mode
- if (To_Kindex) {
- // Direct access of JDBC tables is not implemented
- strcpy(g->Message, "No JDBC direct access");
- return RC_FX;
- } // endif To_Kindex
-
/*********************************************************************/
/* Now start the reading process. */
/* Here is the place to fetch the line(s). */
@@ -1302,70 +1020,26 @@ void TDBJDBC::CloseDB(PGLOBAL g)
/* JDBCCOL public constructor. */
/***********************************************************************/
JDBCCOL::JDBCCOL(PCOLDEF cdp, PTDB tdbp, PCOL cprec, int i, PSZ am)
- : COLBLK(cdp, tdbp, i)
+ : EXTCOL(cdp, tdbp, cprec, i, am)
{
- if (cprec) {
- Next = cprec->GetNext();
- cprec->SetNext(this);
- } else {
- Next = tdbp->GetColumns();
- tdbp->SetColumns(this);
- } // endif cprec
-
- // Set additional JDBC access method information for column.
- Crp = NULL;
- //Long = cdp->GetLong();
- Long = Precision;
- //strcpy(F_Date, cdp->F_Date);
- To_Val = NULL;
-//Slen = 0;
-//StrLen = &Slen;
-//Sqlbuf = NULL;
- Bufp = NULL;
- Blkp = NULL;
- Rank = 0; // Not known yet
-
- if (trace)
- htrc(" making new %sCOL C%d %s at %p\n", am, Index, Name, this);
-
} // end of JDBCCOL constructor
/***********************************************************************/
/* JDBCCOL private constructor. */
/***********************************************************************/
-JDBCCOL::JDBCCOL(void) : COLBLK()
+JDBCCOL::JDBCCOL(void) : EXTCOL()
{
- Crp = NULL;
- Buf_Type = TYPE_INT; // This is a count(*) column
- // Set additional Dos access method information for column.
- Long = sizeof(int);
- To_Val = NULL;
-//Slen = 0;
-//StrLen = &Slen;
-//Sqlbuf = NULL;
- Bufp = NULL;
- Blkp = NULL;
- Rank = 1;
} // end of JDBCCOL constructor
/***********************************************************************/
/* JDBCCOL constructor used for copying columns. */
/* tdbp is the pointer to the new table descriptor. */
/***********************************************************************/
-JDBCCOL::JDBCCOL(JDBCCOL *col1, PTDB tdbp) : COLBLK(col1, tdbp)
+JDBCCOL::JDBCCOL(JDBCCOL *col1, PTDB tdbp) : EXTCOL(col1, tdbp)
{
- Crp = col1->Crp;
- Long = col1->Long;
- //strcpy(F_Date, col1->F_Date);
- To_Val = col1->To_Val;
-//Slen = col1->Slen;
-//StrLen = col1->StrLen;
-//Sqlbuf = col1->Sqlbuf;
- Bufp = col1->Bufp;
- Blkp = col1->Blkp;
- Rank = col1->Rank;
} // end of JDBCCOL copy constructor
+#if 0
/***********************************************************************/
/* SetBuffer: prepare a column block for write operation. */
/***********************************************************************/
@@ -1411,6 +1085,7 @@ bool JDBCCOL::SetBuffer(PGLOBAL g, PVAL value, bool ok, bool check)
Status = (ok) ? BUF_EMPTY : BUF_NO;
return false;
} // end of SetBuffer
+#endif // 0
/***********************************************************************/
/* ReadColumn: when SQLFetch is used there is nothing to do as the */
@@ -1456,72 +1131,8 @@ void JDBCCOL::ReadColumn(PGLOBAL g)
} // end of ReadColumn
-#if 0
/***********************************************************************/
-/* AllocateBuffers: allocate the extended buffer for SQLExtendedFetch */
-/* or Fetch. Note: we use Long+1 here because JDBC must have space */
-/* for the ending null character. */
-/***********************************************************************/
-void JDBCCOL::AllocateBuffers(PGLOBAL g, int rows)
-{
- if (Buf_Type == TYPE_DATE)
- Sqlbuf = (TIMESTAMP_STRUCT*)PlugSubAlloc(g, NULL,
- sizeof(TIMESTAMP_STRUCT));
-
- if (!rows)
- return;
-
- if (Buf_Type == TYPE_DATE)
- Bufp = PlugSubAlloc(g, NULL, rows * sizeof(TIMESTAMP_STRUCT));
- else {
- Blkp = AllocValBlock(g, NULL, Buf_Type, rows, GetBuflen(),
- GetScale(), true, false, false);
- Bufp = Blkp->GetValPointer();
- } // endelse
-
- if (rows > 1)
- StrLen = (SQLLEN *)PlugSubAlloc(g, NULL, rows * sizeof(SQLLEN));
-
-} // end of AllocateBuffers
-
-/***********************************************************************/
-/* Returns the buffer to use for Fetch or Extended Fetch. */
-/***********************************************************************/
-void *JDBCCOL::GetBuffer(DWORD rows)
-{
- if (rows && To_Tdb) {
- assert(rows == (DWORD)((TDBJDBC*)To_Tdb)->Rows);
- return Bufp;
- } else
- return (Buf_Type == TYPE_DATE) ? Sqlbuf : Value->GetTo_Val();
-
-} // end of GetBuffer
-
-/***********************************************************************/
-/* Returns the buffer length to use for Fetch or Extended Fetch. */
-/***********************************************************************/
-SWORD JDBCCOL::GetBuflen(void)
-{
- SWORD flen;
-
- switch (Buf_Type) {
- case TYPE_DATE:
- flen = (SWORD)sizeof(TIMESTAMP_STRUCT);
- break;
- case TYPE_STRING:
- case TYPE_DECIM:
- flen = (SWORD)Value->GetClen() + 1;
- break;
- default:
- flen = (SWORD)Value->GetClen();
- } // endswitch Buf_Type
-
- return flen;
-} // end of GetBuflen
-#endif // 0
-
-/***********************************************************************/
-/* WriteColumn: make sure the bind buffer is updated. */
+/* WriteColumn: Convert if necessary. */
/***********************************************************************/
void JDBCCOL::WriteColumn(PGLOBAL g)
{
@@ -1531,30 +1142,6 @@ void JDBCCOL::WriteColumn(PGLOBAL g)
if (Value != To_Val)
Value->SetValue_pval(To_Val, FALSE); // Convert the inserted value
-#if 0
- if (Buf_Type == TYPE_DATE) {
- struct tm tm, *dbtime = ((DTVAL*)Value)->GetGmTime(&tm);
-
- Sqlbuf->second = dbtime->tm_sec;
- Sqlbuf->minute = dbtime->tm_min;
- Sqlbuf->hour = dbtime->tm_hour;
- Sqlbuf->day = dbtime->tm_mday;
- Sqlbuf->month = dbtime->tm_mon + 1;
- Sqlbuf->year = dbtime->tm_year + 1900;
- Sqlbuf->fraction = 0;
- } else if (Buf_Type == TYPE_DECIM) {
- // Some data sources require local decimal separator
- char *p, sep = ((PTDBJDBC)To_Tdb)->Sep;
-
- if (sep && (p = strchr(Value->GetCharValue(), '.')))
- *p = sep;
-
- } // endif Buf_Type
-
- if (Nullable)
- *StrLen = (Value->IsNull()) ? SQL_NULL_DATA :
- (IsTypeChar(Buf_Type)) ? SQL_NTS : 0;
-#endif // 0
} // end of WriteColumn
/* -------------------------- Class TDBXJDC -------------------------- */
@@ -1795,7 +1382,7 @@ TDBJTB::TDBJTB(PJDBCDEF tdp) : TDBJDRV(tdp)
{
Schema = tdp->Tabschema;
Tab = tdp->Tabname;
- Tabtype = tdp->Tabtype;
+ Tabtype = tdp->Tabtyp;
Ops.Driver = tdp->Driver;
Ops.Url = tdp->Url;
Ops.User = tdp->Username;
diff --git a/storage/connect/tabjdbc.h b/storage/connect/tabjdbc.h
index fee8223abaf..46d2073e923 100644
--- a/storage/connect/tabjdbc.h
+++ b/storage/connect/tabjdbc.h
@@ -21,7 +21,7 @@ typedef class JSRCCOL *PJSRCCOL;
/***********************************************************************/
/* JDBC table. */
/***********************************************************************/
-class DllExport JDBCDEF : public TABDEF { /* Logical table description */
+class DllExport JDBCDEF : public EXTDEF { /* Logical table description */
friend class TDBJDBC;
friend class TDBXJDC;
friend class TDBJDRV;
@@ -33,17 +33,8 @@ public:
// Implementation
virtual const char *GetType(void) { return "JDBC"; }
- PSZ GetTabname(void) { return Tabname; }
- PSZ GetTabschema(void) { return Tabschema; }
- PSZ GetTabcat(void) { return Tabcat; }
- PSZ GetSrcdef(void) { return Srcdef; }
- char GetSep(void) { return (Sep) ? *Sep : 0; }
- int GetQuoted(void) { return Quoted; }
-//int GetCatver(void) { return Catver; }
- int GetOptions(void) { return Options; }
// Methods
- virtual int Indexable(void) { return 2; }
virtual bool DefineAM(PGLOBAL g, LPCSTR am, int poff);
virtual PTDB GetTable(PGLOBAL g, MODE m);
int ParseURL(PGLOBAL g, char *url, bool b = true);
@@ -53,28 +44,7 @@ protected:
// Members
PSZ Driver; /* JDBC driver */
PSZ Url; /* JDBC driver URL */
- PSZ Tabname; /* External table name */
PSZ Wrapname; /* Java wrapper name */
- PSZ Tabschema; /* External table schema */
- PSZ Username; /* User connect name */
- PSZ Password; /* Password connect info */
-//PSZ Prop; /* Connection Properties */
- PSZ Tabcat; /* External table catalog */
- PSZ Tabtype; /* External table type */
- PSZ Colpat; /* Catalog column pattern */
- PSZ Srcdef; /* The source table SQL definition */
- PSZ Qchar; /* Identifier quoting character */
- PSZ Qrystr; /* The original query */
- PSZ Sep; /* Decimal separator */
- int Options; /* Open connection options */
-//int Cto; /* Open connection timeout */
-//int Qto; /* Query (command) timeout */
- int Quoted; /* Identifier quoting level */
- int Maxerr; /* Maxerr for an Exec table */
- int Maxres; /* Maxres for a catalog table */
- int Memory; /* Put result set in memory */
- bool Scrollable; /* Use scrollable cursor */
- bool Xsrc; /* Execution type */
}; // end of JDBCDEF
#if !defined(NJDBC)
@@ -84,34 +54,34 @@ protected:
/* This is the JDBC Access Method class declaration for files from */
/* other DB drivers to be accessed via JDBC. */
/***********************************************************************/
-class TDBJDBC : public TDBASE {
+class TDBJDBC : public TDBEXT {
friend class JDBCCOL;
friend class JDBConn;
public:
// Constructor
TDBJDBC(PJDBCDEF tdp = NULL);
- TDBJDBC(PTDBJDBC tdbp);
+ TDBJDBC(PTDBJDBC tdbp);
// Implementation
- virtual AMT GetAmType(void) { return TYPE_AM_JDBC; }
- virtual PTDB Duplicate(PGLOBAL g) { return (PTDB)new(g)TDBJDBC(this); }
+ virtual AMT GetAmType(void) {return TYPE_AM_JDBC;}
+ virtual PTDB Duplicate(PGLOBAL g) {return (PTDB)new(g) TDBJDBC(this);}
// Methods
- virtual PTDB CopyOne(PTABS t);
- virtual int GetRecpos(void);
+ virtual PTDB Clone(PTABS t);
+//virtual int GetRecpos(void);
virtual bool SetRecpos(PGLOBAL g, int recpos);
//virtual PSZ GetFile(PGLOBAL g);
//virtual void SetFile(PGLOBAL g, PSZ fn);
virtual void ResetSize(void);
- //virtual int GetAffectedRows(void) {return AftRows;}
+//virtual int GetAffectedRows(void) {return AftRows;}
virtual PSZ GetServer(void) { return "JDBC"; }
virtual int Indexable(void) { return 2; }
// Database routines
virtual PCOL MakeCol(PGLOBAL g, PCOLDEF cdp, PCOL cprec, int n);
virtual int Cardinality(PGLOBAL g);
- virtual int GetMaxSize(PGLOBAL g);
- virtual int GetProgMax(PGLOBAL g);
+//virtual int GetMaxSize(PGLOBAL g);
+//virtual int GetProgMax(PGLOBAL g);
virtual bool OpenDB(PGLOBAL g);
virtual int ReadDB(PGLOBAL g);
virtual int WriteDB(PGLOBAL g);
@@ -121,97 +91,50 @@ public:
protected:
// Internal functions
- int Decode(char *utf, char *buf, size_t n);
- bool MakeSQL(PGLOBAL g, bool cnt);
+//int Decode(char *utf, char *buf, size_t n);
+//bool MakeSQL(PGLOBAL g, bool cnt);
bool MakeInsert(PGLOBAL g);
- bool MakeCommand(PGLOBAL g);
- //bool MakeFilter(PGLOBAL g, bool c);
+//virtual bool MakeCommand(PGLOBAL g);
+//bool MakeFilter(PGLOBAL g, bool c);
bool SetParameters(PGLOBAL g);
- //char *MakeUpdate(PGLOBAL g);
- //char *MakeDelete(PGLOBAL g);
+//char *MakeUpdate(PGLOBAL g);
+//char *MakeDelete(PGLOBAL g);
// Members
JDBConn *Jcp; // Points to a JDBC connection class
JDBCCOL *Cnp; // Points to count(*) column
JDBCPARM Ops; // Additional parameters
- PSTRG Query; // Constructed SQL query
char *WrapName; // Points to Java wrapper name
- char *TableName; // Points to JDBC table name
- char *Schema; // Points to JDBC table Schema
- char *User; // User connect info
- char *Pwd; // Password connect info
- char *Catalog; // Points to JDBC table Catalog
- char *Srcdef; // The source table SQL definition
- char *Count; // Points to count(*) SQL statement
-//char *Where; // Points to local where clause
- char *Quote; // The identifier quoting character
- char *MulConn; // Used for multiple JDBC tables
- char *DBQ; // The address part of Connect string
- char *Qrystr; // The original query
- char Sep; // The decimal separator
- int Options; // Connect options
-//int Cto; // Connect timeout
-//int Qto; // Query timeout
- int Quoted; // The identifier quoting level
- int Fpos; // Position of last read record
- int Curpos; // Cursor position of last fetch
- int AftRows; // The number of affected rows
- int Rows; // Rowset size
- int CurNum; // Current buffer line number
- int Rbuf; // Number of lines read in buffer
- int BufSize; // Size of connect string buffer
- int Ncol; // The column number
- int Nparm; // The number of statement parameters
- int Memory; // 0: No 1: Alloc 2: Put 3: Get
-//bool Scrollable; // Use scrollable cursor --> in Ops
- bool Placed; // True for position reading
+//int Ncol; // The column number
bool Prepared; // True when using prepared statement
bool Werr; // Write error
bool Rerr; // Rewind error
- PQRYRES Qrp; // Points to storage result
}; // end of class TDBJDBC
/***********************************************************************/
/* Class JDBCCOL: JDBC access method column descriptor. */
/* This A.M. is used for JDBC tables. */
/***********************************************************************/
-class JDBCCOL : public COLBLK {
+class JDBCCOL : public EXTCOL {
friend class TDBJDBC;
public:
// Constructors
JDBCCOL(PCOLDEF cdp, PTDB tdbp, PCOL cprec, int i, PSZ am = "JDBC");
- JDBCCOL(JDBCCOL *colp, PTDB tdbp); // Constructor used in copy process
+ JDBCCOL(JDBCCOL *colp, PTDB tdbp); // Constructor used in copy process
// Implementation
- virtual int GetAmType(void) { return TYPE_AM_JDBC; }
-//SQLLEN *GetStrLen(void) { return StrLen; }
- int GetRank(void) { return Rank; }
-//PVBLK GetBlkp(void) {return Blkp;}
- void SetCrp(PCOLRES crp) { Crp = crp; }
+ virtual int GetAmType(void) { return TYPE_AM_JDBC; }
// Methods
- virtual bool SetBuffer(PGLOBAL g, PVAL value, bool ok, bool check);
- virtual void ReadColumn(PGLOBAL g);
- virtual void WriteColumn(PGLOBAL g);
-//void AllocateBuffers(PGLOBAL g, int rows);
-//void *GetBuffer(DWORD rows);
-//SWORD GetBuflen(void);
- // void Print(PGLOBAL g, FILE *, uint);
+//virtual bool SetBuffer(PGLOBAL g, PVAL value, bool ok, bool check);
+ virtual void ReadColumn(PGLOBAL g);
+ virtual void WriteColumn(PGLOBAL g);
protected:
- // Constructor used by GetMaxSize
- JDBCCOL(void);
+ // Constructor for count(*) column
+ JDBCCOL(void);
// Members
- //TIMESTAMP_STRUCT *Sqlbuf; // To get SQL_TIMESTAMP's
- PCOLRES Crp; // To storage result
- void *Bufp; // To extended buffer
- PVBLK Blkp; // To Value Block
- //char F_Date[12]; // Internal Date format
- PVAL To_Val; // To value used for Insert
-//SQLLEN *StrLen; // As returned by JDBC
-//SQLLEN Slen; // Used with Fetch
- int Rank; // Rank (position) number in the query
}; // end of class JDBCCOL
/***********************************************************************/
@@ -268,7 +191,7 @@ public:
JSRCCOL(PCOLDEF cdp, PTDB tdbp, PCOL cprec, int i, PSZ am = "JDBC");
// Implementation
- //virtual int GetAmType(void) {return TYPE_AM_JDBC;}
+ virtual int GetAmType(void) {return TYPE_AM_JDBC;}
// Methods
virtual void ReadColumn(PGLOBAL g);
diff --git a/storage/connect/tabjson.cpp b/storage/connect/tabjson.cpp
index 1b9ce8b64c9..1e11d454cfc 100644
--- a/storage/connect/tabjson.cpp
+++ b/storage/connect/tabjson.cpp
@@ -129,7 +129,7 @@ PQRYRES JSONColumns(PGLOBAL g, char *db, PTOS topt, bool info)
if (tdp->Pretty == 2) {
if (tdp->Zipped) {
#if defined(ZIP_SUPPORT)
- tjsp = new(g) TDBJSON(tdp, new(g) ZIPFAM(tdp));
+ tjsp = new(g) TDBJSON(tdp, new(g) UNZFAM(tdp));
#else // !ZIP_SUPPORT
sprintf(g->Message, MSG(NO_FEAT_SUPPORT), "ZIP");
return NULL;
@@ -151,7 +151,7 @@ PQRYRES JSONColumns(PGLOBAL g, char *db, PTOS topt, bool info)
if (tdp->Zipped) {
#if defined(ZIP_SUPPORT)
- tjnp = new(g)TDBJSN(tdp, new(g)ZIPFAM(tdp));
+ tjnp = new(g)TDBJSN(tdp, new(g)UNZFAM(tdp));
#else // !ZIP_SUPPORT
sprintf(g->Message, MSG(NO_FEAT_SUPPORT), "ZIP");
return NULL;
@@ -441,7 +441,14 @@ PTDB JSONDEF::GetTable(PGLOBAL g, MODE m)
if (Zipped) {
#if defined(ZIP_SUPPORT)
- txfp = new(g) ZIPFAM(this);
+ if (m == MODE_READ || m == MODE_UPDATE) {
+ txfp = new(g) UNZFAM(this);
+ } else if (m == MODE_INSERT) {
+ txfp = new(g) ZIPFAM(this);
+ } else {
+ strcpy(g->Message, "UPDATE/DELETE not supported for ZIP");
+ return NULL;
+ } // endif's m
#else // !ZIP_SUPPORT
sprintf(g->Message, MSG(NO_FEAT_SUPPORT), "ZIP");
return NULL;
@@ -479,7 +486,15 @@ PTDB JSONDEF::GetTable(PGLOBAL g, MODE m)
} else {
if (Zipped) {
#if defined(ZIP_SUPPORT)
- txfp = new(g)ZIPFAM(this);
+ if (m == MODE_READ || m == MODE_UPDATE) {
+ txfp = new(g) UNZFAM(this);
+ } else if (m == MODE_INSERT) {
+ strcpy(g->Message, "INSERT supported only for zipped JSON when pretty=0");
+ return NULL;
+ } else {
+ strcpy(g->Message, "UPDATE/DELETE not supported for ZIP");
+ return NULL;
+ } // endif's m
#else // !ZIP_SUPPORT
sprintf(g->Message, MSG(NO_FEAT_SUPPORT), "ZIP");
return NULL;
@@ -559,7 +574,7 @@ TDBJSN::TDBJSN(TDBJSN *tdbp) : TDBDOS(NULL, tdbp)
} // end of TDBJSN copy constructor
// Used for update
-PTDB TDBJSN::CopyOne(PTABS t)
+PTDB TDBJSN::Clone(PTABS t)
{
G = NULL;
PTDB tp;
@@ -574,7 +589,7 @@ PTDB TDBJSN::CopyOne(PTABS t)
} // endfor cp1
return tp;
- } // end of CopyOne
+ } // end of Clone
/***********************************************************************/
/* Allocate JSN column description block. */
@@ -1563,7 +1578,7 @@ TDBJSON::TDBJSON(PJTDB tdbp) : TDBJSN(tdbp)
} // end of TDBJSON copy constructor
// Used for update
-PTDB TDBJSON::CopyOne(PTABS t)
+PTDB TDBJSON::Clone(PTABS t)
{
PTDB tp;
PJCOL cp1, cp2;
@@ -1577,7 +1592,7 @@ PTDB TDBJSON::CopyOne(PTABS t)
} // endfor cp1
return tp;
- } // end of CopyOne
+ } // end of Clone
/***********************************************************************/
/* Make the document tree from the object path. */
diff --git a/storage/connect/tabjson.h b/storage/connect/tabjson.h
index c9d30d48f2a..924ce387900 100644
--- a/storage/connect/tabjson.h
+++ b/storage/connect/tabjson.h
@@ -82,7 +82,7 @@ public:
void SetG(PGLOBAL g) {G = g;}
// Methods
- virtual PTDB CopyOne(PTABS t);
+ virtual PTDB Clone(PTABS t);
virtual PCOL MakeCol(PGLOBAL g, PCOLDEF cdp, PCOL cprec, int n);
virtual PCOL InsertSpecialColumn(PCOL colp);
virtual int RowNumber(PGLOBAL g, bool b = FALSE)
@@ -188,7 +188,7 @@ class TDBJSON : public TDBJSN {
PJAR GetDoc(void) {return Doc;}
// Methods
- virtual PTDB CopyOne(PTABS t);
+ virtual PTDB Clone(PTABS t);
// Database routines
virtual int Cardinality(PGLOBAL g);
diff --git a/storage/connect/table.cpp b/storage/connect/table.cpp
index c21bb1660ea..916449be6c6 100644
--- a/storage/connect/table.cpp
+++ b/storage/connect/table.cpp
@@ -1,7 +1,7 @@
/************** Table C++ Functions Source Code File (.CPP) ************/
-/* Name: TABLE.CPP Version 2.7 */
+/* Name: TABLE.CPP Version 2.8 */
/* */
-/* (C) Copyright to the author Olivier BERTRAND 1999-2016 */
+/* (C) Copyright to the author Olivier BERTRAND 1999-2017 */
/* */
/* This file contains the TBX, TDB and OPJOIN classes functions. */
/***********************************************************************/
@@ -10,6 +10,7 @@
/* Include relevant MariaDB header file. */
/***********************************************************************/
#include "my_global.h"
+#include "sql_string.h"
/***********************************************************************/
/* Include required application header files */
@@ -40,8 +41,9 @@ void AddPointer(PTABS, void *);
/* TDB public constructors. */
/***********************************************************************/
TDB::TDB(PTABDEF tdp) : Tdb_No(++Tnum)
- {
- Use = USE_NO;
+{
+ To_Def = tdp;
+ Use = USE_NO;
To_Orig = NULL;
To_Filter = NULL;
To_CondFil = NULL;
@@ -49,14 +51,20 @@ TDB::TDB(PTABDEF tdp) : Tdb_No(++Tnum)
Name = (tdp) ? tdp->GetName() : NULL;
To_Table = NULL;
Columns = NULL;
- Degree = (tdp) ? tdp->GetDegree() : 0;
+ To_SetCols = NULL;
+ Degree = (tdp) ? tdp->GetDegree() : 0;
Mode = MODE_ANY;
Cardinal = -1;
- } // end of TDB standard constructor
+ MaxSize = -1;
+ Read_Only = (tdp) ? tdp->IsReadOnly() : false;
+ m_data_charset = (tdp) ? tdp->data_charset() : NULL;
+ csname = (tdp) ? tdp->csname : NULL;
+} // end of TDB standard constructor
TDB::TDB(PTDB tdbp) : Tdb_No(++Tnum)
- {
- Use = tdbp->Use;
+{
+ To_Def = tdbp->To_Def;
+ Use = tdbp->Use;
To_Orig = tdbp;
To_Filter = NULL;
To_CondFil = NULL;
@@ -64,12 +72,192 @@ TDB::TDB(PTDB tdbp) : Tdb_No(++Tnum)
Name = tdbp->Name;
To_Table = tdbp->To_Table;
Columns = NULL;
- Degree = tdbp->Degree;
+ To_SetCols = tdbp->To_SetCols; // ???
+ Degree = tdbp->Degree;
Mode = tdbp->Mode;
Cardinal = tdbp->Cardinal;
- } // end of TDB copy constructor
+ MaxSize = tdbp->MaxSize;
+ Read_Only = tdbp->IsReadOnly();
+ m_data_charset = tdbp->data_charset();
+ csname = tdbp->csname;
+} // end of TDB copy constructor
// Methods
+/***********************************************************************/
+/* Return the pointer on the charset of this table. */
+/***********************************************************************/
+CHARSET_INFO *TDB::data_charset(void)
+{
+ // If no DATA_CHARSET is specified, we assume that character
+ // set of the remote data is the same with CHARACTER SET
+ // definition of the SQL column.
+ return m_data_charset ? m_data_charset : &my_charset_bin;
+} // end of data_charset
+
+/***********************************************************************/
+/* Return the datapath of the DB this table belongs to. */
+/***********************************************************************/
+PSZ TDB::GetPath(void)
+{
+ return To_Def->GetPath();
+} // end of GetPath
+
+/***********************************************************************/
+/* Return true if name is a special column of this table. */
+/***********************************************************************/
+bool TDB::IsSpecial(PSZ name)
+{
+ for (PCOLDEF cdp = To_Def->GetCols(); cdp; cdp = cdp->GetNext())
+ if (!stricmp(cdp->GetName(), name) && (cdp->Flags & U_SPECIAL))
+ return true; // Special column to ignore while inserting
+
+ return false; // Not found or not special or not inserting
+} // end of IsSpecial
+
+/***********************************************************************/
+/* Initialize TDB based column description block construction. */
+/* name is used to call columns by name. */
+/* num is used by TBL to construct columns by index number. */
+/* Note: name=Null and num=0 for constructing all columns (select *) */
+/***********************************************************************/
+PCOL TDB::ColDB(PGLOBAL g, PSZ name, int num)
+{
+ int i;
+ PCOLDEF cdp;
+ PCOL cp, colp = NULL, cprec = NULL;
+
+ if (trace)
+ htrc("ColDB: am=%d colname=%s tabname=%s num=%d\n",
+ GetAmType(), SVP(name), Name, num);
+
+ for (cdp = To_Def->GetCols(), i = 1; cdp; cdp = cdp->GetNext(), i++)
+ if ((!name && !num) ||
+ (name && !stricmp(cdp->GetName(), name)) || num == i) {
+ /*****************************************************************/
+ /* Check for existence of desired column. */
+ /* Also find where to insert the new block. */
+ /*****************************************************************/
+ for (cp = Columns; cp; cp = cp->GetNext())
+ if ((num && cp->GetIndex() == i) ||
+ (name && !stricmp(cp->GetName(), name)))
+ break; // Found
+ else if (cp->GetIndex() < i)
+ cprec = cp;
+
+ if (trace)
+ htrc("cdp(%d).Name=%s cp=%p\n", i, cdp->GetName(), cp);
+
+ /*****************************************************************/
+ /* Now take care of Column Description Block. */
+ /*****************************************************************/
+ if (cp)
+ colp = cp;
+ else if (!(cdp->Flags & U_SPECIAL))
+ colp = MakeCol(g, cdp, cprec, i);
+ else if (Mode != MODE_INSERT)
+ colp = InsertSpcBlk(g, cdp);
+
+ if (trace)
+ htrc("colp=%p\n", colp);
+
+ if (name || num)
+ break;
+ else if (colp && !colp->IsSpecial())
+ cprec = colp;
+
+ } // endif Name
+
+ return (colp);
+} // end of ColDB
+
+/***********************************************************************/
+/* InsertSpecialColumn: Put a special column ahead of the column list.*/
+/***********************************************************************/
+PCOL TDB::InsertSpecialColumn(PCOL colp)
+{
+ if (!colp->IsSpecial())
+ return NULL;
+
+ colp->SetNext(Columns);
+ Columns = colp;
+ return colp;
+} // end of InsertSpecialColumn
+
+/***********************************************************************/
+/* Make a special COLBLK to insert in a table. */
+/***********************************************************************/
+PCOL TDB::InsertSpcBlk(PGLOBAL g, PCOLDEF cdp)
+{
+ //char *name = cdp->GetName();
+ char *name = cdp->GetFmt();
+ PCOLUMN cp;
+ PCOL colp;
+
+ cp = new(g)COLUMN(cdp->GetName());
+
+ if (!To_Table) {
+ strcpy(g->Message, "Cannot make special column: To_Table is NULL");
+ return NULL;
+ } else
+ cp->SetTo_Table(To_Table);
+
+ if (!stricmp(name, "FILEID") || !stricmp(name, "FDISK") ||
+ !stricmp(name, "FPATH") || !stricmp(name, "FNAME") ||
+ !stricmp(name, "FTYPE") || !stricmp(name, "SERVID")) {
+ if (!To_Def || !(To_Def->GetPseudo() & 2)) {
+ sprintf(g->Message, MSG(BAD_SPEC_COLUMN));
+ return NULL;
+ } // endif Pseudo
+
+ if (!stricmp(name, "FILEID"))
+ colp = new(g)FIDBLK(cp, OP_XX);
+ else if (!stricmp(name, "FDISK"))
+ colp = new(g)FIDBLK(cp, OP_FDISK);
+ else if (!stricmp(name, "FPATH"))
+ colp = new(g)FIDBLK(cp, OP_FPATH);
+ else if (!stricmp(name, "FNAME"))
+ colp = new(g)FIDBLK(cp, OP_FNAME);
+ else if (!stricmp(name, "FTYPE"))
+ colp = new(g)FIDBLK(cp, OP_FTYPE);
+ else
+ colp = new(g)SIDBLK(cp);
+
+ } else if (!stricmp(name, "TABID")) {
+ colp = new(g)TIDBLK(cp);
+ } else if (!stricmp(name, "PARTID")) {
+ colp = new(g)PRTBLK(cp);
+ //} else if (!stricmp(name, "CONID")) {
+ // colp = new(g) CIDBLK(cp);
+ } else if (!stricmp(name, "ROWID")) {
+ colp = new(g)RIDBLK(cp, false);
+ } else if (!stricmp(name, "ROWNUM")) {
+ colp = new(g)RIDBLK(cp, true);
+ } else {
+ sprintf(g->Message, MSG(BAD_SPECIAL_COL), name);
+ return NULL;
+ } // endif's name
+
+ if (!(colp = InsertSpecialColumn(colp))) {
+ sprintf(g->Message, MSG(BAD_SPECIAL_COL), name);
+ return NULL;
+ } // endif Insert
+
+ return (colp);
+} // end of InsertSpcBlk
+
+/***********************************************************************/
+/* Marks DOS/MAP table columns used in internal joins. */
+/* tdb2 is the top of tree or first tdb in chained tdb's and tdbp */
+/* points to the currently marked tdb. */
+/* Two questions here: exact meaning of U_J_INT ? */
+/* Why is the eventual reference to To_Key_Col not marked U_J_EXT ? */
+/***********************************************************************/
+void TDB::MarkDB(PGLOBAL, PTDB tdb2)
+{
+ if (trace)
+ htrc("DOS MarkDB: tdbp=%p tdb2=%p\n", this, tdb2);
+
+} // end of MarkDB
/***********************************************************************/
/* RowNumber: returns the current row ordinal number. */
@@ -86,7 +274,7 @@ PTDB TDB::Copy(PTABS t)
//PGLOBAL g = t->G; // Is this really useful ???
for (tdb1 = this; tdb1; tdb1 = tdb1->Next) {
- tp = tdb1->CopyOne(t);
+ tp = tdb1->Clone(t);
if (!outp)
outp = tp;
@@ -100,6 +288,15 @@ PTDB TDB::Copy(PTABS t)
return outp;
} // end of Copy
+/***********************************************************************/
+/* SetRecpos: Replace the table at the specified position. */
+/***********************************************************************/
+bool TDB::SetRecpos(PGLOBAL g, int)
+{
+ strcpy(g->Message, MSG(SETRECPOS_NIY));
+ return true;
+} // end of SetRecpos
+
void TDB::Print(PGLOBAL g, FILE *f, uint n)
{
PCOL cp;
@@ -135,34 +332,34 @@ void TDB::Print(PGLOBAL, char *ps, uint)
/***********************************************************************/
TDBASE::TDBASE(PTABDEF tdp) : TDB(tdp)
{
- To_Def = tdp;
+//To_Def = tdp;
To_Link = NULL;
To_Key_Col = NULL;
To_Kindex = NULL;
To_Xdp = NULL;
- To_SetCols = NULL;
+//To_SetCols = NULL;
Ftype = RECFM_NAF;
- MaxSize = -1;
+//MaxSize = -1;
Knum = 0;
- Read_Only = (tdp) ? tdp->IsReadOnly() : false;
- m_data_charset= (tdp) ? tdp->data_charset() : NULL;
- csname = (tdp) ? tdp->csname : NULL;
+//Read_Only = (tdp) ? tdp->IsReadOnly() : false;
+//m_data_charset= (tdp) ? tdp->data_charset() : NULL;
+//csname = (tdp) ? tdp->csname : NULL;
} // end of TDBASE constructor
TDBASE::TDBASE(PTDBASE tdbp) : TDB(tdbp)
{
- To_Def = tdbp->To_Def;
+//To_Def = tdbp->To_Def;
To_Link = tdbp->To_Link;
To_Key_Col = tdbp->To_Key_Col;
To_Kindex = tdbp->To_Kindex;
To_Xdp = tdbp->To_Xdp;
- To_SetCols = tdbp->To_SetCols; // ???
+//To_SetCols = tdbp->To_SetCols; // ???
Ftype = tdbp->Ftype;
- MaxSize = tdbp->MaxSize;
+//MaxSize = tdbp->MaxSize;
Knum = tdbp->Knum;
- Read_Only = tdbp->Read_Only;
- m_data_charset= tdbp->m_data_charset;
- csname = tdbp->csname;
+//Read_Only = tdbp->Read_Only;
+//m_data_charset= tdbp->m_data_charset;
+//csname = tdbp->csname;
} // end of TDBASE copy constructor
/***********************************************************************/
@@ -173,6 +370,7 @@ PCATLG TDBASE::GetCat(void)
return (To_Def) ? To_Def->GetCat() : NULL;
} // end of GetCat
+#if 0
/***********************************************************************/
/* Return the pointer on the charset of this table. */
/***********************************************************************/
@@ -334,6 +532,7 @@ PCOL TDBASE::InsertSpcBlk(PGLOBAL g, PCOLDEF cdp)
return (colp);
} // end of InsertSpcBlk
+#endif // 0
/***********************************************************************/
/* ResetTableOpt: Wrong for this table type. */
@@ -362,6 +561,7 @@ void TDBASE::ResetKindex(PGLOBAL g, PKXBASE kxp)
To_Kindex = kxp;
} // end of ResetKindex
+#if 0
/***********************************************************************/
/* SetRecpos: Replace the table at the specified position. */
/***********************************************************************/
@@ -370,6 +570,7 @@ bool TDBASE::SetRecpos(PGLOBAL g, int)
strcpy(g->Message, MSG(SETRECPOS_NIY));
return true;
} // end of SetRecpos
+#endif // 0
/***********************************************************************/
/* Methods */
@@ -379,6 +580,7 @@ void TDBASE::PrintAM(FILE *f, char *m)
fprintf(f, "%s AM(%d): mode=%d\n", m, GetAmType(), Mode);
} // end of PrintAM
+#if 0
/***********************************************************************/
/* Marks DOS/MAP table columns used in internal joins. */
/* tdb2 is the top of tree or first tdb in chained tdb's and tdbp */
@@ -392,6 +594,7 @@ void TDBASE::MarkDB(PGLOBAL, PTDB tdb2)
htrc("DOS MarkDB: tdbp=%p tdb2=%p\n", this, tdb2);
} // end of MarkDB
+#endif // 0
/* ---------------------------TDBCAT class --------------------------- */
diff --git a/storage/connect/tabmac.cpp b/storage/connect/tabmac.cpp
index e6e2abb54e2..bbaba591540 100644
--- a/storage/connect/tabmac.cpp
+++ b/storage/connect/tabmac.cpp
@@ -12,7 +12,7 @@
#include "global.h"
#include "plgdbsem.h"
//#include "catalog.h"
-#include "reldef.h"
+//#include "reldef.h"
#include "xtable.h"
#include "colblk.h"
#include "tabmac.h"
diff --git a/storage/connect/tabmac.h b/storage/connect/tabmac.h
index f9a66e82eaa..47565bb2541 100644
--- a/storage/connect/tabmac.h
+++ b/storage/connect/tabmac.h
@@ -52,7 +52,7 @@ class TDBMAC : public TDBASE {
//virtual PTDB Duplicate(PGLOBAL g) {return (PTDB)new(g) TDBMAC(g, this);}
// Methods
-//virtual PTDB CopyOne(PTABS t);
+//virtual PTDB Clone(PTABS t);
virtual int GetRecpos(void) {return N;}
virtual int RowNumber(PGLOBAL g, bool b = false) {return N;}
diff --git a/storage/connect/tabmul.cpp b/storage/connect/tabmul.cpp
index 22499801d07..78adde81d12 100644
--- a/storage/connect/tabmul.cpp
+++ b/storage/connect/tabmul.cpp
@@ -1,11 +1,11 @@
/************* TabMul C++ Program Source Code File (.CPP) **************/
/* PROGRAM NAME: TABMUL */
/* ------------- */
-/* Version 1.7 */
+/* Version 1.8 */
/* */
/* COPYRIGHT: */
/* ---------- */
-/* (C) Copyright to PlugDB Software Development 2003 - 2015 */
+/* (C) Copyright to PlugDB Software Development 2003 - 2017 */
/* Author: Olivier BERTRAND */
/* */
/* WHAT THIS PROGRAM DOES: */
@@ -73,7 +73,7 @@
/***********************************************************************/
/* TABMUL constructors. */
/***********************************************************************/
-TDBMUL::TDBMUL(PTDBASE tdbp) : TDBASE(tdbp->GetDef())
+TDBMUL::TDBMUL(PTDB tdbp) : TDBASE(tdbp->GetDef())
{
Tdbp = tdbp;
Filenames = NULL;
@@ -94,22 +94,22 @@ TDBMUL::TDBMUL(PTDBMUL tdbp) : TDBASE(tdbp)
} // end of TDBMUL copy constructor
// Method
-PTDB TDBMUL::CopyOne(PTABS t)
+PTDB TDBMUL::Clone(PTABS t)
{
PTDBMUL tp;
PGLOBAL g = t->G; // Is this really useful ???
tp = new(g) TDBMUL(this);
- tp->Tdbp = (PTDBASE)Tdbp->CopyOne(t);
+ tp->Tdbp = Tdbp->Clone(t);
tp->Columns = tp->Tdbp->GetColumns();
return tp;
- } // end of CopyOne
+ } // end of Clone
PTDB TDBMUL::Duplicate(PGLOBAL g)
{
PTDBMUL tmup = new(g) TDBMUL(this);
- tmup->Tdbp = (PTDBASE)Tdbp->Duplicate(g);
+ tmup->Tdbp = Tdbp->Duplicate(g);
return tmup;
} // end of Duplicate
@@ -658,7 +658,7 @@ TDBDIR::TDBDIR(PTDBDIR tdbp) : TDBASE(tdbp)
} // end of TDBDIR copy constructor
// Method
-PTDB TDBDIR::CopyOne(PTABS t)
+PTDB TDBDIR::Clone(PTABS t)
{
PTDB tp;
PGLOBAL g = t->G; // Is this really useful ???
@@ -666,7 +666,7 @@ PTDB TDBDIR::CopyOne(PTABS t)
tp = new(g) TDBDIR(this);
tp->SetColumns(Columns);
return tp;
- } // end of CopyOne
+ } // end of Clone
/***********************************************************************/
/* Initialize/get the components of the search file pattern. */
@@ -711,7 +711,7 @@ int TDBDIR::GetMaxSize(PGLOBAL g)
if (MaxSize < 0) {
int n = -1;
#if defined(__WIN__)
- intptr_t h;
+ int h;
// Start searching files in the target directory.
h = _findfirst(Path(g), &FileData);
@@ -974,7 +974,7 @@ TDBSDR::TDBSDR(PTDBSDR tdbp) : TDBDIR(tdbp)
} // end of TDBSDR copy constructor
// Method
-PTDB TDBSDR::CopyOne(PTABS t)
+PTDB TDBSDR::Clone(PTABS t)
{
PTDB tp;
PGLOBAL g = t->G; // Is this really useful ???
@@ -982,7 +982,7 @@ PTDB TDBSDR::CopyOne(PTABS t)
tp = new(g) TDBSDR(this);
tp->SetColumns(Columns);
return tp;
- } // end of CopyOne
+ } // end of Clone
/***********************************************************************/
/* SDR GetMaxSize: returns the number of retrieved files. */
@@ -1007,7 +1007,7 @@ int TDBSDR::FindInDir(PGLOBAL g)
// Start searching files in the target directory.
#if defined(__WIN__)
- intptr_t h = _findfirst(Path(g), &FileData);
+ int h = _findfirst(Path(g), &FileData);
if (h != -1) {
for (n = 1;; n++)
@@ -1251,7 +1251,7 @@ TDBDHR::TDBDHR(PTDBDHR tdbp) : TDBASE(tdbp)
} // end of TDBDHR copy constructor
// Method
-PTDB TDBDHR::CopyOne(PTABS t)
+PTDB TDBDHR::Clone(PTABS t)
{
PTDB tp;
PGLOBAL g = t->G; // Is this really useful ???
@@ -1259,7 +1259,7 @@ PTDB TDBDHR::CopyOne(PTABS t)
tp = new(g) TDBDHR(this);
tp->Columns = Columns;
return tp;
- } // end of CopyOne
+ } // end of Clone
/***********************************************************************/
/* Allocate DHR column description block. */
diff --git a/storage/connect/tabmul.h b/storage/connect/tabmul.h
index 53d7198eec7..51fa7f9000a 100644
--- a/storage/connect/tabmul.h
+++ b/storage/connect/tabmul.h
@@ -1,7 +1,7 @@
/*************** Tabmul H Declares Source Code File (.H) ***************/
-/* Name: TABMUL.H Version 1.4 */
+/* Name: TABMUL.H Version 1.5 */
/* */
-/* (C) Copyright to PlugDB Software Development 2003-2012 */
+/* (C) Copyright to PlugDB Software Development 2003-2017 */
/* Author: Olivier BERTRAND */
/* */
/* This file contains the TDBMUL and TDBDIR classes declares. */
@@ -28,7 +28,7 @@ class DllExport TDBMUL : public TDBASE {
//friend class MULCOL;
public:
// Constructor
- TDBMUL(PTDBASE tdbp);
+ TDBMUL(PTDB tdbp);
TDBMUL(PTDBMUL tdbp);
// Implementation
@@ -37,7 +37,7 @@ class DllExport TDBMUL : public TDBASE {
// Methods
virtual void ResetDB(void);
- virtual PTDB CopyOne(PTABS t);
+ virtual PTDB Clone(PTABS t);
virtual bool IsSame(PTDB tp) {return tp == (PTDB)Tdbp;}
virtual PSZ GetFile(PGLOBAL g) {return Tdbp->GetFile(g);}
virtual int GetRecpos(void) {return 0;}
@@ -61,7 +61,7 @@ class DllExport TDBMUL : public TDBASE {
protected:
// Members
- TDBASE *Tdbp; // Points to a (file) table class
+ PTDB Tdbp; // Points to a (file) table class
char* *Filenames; // Points to file names
int Rows; // Total rows of already read files
int Mul; // Type of multiple file list
@@ -112,7 +112,7 @@ class TDBDIR : public TDBASE {
{return (PTDB)new(g) TDBDIR(this);}
// Methods
- virtual PTDB CopyOne(PTABS t);
+ virtual PTDB Clone(PTABS t);
virtual int GetRecpos(void) {return iFile;}
// Database routines
@@ -134,7 +134,7 @@ class TDBDIR : public TDBASE {
int iFile; // Index of currently retrieved file
#if defined(__WIN__)
_finddata_t FileData; // Find data structure
- intptr_t Hsearch; // Search handle
+ intptr_t Hsearch; // Search handle
char Drive[_MAX_DRIVE]; // Drive name
#else // !__WIN__
struct stat Fileinfo; // File info structure
@@ -168,7 +168,7 @@ class TDBSDR : public TDBDIR {
{return (PTDB)new(g) TDBSDR(this);}
// Methods
- virtual PTDB CopyOne(PTABS t);
+ virtual PTDB Clone(PTABS t);
// Database routines
virtual int GetMaxSize(PGLOBAL g);
@@ -184,7 +184,7 @@ class TDBSDR : public TDBDIR {
struct _Sub_Dir *Next;
struct _Sub_Dir *Prev;
#if defined(__WIN__)
- intptr_t H; // Search handle
+ intptr_t H; // Search handle
#else // !__WIN__
DIR *D;
#endif // !__WIN__
diff --git a/storage/connect/tabmysql.cpp b/storage/connect/tabmysql.cpp
index 98a476bf94f..1a715819fc8 100644
--- a/storage/connect/tabmysql.cpp
+++ b/storage/connect/tabmysql.cpp
@@ -1,11 +1,11 @@
/************* TabMySQL C++ Program Source Code File (.CPP) *************/
/* PROGRAM NAME: TABMYSQL */
/* ------------- */
-/* Version 1.9 */
+/* Version 2.0 */
/* */
/* AUTHOR: */
/* ------- */
-/* Olivier BERTRAND 2007-2015 */
+/* Olivier BERTRAND 2007-2017 */
/* */
/* WHAT THIS PROGRAM DOES: */
/* ----------------------- */
@@ -54,9 +54,10 @@
#include "global.h"
#include "plgdbsem.h"
#include "xtable.h"
+#include "tabext.h"
#include "tabcol.h"
#include "colblk.h"
-#include "reldef.h"
+//#include "reldef.h"
#include "tabmysql.h"
#include "valblk.h"
#include "tabutil.h"
@@ -84,16 +85,16 @@ MYSQLDEF::MYSQLDEF(void)
{
Pseudo = 2; // SERVID is Ok but not ROWID
Hostname = NULL;
- Database = NULL;
- Tabname = NULL;
- Srcdef = NULL;
- Username = NULL;
- Password = NULL;
+//Tabschema = NULL;
+//Tabname = NULL;
+//Srcdef = NULL;
+//Username = NULL;
+//Password = NULL;
Portnumber = 0;
Isview = false;
Bind = false;
Delayed = false;
- Xsrc = false;
+//Xsrc = false;
Huge = false;
} // end of MYSQLDEF constructor
@@ -128,7 +129,7 @@ bool MYSQLDEF::GetServerInfo(PGLOBAL g, const char *server_name)
// TODO: We need to examine which of these can really be NULL
Hostname = PlugDup(g, server->host);
- Database = PlugDup(g, server->db);
+ Tabschema = PlugDup(g, server->db);
Username = PlugDup(g, server->username);
Password = PlugDup(g, server->password);
Portnumber = (server->port) ? server->port : GetDefaultPort();
@@ -200,7 +201,7 @@ bool MYSQLDEF::ParseURL(PGLOBAL g, char *url, bool b)
Tabname = (b) ? GetStringCatInfo(g, "Tabname", Name) : NULL;
if (trace)
- htrc("server: %s Tabname: %s", url, Tabname);
+ htrc("server: %s TableName: %s", url, Tabname);
Server = url;
return GetServerInfo(g, url);
@@ -253,10 +254,10 @@ bool MYSQLDEF::ParseURL(PGLOBAL g, char *url, bool b)
return true;
} // endif
- if ((Database = strchr(Hostname, '/'))) {
- *Database++ = 0;
+ if ((Tabschema = strchr(Hostname, '/'))) {
+ *Tabschema++ = 0;
- if ((Tabname = strchr(Database, '/'))) {
+ if ((Tabname = strchr(Tabschema, '/'))) {
*Tabname++ = 0;
// Make sure there's not an extra /
@@ -265,7 +266,7 @@ bool MYSQLDEF::ParseURL(PGLOBAL g, char *url, bool b)
return true;
} // endif /
- } // endif Tabname
+ } // endif TableName
} // endif database
@@ -283,8 +284,8 @@ bool MYSQLDEF::ParseURL(PGLOBAL g, char *url, bool b)
if (Hostname[0] == 0)
Hostname = (b) ? GetStringCatInfo(g, "Host", "localhost") : NULL;
- if (!Database || !*Database)
- Database = (b) ? GetStringCatInfo(g, "Database", "*") : NULL;
+ if (!Tabschema || !*Tabschema)
+ Tabschema = (b) ? GetStringCatInfo(g, "Database", "*") : NULL;
if (!Tabname || !*Tabname)
Tabname = (b) ? GetStringCatInfo(g, "Tabname", Name) : NULL;
@@ -320,7 +321,7 @@ bool MYSQLDEF::DefineAM(PGLOBAL g, LPCSTR am, int)
if (!url || !*url) {
// Not using the connection URL
Hostname = GetStringCatInfo(g, "Host", "localhost");
- Database = GetStringCatInfo(g, "Database", "*");
+ Tabschema = GetStringCatInfo(g, "Database", "*");
Tabname = GetStringCatInfo(g, "Name", Name); // Deprecated
Tabname = GetStringCatInfo(g, "Tabname", Tabname);
Username = GetStringCatInfo(g, "User", "*");
@@ -334,7 +335,7 @@ bool MYSQLDEF::DefineAM(PGLOBAL g, LPCSTR am, int)
Delayed = !!GetIntCatInfo("Delayed", 0);
} else {
// MYSQL access from a PROXY table
- Database = GetStringCatInfo(g, "Database", Schema ? Schema : PlugDup(g, "*"));
+ Tabschema = GetStringCatInfo(g, "Database", Tabschema ? Tabschema : PlugDup(g, "*"));
Isview = GetBoolCatInfo("View", false);
// We must get other connection parms from the calling table
@@ -348,12 +349,12 @@ bool MYSQLDEF::DefineAM(PGLOBAL g, LPCSTR am, int)
Portnumber = GetIntCatInfo("Port", GetDefaultPort());
Server = Hostname;
} else {
- char *locdb = Database;
+ char *locdb = Tabschema;
if (ParseURL(g, url))
return true;
- Database = locdb;
+ Tabschema = locdb;
} // endif url
Tabname = Name;
@@ -362,7 +363,7 @@ bool MYSQLDEF::DefineAM(PGLOBAL g, LPCSTR am, int)
if ((Srcdef = GetStringCatInfo(g, "Srcdef", NULL))) {
Read_Only = true;
Isview = true;
- } else if (CheckSelf(g, Hc->GetTable()->s, Hostname, Database,
+ } else if (CheckSelf(g, Hc->GetTable()->s, Hostname, Tabschema,
Tabname, Srcdef, Portnumber))
return true;
@@ -372,7 +373,7 @@ bool MYSQLDEF::DefineAM(PGLOBAL g, LPCSTR am, int)
// Specific for command executing tables
Xsrc = GetBoolCatInfo("Execsrc", false);
- Mxr = GetIntCatInfo("Maxerr", 0);
+ Maxerr = GetIntCatInfo("Maxerr", 0);
Huge = GetBoolCatInfo("Huge", false);
return false;
} // end of DefineAM
@@ -396,17 +397,17 @@ PTDB MYSQLDEF::GetTable(PGLOBAL g, MODE)
/***********************************************************************/
/* Implementation of the TDBMYSQL class. */
/***********************************************************************/
-TDBMYSQL::TDBMYSQL(PMYDEF tdp) : TDBASE(tdp)
+TDBMYSQL::TDBMYSQL(PMYDEF tdp) : TDBEXT(tdp)
{
if (tdp) {
Host = tdp->Hostname;
- Database = tdp->Database;
- Tabname = tdp->Tabname;
- Srcdef = tdp->Srcdef;
- User = tdp->Username;
- Pwd = tdp->Password;
+// Schema = tdp->Tabschema;
+// TableName = tdp->Tabname;
+// Srcdef = tdp->Srcdef;
+// User = tdp->Username;
+// Pwd = tdp->Password;
Server = tdp->Server;
- Qrystr = tdp->Qrystr;
+// Qrystr = tdp->Qrystr;
Quoted = MY_MAX(0, tdp->Quoted);
Port = tdp->Portnumber;
Isview = tdp->Isview;
@@ -415,14 +416,14 @@ TDBMYSQL::TDBMYSQL(PMYDEF tdp) : TDBASE(tdp)
Myc.m_Use = tdp->Huge;
} else {
Host = NULL;
- Database = NULL;
- Tabname = NULL;
- Srcdef = NULL;
- User = NULL;
- Pwd = NULL;
+// Schema = NULL;
+// TableName = NULL;
+// Srcdef = NULL;
+// User = NULL;
+// Pwd = NULL;
Server = NULL;
- Qrystr = NULL;
- Quoted = 0;
+// Qrystr = NULL;
+// Quoted = 0;
Port = 0;
Isview = false;
Prep = false;
@@ -430,39 +431,40 @@ TDBMYSQL::TDBMYSQL(PMYDEF tdp) : TDBASE(tdp)
} // endif tdp
Bind = NULL;
- Query = NULL;
+//Query = NULL;
Fetched = false;
m_Rc = RC_FX;
- AftRows = 0;
+//AftRows = 0;
N = -1;
- Nparm = 0;
+//Nparm = 0;
} // end of TDBMYSQL constructor
-TDBMYSQL::TDBMYSQL(PTDBMY tdbp) : TDBASE(tdbp)
+TDBMYSQL::TDBMYSQL(PTDBMY tdbp) : TDBEXT(tdbp)
{
Host = tdbp->Host;
- Database = tdbp->Database;
- Tabname = tdbp->Tabname;
- Srcdef = tdbp->Srcdef;
- User = tdbp->User;
- Pwd = tdbp->Pwd;
- Qrystr = tdbp->Qrystr;
- Quoted = tdbp->Quoted;
+//Schema = tdbp->Schema;
+//TableName = tdbp->TableName;
+//Srcdef = tdbp->Srcdef;
+//User = tdbp->User;
+//Pwd = tdbp->Pwd;
+//Qrystr = tdbp->Qrystr;
+//Quoted = tdbp->Quoted;
+ Server = tdbp->Server;
Port = tdbp->Port;
Isview = tdbp->Isview;
Prep = tdbp->Prep;
Delayed = tdbp->Delayed;
Bind = NULL;
- Query = tdbp->Query;
+//Query = tdbp->Query;
Fetched = tdbp->Fetched;
m_Rc = tdbp->m_Rc;
- AftRows = tdbp->AftRows;
+//AftRows = tdbp->AftRows;
N = tdbp->N;
- Nparm = tdbp->Nparm;
+//Nparm = tdbp->Nparm;
} // end of TDBMYSQL copy constructor
-// Is this really useful ???
-PTDB TDBMYSQL::CopyOne(PTABS t)
+// Is this really useful ??? --> Yes for UPDATE
+PTDB TDBMYSQL::Clone(PTABS t)
{
PTDB tp;
PCOL cp1, cp2;
@@ -477,7 +479,7 @@ PTDB TDBMYSQL::CopyOne(PTABS t)
} // endfor cp1
return tp;
- } // end of CopyOne
+ } // end of Clone
/***********************************************************************/
/* Allocate MYSQL column description block. */
@@ -504,10 +506,18 @@ bool TDBMYSQL::MakeSelect(PGLOBAL g, bool mx)
if (Query)
return false; // already done
- if (Srcdef) {
- Query = new(g)STRING(g, 0, Srcdef);
- return false;
- } // endif Srcdef
+ if (Srcdef) {
+ if (strstr(Srcdef, "%s")) {
+ char *fil;
+
+ fil = (To_CondFil) ? To_CondFil->Body : PlugDup(g, "1=1");
+ Query = new(g)STRING(g, strlen(Srcdef) + strlen(fil));
+ Query->SetLength(sprintf(Query->GetStr(), Srcdef, fil));
+ } else
+ Query = new(g)STRING(g, 0, Srcdef);
+
+ return false;
+ } // endif Srcdef
// Allocate the string used to contain Query
Query = new(g) STRING(g, 1023, "SELECT ");
@@ -540,7 +550,7 @@ bool TDBMYSQL::MakeSelect(PGLOBAL g, bool mx)
oom |= Query->Append(" FROM ");
oom |= Query->Append(tk);
- oom |= Query->Append(Tabname);
+ oom |= Query->Append(TableName);
oom |= Query->Append(tk);
len = Query->GetLength();
@@ -608,7 +618,7 @@ bool TDBMYSQL::MakeInsert(PGLOBAL g)
} // endif colp
// Below 40 is enough to contain the fixed part of the query
- len += (strlen(Tabname) + 40);
+ len += (strlen(TableName) + 40);
Query = new(g) STRING(g, len);
if (Delayed)
@@ -617,7 +627,7 @@ bool TDBMYSQL::MakeInsert(PGLOBAL g)
oom = Query->Set("INSERT INTO ");
oom |= Query->Append(tk);
- oom |= Query->Append(Tabname);
+ oom |= Query->Append(TableName);
oom |= Query->Append("` (");
for (colp = Columns; colp; colp = colp->GetNext()) {
@@ -653,11 +663,11 @@ bool TDBMYSQL::MakeInsert(PGLOBAL g)
/* MakeCommand: make the Update or Delete statement to send to the */
/* MySQL server. Limited to remote values and filtering. */
/***********************************************************************/
-int TDBMYSQL::MakeCommand(PGLOBAL g)
+bool TDBMYSQL::MakeCommand(PGLOBAL g)
{
Query = new(g) STRING(g, strlen(Qrystr) + 64);
- if (Quoted > 0 || stricmp(Name, Tabname)) {
+ if (Quoted > 0 || stricmp(Name, TableName)) {
char *p, *qrystr, name[68];
bool qtd = Quoted > 0;
@@ -678,29 +688,29 @@ int TDBMYSQL::MakeCommand(PGLOBAL g)
if (qtd && *(p-1) == ' ') {
oom |= Query->Append('`');
- oom |= Query->Append(Tabname);
+ oom |= Query->Append(TableName);
oom |= Query->Append('`');
} else
- oom |= Query->Append(Tabname);
+ oom |= Query->Append(TableName);
oom |= Query->Append(Qrystr + (p - qrystr) + strlen(name));
if (oom) {
strcpy(g->Message, "MakeCommand: Out of memory");
- return RC_FX;
+ return true;
} else
strlwr(strcpy(qrystr, Query->GetStr()));
} else {
sprintf(g->Message, "Cannot use this %s command",
(Mode == MODE_UPDATE) ? "UPDATE" : "DELETE");
- return RC_FX;
+ return true;
} // endif p
} else
(void)Query->Set(Qrystr);
- return RC_OK;
+ return false;
} // end of MakeCommand
#if 0
@@ -727,7 +737,7 @@ int TDBMYSQL::MakeUpdate(PGLOBAL g)
} // endif sscanf
assert(!stricmp(cmd, "update"));
- strcat(strcat(strcat(strcpy(Query, "UPDATE "), qc), Tabname), qc);
+ strcat(strcat(strcat(strcpy(Query, "UPDATE "), qc), TableName), qc);
strcat(Query, end);
return RC_OK;
} // end of MakeUpdate
@@ -754,7 +764,7 @@ int TDBMYSQL::MakeDelete(PGLOBAL g)
} // endif sscanf
assert(!stricmp(cmd, "delete") && !stricmp(from, "from"));
- strcat(strcat(strcat(strcpy(Query, "DELETE FROM "), qc), Tabname), qc);
+ strcat(strcat(strcat(strcpy(Query, "DELETE FROM "), qc), TableName), qc);
if (*end)
strcat(Query, end);
@@ -776,15 +786,15 @@ int TDBMYSQL::Cardinality(PGLOBAL g)
char query[96];
MYSQLC myc;
- if (myc.Open(g, Host, Database, User, Pwd, Port, csname))
+ if (myc.Open(g, Host, Schema, User, Pwd, Port, csname))
return -1;
strcpy(query, "SELECT COUNT(*) FROM ");
if (Quoted > 0)
- strcat(strcat(strcat(query, "`"), Tabname), "`");
+ strcat(strcat(strcat(query, "`"), TableName), "`");
else
- strcat(query, Tabname);
+ strcat(query, TableName);
Cardinal = myc.GetTableSize(g, query);
myc.Close();
@@ -794,6 +804,7 @@ int TDBMYSQL::Cardinality(PGLOBAL g)
return Cardinal;
} // end of Cardinality
+#if 0
/***********************************************************************/
/* MYSQL GetMaxSize: returns the maximum number of rows in the table. */
/***********************************************************************/
@@ -812,6 +823,7 @@ int TDBMYSQL::GetMaxSize(PGLOBAL g)
return MaxSize;
} // end of GetMaxSize
+#endif // 0
/***********************************************************************/
/* This a fake routine as ROWID does not exist in MySQL. */
@@ -872,7 +884,7 @@ bool TDBMYSQL::OpenDB(PGLOBAL g)
/* servers allowing concurency in getting results ??? */
/*********************************************************************/
if (!Myc.Connected()) {
- if (Myc.Open(g, Host, Database, User, Pwd, Port, csname))
+ if (Myc.Open(g, Host, Schema, User, Pwd, Port, csname))
return true;
} // endif Connected
@@ -931,14 +943,14 @@ bool TDBMYSQL::OpenDB(PGLOBAL g)
char cmd[64];
int w;
- sprintf(cmd, "ALTER TABLE `%s` DISABLE KEYS", Tabname);
+ sprintf(cmd, "ALTER TABLE `%s` DISABLE KEYS", TableName);
m_Rc = Myc.ExecSQL(g, cmd, &w); // may fail for some engines
} // endif m_Rc
} else
// m_Rc = (Mode == MODE_DELETE) ? MakeDelete(g) : MakeUpdate(g);
- m_Rc = MakeCommand(g);
+ m_Rc = (MakeCommand(g)) ? RC_FX : RC_OK;
if (m_Rc == RC_FX) {
Myc.Close();
@@ -1030,7 +1042,7 @@ int TDBMYSQL::SendCommand(PGLOBAL g)
if (Myc.ExecSQLcmd(g, Query->GetStr(), &w) == RC_NF) {
AftRows = Myc.m_Afrw;
- sprintf(g->Message, "%s: %d affected rows", Tabname, AftRows);
+ sprintf(g->Message, "%s: %d affected rows", TableName, AftRows);
PushWarning(g, this, 0); // 0 means a Note
if (trace)
@@ -1039,7 +1051,7 @@ int TDBMYSQL::SendCommand(PGLOBAL g)
if (w && Myc.ExecSQL(g, "SHOW WARNINGS") == RC_OK) {
// We got warnings from the remote server
while (Myc.Fetch(g, -1) == RC_OK) {
- sprintf(g->Message, "%s: (%s) %s", Tabname,
+ sprintf(g->Message, "%s: (%s) %s", TableName,
Myc.GetCharField(1), Myc.GetCharField(2));
PushWarning(g, this);
} // endwhile Fetch
@@ -1116,8 +1128,7 @@ int TDBMYSQL::ReadDB(PGLOBAL g)
int rc;
if (trace > 1)
- htrc("MySQL ReadDB: R%d Mode=%d key=%p link=%p Kindex=%p\n",
- GetTdb_No(), Mode, To_Key_Col, To_Link, To_Kindex);
+ htrc("MySQL ReadDB: R%d Mode=%d\n", GetTdb_No(), Mode);
if (Mode == MODE_UPDATE || Mode == MODE_DELETE)
return SendCommand(g);
@@ -1205,7 +1216,7 @@ void TDBMYSQL::CloseDB(PGLOBAL g)
PDBUSER dup = PlgGetUser(g);
dup->Step = "Enabling indexes";
- sprintf(cmd, "ALTER TABLE `%s` ENABLE KEYS", Tabname);
+ sprintf(cmd, "ALTER TABLE `%s` ENABLE KEYS", TableName);
Myc.m_Rows = -1; // To execute the query
m_Rc = Myc.ExecSQL(g, cmd, &w); // May fail for some engines
} // endif m_Rc
@@ -1463,7 +1474,7 @@ TDBMYEXC::TDBMYEXC(PMYDEF tdp) : TDBMYSQL(tdp)
Havew = false;
Isw = false;
Warnings = 0;
- Mxr = tdp->Mxr;
+ Mxr = tdp->Maxerr;
Nerr = 0;
} // end of TDBMYEXC constructor
@@ -1479,7 +1490,7 @@ TDBMYEXC::TDBMYEXC(PTDBMYX tdbp) : TDBMYSQL(tdbp)
} // end of TDBMYEXC copy constructor
// Is this really useful ???
-PTDB TDBMYEXC::CopyOne(PTABS t)
+PTDB TDBMYEXC::Clone(PTABS t)
{
PTDB tp;
PCOL cp1, cp2;
@@ -1494,7 +1505,7 @@ PTDB TDBMYEXC::CopyOne(PTABS t)
} // endfor cp1
return tp;
- } // end of CopyOne
+ } // end of Clone
/***********************************************************************/
/* Allocate MYSQL column description block. */
@@ -1565,7 +1576,7 @@ bool TDBMYEXC::OpenDB(PGLOBAL g)
/* servers allowing concurency in getting results ??? */
/*********************************************************************/
if (!Myc.Connected())
- if (Myc.Open(g, Host, Database, User, Pwd, Port))
+ if (Myc.Open(g, Host, Schema, User, Pwd, Port))
return true;
Use = USE_OPEN; // Do it now in case we are recursively called
@@ -1728,7 +1739,7 @@ void MYXCOL::WriteColumn(PGLOBAL)
TDBMCL::TDBMCL(PMYDEF tdp) : TDBCAT(tdp)
{
Host = tdp->Hostname;
- Db = tdp->Database;
+ Db = tdp->Tabschema;
Tab = tdp->Tabname;
User = tdp->Username;
Pwd = tdp->Password;
diff --git a/storage/connect/tabmysql.h b/storage/connect/tabmysql.h
index edb15b5cca6..050fa59259b 100644
--- a/storage/connect/tabmysql.h
+++ b/storage/connect/tabmysql.h
@@ -1,4 +1,4 @@
-// TDBMYSQL.H Olivier Bertrand 2007-2014
+// TDBMYSQL.H Olivier Bertrand 2007-2017
#include "myconn.h" // MySQL connection declares
typedef class MYSQLDEF *PMYDEF;
@@ -18,7 +18,7 @@ typedef class MYSQLC *PMYC;
/***********************************************************************/
/* MYSQL table. */
/***********************************************************************/
-class MYSQLDEF : public TABDEF {/* Logical table description */
+class MYSQLDEF : public EXTDEF {/* Logical table description */
friend class TDBMYSQL;
friend class TDBMYEXC;
friend class TDBMCL;
@@ -27,19 +27,18 @@ class MYSQLDEF : public TABDEF {/* Logical table description */
// Constructor
MYSQLDEF(void);
-
// Implementation
virtual const char *GetType(void) {return "MYSQL";}
inline PSZ GetHostname(void) {return Hostname;};
- inline PSZ GetDatabase(void) {return Database;};
- inline PSZ GetTabname(void) {return Tabname;}
- inline PSZ GetSrcdef(void) {return Srcdef;}
- inline PSZ GetUsername(void) {return Username;};
- inline PSZ GetPassword(void) {return Password;};
+//inline PSZ GetDatabase(void) {return Tabschema;};
+//inline PSZ GetTabname(void) {return Tabname;}
+//inline PSZ GetSrcdef(void) {return Srcdef;}
+//inline PSZ GetUsername(void) {return Username;};
+//inline PSZ GetPassword(void) {return Password;};
inline int GetPortnumber(void) {return Portnumber;}
// Methods
- virtual int Indexable(void) {return 2;}
+//virtual int Indexable(void) {return 2;}
virtual bool DefineAM(PGLOBAL g, LPCSTR am, int poff);
virtual PTDB GetTable(PGLOBAL g, MODE m);
bool ParseURL(PGLOBAL g, char *url, bool b = true);
@@ -48,27 +47,27 @@ class MYSQLDEF : public TABDEF {/* Logical table description */
protected:
// Members
PSZ Hostname; /* Host machine to use */
- PSZ Database; /* Database to be used by server */
- PSZ Tabname; /* External table name */
- PSZ Srcdef; /* The source table SQL definition */
- PSZ Username; /* User logon name */
- PSZ Password; /* Password logon info */
+//PSZ Tabschema; /* Database to be used by server */
+//PSZ Tabname; /* External table name */
+//PSZ Srcdef; /* The source table SQL definition */
+//PSZ Username; /* User logon name */
+//PSZ Password; /* Password logon info */
PSZ Server; /* PServerID */
- PSZ Qrystr; /* The original query */
+//PSZ Qrystr; /* The original query */
int Portnumber; /* MySQL port number (0 = default) */
- int Mxr; /* Maxerr for an Exec table */
- int Quoted; /* Identifier quoting level */
+//int Maxerr; /* Maxerr for an Exec table */
+//int Quoted; /* Identifier quoting level */
bool Isview; /* true if this table is a MySQL view */
bool Bind; /* Use prepared statement on insert */
bool Delayed; /* Delayed insert */
- bool Xsrc; /* Execution type */
+//bool Xsrc; /* Execution type */
bool Huge; /* True for big table */
}; // end of MYSQLDEF
/***********************************************************************/
/* This is the class declaration for the MYSQL table. */
/***********************************************************************/
-class TDBMYSQL : public TDBASE {
+class TDBMYSQL : public TDBEXT {
friend class MYSQLCOL;
public:
// Constructor
@@ -80,7 +79,7 @@ class TDBMYSQL : public TDBASE {
virtual PTDB Duplicate(PGLOBAL g) {return (PTDB)new(g) TDBMYSQL(this);}
// Methods
- virtual PTDB CopyOne(PTABS t);
+ virtual PTDB Clone(PTABS t);
//virtual int GetAffectedRows(void) {return AftRows;}
virtual int GetRecpos(void) {return N;}
virtual int GetProgMax(PGLOBAL g);
@@ -88,12 +87,12 @@ class TDBMYSQL : public TDBASE {
virtual int RowNumber(PGLOBAL g, bool b = false);
virtual bool IsView(void) {return Isview;}
virtual PSZ GetServer(void) {return Server;}
- void SetDatabase(LPCSTR db) {Database = (char*)db;}
+ void SetDatabase(LPCSTR db) {Schema = (char*)db;}
- // Database routines
+ // Schema routines
virtual PCOL MakeCol(PGLOBAL g, PCOLDEF cdp, PCOL cprec, int n);
virtual int Cardinality(PGLOBAL g);
- virtual int GetMaxSize(PGLOBAL g);
+//virtual int GetMaxSize(PGLOBAL g);
virtual bool OpenDB(PGLOBAL g);
virtual int ReadDB(PGLOBAL g);
virtual int WriteDB(PGLOBAL g);
@@ -111,7 +110,7 @@ class TDBMYSQL : public TDBASE {
bool MakeSelect(PGLOBAL g, bool mx);
bool MakeInsert(PGLOBAL g);
int BindColumns(PGLOBAL g);
- int MakeCommand(PGLOBAL g);
+ virtual bool MakeCommand(PGLOBAL g);
//int MakeUpdate(PGLOBAL g);
//int MakeDelete(PGLOBAL g);
int SendCommand(PGLOBAL g);
@@ -119,25 +118,25 @@ class TDBMYSQL : public TDBASE {
// Members
MYSQLC Myc; // MySQL connection class
MYSQL_BIND *Bind; // To the MySQL bind structure array
- PSTRG Query; // Constructed SQL query
+//PSTRG Query; // Constructed SQL query
char *Host; // Host machine to use
- char *User; // User logon info
- char *Pwd; // Password logon info
- char *Database; // Database to be used by server
- char *Tabname; // External table name
- char *Srcdef; // The source table SQL definition
+//char *User; // User logon info
+//char *Pwd; // Password logon info
+//char *Schema; // Database to be used by server
+//char *TableName; // External table name
+//char *Srcdef; // The source table SQL definition
char *Server; // The server ID
- char *Qrystr; // The original query
+//char *Qrystr; // The original query
bool Fetched; // True when fetch was done
bool Isview; // True if this table is a MySQL view
bool Prep; // Use prepared statement on insert
bool Delayed; // Use delayed insert
int m_Rc; // Return code from command
- int AftRows; // The number of affected rows
+//int AftRows; // The number of affected rows
int N; // The current table index
int Port; // MySQL port number (0 = default)
- int Nparm; // The number of statement parameters
- int Quoted; // The identifier quoting level
+//int Nparm; // The number of statement parameters
+//int Quoted; // The identifier quoting level
}; // end of class TDBMYSQL
/***********************************************************************/
@@ -162,9 +161,6 @@ class MYSQLCOL : public COLBLK {
bool FindRank(PGLOBAL g);
protected:
- // Default constructor not to be used
- MYSQLCOL(void) {}
-
// Members
MYSQL_BIND *Bind; // This column bind structure pointer
PVAL To_Val; // To value used for Update/Insert
@@ -187,7 +183,7 @@ class TDBMYEXC : public TDBMYSQL {
virtual PTDB Duplicate(PGLOBAL g) {return (PTDB)new(g) TDBMYEXC(this);}
// Methods
- virtual PTDB CopyOne(PTABS t);
+ virtual PTDB Clone(PTABS t);
virtual bool IsView(void) {return Isview;}
// Database routines
@@ -228,9 +224,6 @@ class MYXCOL : public MYSQLCOL {
virtual void WriteColumn(PGLOBAL g);
protected:
- // Default constructor not to be used
- MYXCOL(void) {}
-
// Members
char *Buffer; // To get returned message
int Flag; // Column content desc
diff --git a/storage/connect/taboccur.cpp b/storage/connect/taboccur.cpp
index 07e260154e0..07272d1b298 100644
--- a/storage/connect/taboccur.cpp
+++ b/storage/connect/taboccur.cpp
@@ -1,7 +1,7 @@
/************ TabOccur CPP Declares Source Code File (.CPP) ************/
-/* Name: TABOCCUR.CPP Version 1.1 */
+/* Name: TABOCCUR.CPP Version 1.2 */
/* */
-/* (C) Copyright to the author Olivier BERTRAND 2013 - 2015 */
+/* (C) Copyright to the author Olivier BERTRAND 2013 - 2017 */
/* */
/* OCCUR: Table that provides a view of a source table where the */
/* contain of several columns of the source table is placed in only */
@@ -39,12 +39,13 @@
/***********************************************************************/
#include "global.h"
#include "plgdbsem.h"
-#include "reldef.h"
+#include "xtable.h"
+#include "tabext.h"
+//#include "reldef.h"
#include "filamtxt.h"
#include "tabdos.h"
#include "tabcol.h"
#include "taboccur.h"
-#include "xtable.h"
#include "tabmysql.h"
#include "ha_connect.h"
diff --git a/storage/connect/tabodbc.cpp b/storage/connect/tabodbc.cpp
index f3ffc99ac15..488acdd330d 100644
--- a/storage/connect/tabodbc.cpp
+++ b/storage/connect/tabodbc.cpp
@@ -67,10 +67,11 @@
#include "plgdbsem.h"
#include "mycat.h"
#include "xtable.h"
+#include "tabext.h"
#include "odbccat.h"
#include "tabodbc.h"
#include "tabmul.h"
-#include "reldef.h"
+//#include "reldef.h"
#include "tabcol.h"
#include "valblk.h"
#include "ha_connect.h"
@@ -95,10 +96,9 @@ bool ExactInfo(void);
/***********************************************************************/
ODBCDEF::ODBCDEF(void)
{
- Connect = Tabname = Tabschema = Username = Password = NULL;
- Tabcat = Colpat = Srcdef = Qchar = Qrystr = Sep = NULL;
- Catver = Options = Cto = Qto = Quoted = Maxerr = Maxres = Memory = 0;
- Scrollable = Xsrc = UseCnc = false;
+ Connect = NULL;
+ Catver = 0;
+ UseCnc = false;
} // end of ODBCDEF constructor
/***********************************************************************/
@@ -113,47 +113,50 @@ bool ODBCDEF::DefineAM(PGLOBAL g, LPCSTR am, int poff)
return true;
} // endif Connect
- Tabname = GetStringCatInfo(g, "Name",
- (Catfunc & (FNC_TABLE | FNC_COL)) ? NULL : Name);
- Tabname = GetStringCatInfo(g, "Tabname", Tabname);
- Tabschema = GetStringCatInfo(g, "Dbname", NULL);
- Tabschema = GetStringCatInfo(g, "Schema", Tabschema);
- Tabcat = GetStringCatInfo(g, "Qualifier", NULL);
- Tabcat = GetStringCatInfo(g, "Catalog", Tabcat);
- Username = GetStringCatInfo(g, "User", NULL);
- Password = GetStringCatInfo(g, "Password", NULL);
-
- if ((Srcdef = GetStringCatInfo(g, "Srcdef", NULL)))
- Read_Only = true;
-
- Qrystr = GetStringCatInfo(g, "Query_String", "?");
- Sep = GetStringCatInfo(g, "Separator", NULL);
+ if (EXTDEF::DefineAM(g, am, poff))
+ return true;
+
+ // Tabname = GetStringCatInfo(g, "Name",
+ // (Catfunc & (FNC_TABLE | FNC_COL)) ? NULL : Name);
+ // Tabname = GetStringCatInfo(g, "Tabname", Tabname);
+ // Tabschema = GetStringCatInfo(g, "Dbname", NULL);
+ // Tabschema = GetStringCatInfo(g, "Schema", Tabschema);
+ // Tabcat = GetStringCatInfo(g, "Qualifier", NULL);
+ // Tabcat = GetStringCatInfo(g, "Catalog", Tabcat);
+ //Username = GetStringCatInfo(g, "User", NULL);
+ // Password = GetStringCatInfo(g, "Password", NULL);
+
+ // if ((Srcdef = GetStringCatInfo(g, "Srcdef", NULL)))
+ // Read_Only = true;
+
+ // Qrystr = GetStringCatInfo(g, "Query_String", "?");
+ // Sep = GetStringCatInfo(g, "Separator", NULL);
Catver = GetIntCatInfo("Catver", 2);
- Xsrc = GetBoolCatInfo("Execsrc", FALSE);
- Maxerr = GetIntCatInfo("Maxerr", 0);
- Maxres = GetIntCatInfo("Maxres", 0);
- Quoted = GetIntCatInfo("Quoted", 0);
+ //Xsrc = GetBoolCatInfo("Execsrc", FALSE);
+ //Maxerr = GetIntCatInfo("Maxerr", 0);
+ //Maxres = GetIntCatInfo("Maxres", 0);
+ //Quoted = GetIntCatInfo("Quoted", 0);
Options = ODBConn::noOdbcDialog;
//Options = ODBConn::noOdbcDialog | ODBConn::useCursorLib;
Cto= GetIntCatInfo("ConnectTimeout", DEFAULT_LOGIN_TIMEOUT);
Qto= GetIntCatInfo("QueryTimeout", DEFAULT_QUERY_TIMEOUT);
- if ((Scrollable = GetBoolCatInfo("Scrollable", false)) && !Elemt)
- Elemt = 1; // Cannot merge SQLFetch and SQLExtendedFetch
+ //if ((Scrollable = GetBoolCatInfo("Scrollable", false)) && !Elemt)
+ // Elemt = 1; // Cannot merge SQLFetch and SQLExtendedFetch
- if (Catfunc == FNC_COL)
- Colpat = GetStringCatInfo(g, "Colpat", NULL);
+ //if (Catfunc == FNC_COL)
+ // Colpat = GetStringCatInfo(g, "Colpat", NULL);
- if (Catfunc == FNC_TABLE)
- Tabtyp = GetStringCatInfo(g, "Tabtype", NULL);
+ //if (Catfunc == FNC_TABLE)
+ // Tabtyp = GetStringCatInfo(g, "Tabtype", NULL);
UseCnc = GetBoolCatInfo("UseDSN", false);
// Memory was Boolean, it is now integer
- if (!(Memory = GetIntCatInfo("Memory", 0)))
- Memory = GetBoolCatInfo("Memory", false) ? 1 : 0;
+ //if (!(Memory = GetIntCatInfo("Memory", 0)))
+ // Memory = GetBoolCatInfo("Memory", false) ? 1 : 0;
- Pseudo = 2; // FILID is Ok but not ROWID
+ //Pseudo = 2; // FILID is Ok but not ROWID
return false;
} // end of DefineAM
@@ -162,7 +165,7 @@ bool ODBCDEF::DefineAM(PGLOBAL g, LPCSTR am, int poff)
/***********************************************************************/
PTDB ODBCDEF::GetTable(PGLOBAL g, MODE m)
{
- PTDBASE tdbp = NULL;
+ PTDB tdbp = NULL;
/*********************************************************************/
/* Allocate a TDB of the proper type. */
@@ -200,103 +203,103 @@ PTDB ODBCDEF::GetTable(PGLOBAL g, MODE m)
/***********************************************************************/
/* Implementation of the TDBODBC class. */
/***********************************************************************/
-TDBODBC::TDBODBC(PODEF tdp) : TDBASE(tdp)
+TDBODBC::TDBODBC(PODEF tdp) : TDBEXT(tdp)
{
Ocp = NULL;
Cnp = NULL;
if (tdp) {
Connect = tdp->Connect;
- TableName = tdp->Tabname;
- Schema = tdp->Tabschema;
+ //TableName = tdp->Tabname;
+ //Schema = tdp->Tabschema;
Ops.User = tdp->Username;
Ops.Pwd = tdp->Password;
- Catalog = tdp->Tabcat;
- Srcdef = tdp->Srcdef;
- Qrystr = tdp->Qrystr;
- Sep = tdp->GetSep();
- Options = tdp->Options;
+ //Catalog = tdp->Tabcat;
+ //Srcdef = tdp->Srcdef;
+ //Qrystr = tdp->Qrystr;
+ //Sep = tdp->GetSep();
+ //Options = tdp->Options;
Ops.Cto = tdp->Cto;
Ops.Qto = tdp->Qto;
- Quoted = MY_MAX(0, tdp->GetQuoted());
- Rows = tdp->GetElemt();
+ //Quoted = MY_MAX(0, tdp->GetQuoted());
+ //Rows = tdp->GetElemt();
Catver = tdp->Catver;
- Memory = tdp->Memory;
- Scrollable = tdp->Scrollable;
+ //Memory = tdp->Memory;
+ //Scrollable = tdp->Scrollable;
Ops.UseCnc = tdp->UseCnc;
} else {
Connect = NULL;
- TableName = NULL;
- Schema = NULL;
+ //TableName = NULL;
+ //Schema = NULL;
Ops.User = NULL;
Ops.Pwd = NULL;
- Catalog = NULL;
- Srcdef = NULL;
- Qrystr = NULL;
- Sep = 0;
- Options = 0;
+ //Catalog = NULL;
+ //Srcdef = NULL;
+ //Qrystr = NULL;
+ //Sep = 0;
+ //Options = 0;
Ops.Cto = DEFAULT_LOGIN_TIMEOUT;
Ops.Qto = DEFAULT_QUERY_TIMEOUT;
- Quoted = 0;
- Rows = 0;
+ //Quoted = 0;
+ //Rows = 0;
Catver = 0;
- Memory = 0;
- Scrollable = false;
+ //Memory = 0;
+ //Scrollable = false;
Ops.UseCnc = false;
} // endif tdp
- Quote = NULL;
- Query = NULL;
- Count = NULL;
+ //Quote = NULL;
+ //Query = NULL;
+ //Count = NULL;
//Where = NULL;
- MulConn = NULL;
- DBQ = NULL;
- Qrp = NULL;
- Fpos = 0;
- Curpos = 0;
- AftRows = 0;
- CurNum = 0;
- Rbuf = 0;
- BufSize = 0;
- Nparm = 0;
- Placed = false;
+ //MulConn = NULL;
+ //DBQ = NULL;
+ //Qrp = NULL;
+ //Fpos = 0;
+ //Curpos = 0;
+ //AftRows = 0;
+ //CurNum = 0;
+ //Rbuf = 0;
+ //BufSize = 0;
+ //Nparm = 0;
+ //Placed = false;
} // end of TDBODBC standard constructor
-TDBODBC::TDBODBC(PTDBODBC tdbp) : TDBASE(tdbp)
+TDBODBC::TDBODBC(PTDBODBC tdbp) : TDBEXT(tdbp)
{
Ocp = tdbp->Ocp; // is that right ?
Cnp = tdbp->Cnp;
Connect = tdbp->Connect;
- TableName = tdbp->TableName;
- Schema = tdbp->Schema;
+ //TableName = tdbp->TableName;
+ //Schema = tdbp->Schema;
Ops = tdbp->Ops;
- Catalog = tdbp->Catalog;
- Srcdef = tdbp->Srcdef;
- Qrystr = tdbp->Qrystr;
- Memory = tdbp->Memory;
- Scrollable = tdbp->Scrollable;
- Quote = tdbp->Quote;
- Query = tdbp->Query;
- Count = tdbp->Count;
+ //Catalog = tdbp->Catalog;
+ //Srcdef = tdbp->Srcdef;
+ //Qrystr = tdbp->Qrystr;
+ //Memory = tdbp->Memory;
+ //Scrollable = tdbp->Scrollable;
+ //Quote = tdbp->Quote;
+ //Query = tdbp->Query;
+ //Count = tdbp->Count;
//Where = tdbp->Where;
- MulConn = tdbp->MulConn;
- DBQ = tdbp->DBQ;
- Options = tdbp->Options;
- Quoted = tdbp->Quoted;
- Rows = tdbp->Rows;
- Fpos = 0;
- Curpos = 0;
- AftRows = 0;
- CurNum = 0;
- Rbuf = 0;
- BufSize = tdbp->BufSize;
- Nparm = tdbp->Nparm;
- Qrp = tdbp->Qrp;
- Placed = false;
+ //MulConn = tdbp->MulConn;
+ //DBQ = tdbp->DBQ;
+ //Options = tdbp->Options;
+ //Quoted = tdbp->Quoted;
+ //Rows = tdbp->Rows;
+ //Fpos = 0;
+ //Curpos = 0;
+ //AftRows = 0;
+ //CurNum = 0;
+ //Rbuf = 0;
+ //BufSize = tdbp->BufSize;
+ //Nparm = tdbp->Nparm;
+ //Qrp = tdbp->Qrp;
+ //Placed = false;
} // end of TDBODBC copy constructor
// Method
-PTDB TDBODBC::CopyOne(PTABS t)
+PTDB TDBODBC::Clone(PTABS t)
{
PTDB tp;
PODBCCOL cp1, cp2;
@@ -386,6 +389,7 @@ void TDBODBC::SetFile(PGLOBAL g, PSZ fn)
DBQ = fn;
} // end of SetFile
+#if 0
/******************************************************************/
/* Convert an UTF-8 string to latin characters. */
/******************************************************************/
@@ -414,7 +418,15 @@ bool TDBODBC::MakeSQL(PGLOBAL g, bool cnt)
PCOL colp;
if (Srcdef) {
- Query = new(g)STRING(g, 0, Srcdef);
+ if (strstr(Srcdef, "%s")) {
+ char *fil;
+
+ fil = (To_CondFil) ? To_CondFil->Body : PlugDup(g, "1=1");
+ Query = new(g)STRING(g, strlen(Srcdef) + strlen(fil));
+ Query->SetLength(sprintf(Query->GetStr(), Srcdef, fil));
+ } else
+ Query = new(g)STRING(g, 0, Srcdef);
+
return false;
} // endif Srcdef
@@ -442,7 +454,8 @@ bool TDBODBC::MakeSQL(PGLOBAL g, bool cnt)
} else
oom |= Query->Append(buf);
- } // endif colp
+ ((PEXTCOL)colp)->SetRank(++Ncol);
+ } // endif colp
} else
// !Columns can occur for queries such that sql count(*) from...
@@ -458,10 +471,6 @@ bool TDBODBC::MakeSQL(PGLOBAL g, bool cnt)
if (Catalog && *Catalog)
catp = Catalog;
- // Following lines are commented because of MSDEV-10520
- // Indeed the schema in the tablep is the local table database and
- // is normally not related to the remote table database.
- // TODO: Try to remember why this was done and if it was useful in some case.
//if (tablep->GetSchema())
// schmp = (char*)tablep->GetSchema();
//else
@@ -516,6 +525,7 @@ bool TDBODBC::MakeSQL(PGLOBAL g, bool cnt)
return false;
} // end of MakeSQL
+#endif // 0
/***********************************************************************/
/* MakeInsert: make the Insert statement used with ODBC connection. */
@@ -536,7 +546,7 @@ bool TDBODBC::MakeInsert(PGLOBAL g)
// Column name can be encoded in UTF-8
Decode(colp->GetName(), buf, sizeof(buf));
len += (strlen(buf) + 6); // comma + quotes + valist
- ((PODBCCOL)colp)->Rank = ++Nparm;
+ ((PEXTCOL)colp)->SetRank(++Nparm);
} // endif colp
// Below 32 is enough to contain the fixed part of the query
@@ -555,7 +565,7 @@ bool TDBODBC::MakeInsert(PGLOBAL g)
if (schmp)
len += strlen(schmp) + 1;
- // Column name can be encoded in UTF-8
+ // Table name can be encoded in UTF-8
Decode(TableName, buf, sizeof(buf));
len += (strlen(buf) + 32);
Query = new(g) STRING(g, len, "INSERT INTO ");
@@ -634,6 +644,7 @@ bool TDBODBC::BindParameters(PGLOBAL g)
return false;
} // end of BindParameters
+#if 0
/***********************************************************************/
/* MakeCommand: make the Update or Delete statement to send to the */
/* MySQL server. Limited to remote values and filtering. */
@@ -664,19 +675,20 @@ bool TDBODBC::MakeCommand(PGLOBAL g)
// If so, it must be quoted in the original query
strlwr(strcat(strcat(strcpy(name, " "), Name), " "));
- if (!strstr(" update delete low_priority ignore quick from ", name))
- strlwr(strcpy(name, Name)); // Not a keyword
- else
- strlwr(strcat(strcat(strcpy(name, qc), Name), qc));
+ if (strstr(" update delete low_priority ignore quick from ", name)) {
+ strlwr(strcat(strcat(strcpy(name, qc), Name), qc));
+ k += 2;
+ } else
+ strlwr(strcpy(name, Name)); // Not a keyword
if ((p = strstr(qrystr, name))) {
for (i = 0; i < p - qrystr; i++)
stmt[i] = (Qrystr[i] == '`') ? *qc : Qrystr[i];
stmt[i] = 0;
- k = i + (int)strlen(Name);
+ k += i + (int)strlen(Name);
- if (qtd && *(p-1) == ' ')
+ if (qtd && *(p - 1) == ' ')
strcat(strcat(strcat(stmt, qc), TableName), qc);
else
strcat(stmt, TableName);
@@ -692,15 +704,14 @@ bool TDBODBC::MakeCommand(PGLOBAL g)
} else {
sprintf(g->Message, "Cannot use this %s command",
- (Mode == MODE_UPDATE) ? "UPDATE" : "DELETE");
- return false;
+ (Mode == MODE_UPDATE) ? "UPDATE" : "DELETE");
+ return true;
} // endif p
Query = new(g) STRING(g, 0, stmt);
return (!Query->GetSize());
} // end of MakeCommand
-#if 0
/***********************************************************************/
/* MakeUpdate: make the SQL statement to send to ODBC connection. */
/***********************************************************************/
@@ -818,6 +829,7 @@ int TDBODBC::Cardinality(PGLOBAL g)
return Cardinal;
} // end of Cardinality
+#if 0
/***********************************************************************/
/* ODBC GetMaxSize: returns table size estimate in number of lines. */
/***********************************************************************/
@@ -844,6 +856,7 @@ int TDBODBC::GetProgMax(PGLOBAL g)
{
return GetMaxSize(g);
} // end of GetProgMax
+#endif // 0
/***********************************************************************/
/* ODBC Access Method opening routine. */
@@ -981,6 +994,7 @@ bool TDBODBC::OpenDB(PGLOBAL g)
return false;
} // end of OpenDB
+#if 0
/***********************************************************************/
/* GetRecpos: return the position of last read record. */
/***********************************************************************/
@@ -988,6 +1002,7 @@ int TDBODBC::GetRecpos(void)
{
return Fpos;
} // end of GetRecpos
+#endif // 0
/***********************************************************************/
/* SetRecpos: set the position of next read record. */
@@ -1081,8 +1096,9 @@ int TDBODBC::ReadDB(PGLOBAL g)
int rc;
if (trace > 1)
- htrc("ODBC ReadDB: R%d Mode=%d key=%p link=%p Kindex=%p\n",
- GetTdb_No(), Mode, To_Key_Col, To_Link, To_Kindex);
+ htrc("ODBC ReadDB: R%d Mode=%d\n", GetTdb_No(), Mode);
+ //htrc("ODBC ReadDB: R%d Mode=%d key=%p link=%p Kindex=%p\n",
+ // GetTdb_No(), Mode, To_Key_Col, To_Link, To_Kindex);
if (Mode == MODE_UPDATE || Mode == MODE_DELETE) {
if (!Query && MakeCommand(g))
@@ -1102,11 +1118,11 @@ int TDBODBC::ReadDB(PGLOBAL g)
} // endif Mode
- if (To_Kindex) {
- // Direct access of ODBC tables is not implemented yet
- strcpy(g->Message, MSG(NO_ODBC_DIRECT));
- return RC_FX;
- } // endif To_Kindex
+ //if (To_Kindex) {
+ // // Direct access of ODBC tables is not implemented yet
+ // strcpy(g->Message, MSG(NO_ODBC_DIRECT));
+ // return RC_FX;
+ // } // endif To_Kindex
/*********************************************************************/
/* Now start the reading process. */
@@ -1212,70 +1228,58 @@ void TDBODBC::CloseDB(PGLOBAL g)
/* ODBCCOL public constructor. */
/***********************************************************************/
ODBCCOL::ODBCCOL(PCOLDEF cdp, PTDB tdbp, PCOL cprec, int i, PSZ am)
- : COLBLK(cdp, tdbp, i)
+ : EXTCOL(cdp, tdbp, cprec, i, am)
{
- if (cprec) {
- Next = cprec->GetNext();
- cprec->SetNext(this);
- } else {
- Next = tdbp->GetColumns();
- tdbp->SetColumns(this);
- } // endif cprec
-
// Set additional ODBC access method information for column.
- Crp = NULL;
-//Long = cdp->GetLong();
- Long = Precision;
+//Crp = NULL;
+//Long = Precision;
//strcpy(F_Date, cdp->F_Date);
- To_Val = NULL;
+//To_Val = NULL;
Slen = 0;
StrLen = &Slen;
Sqlbuf = NULL;
- Bufp = NULL;
- Blkp = NULL;
- Rank = 0; // Not known yet
-
- if (trace)
- htrc(" making new %sCOL C%d %s at %p\n", am, Index, Name, this);
-
+//Bufp = NULL;
+//Blkp = NULL;
+//Rank = 0; // Not known yet
} // end of ODBCCOL constructor
/***********************************************************************/
/* ODBCCOL private constructor. */
/***********************************************************************/
-ODBCCOL::ODBCCOL(void) : COLBLK()
+ODBCCOL::ODBCCOL(void) : EXTCOL()
{
- Crp = NULL;
- Buf_Type = TYPE_INT; // This is a count(*) column
- // Set additional Dos access method information for column.
- Long = sizeof(int);
- To_Val = NULL;
+//Crp = NULL;
+//Buf_Type = TYPE_INT; // This is a count(*) column
+//// Set additional Dos access method information for column.
+//Long = sizeof(int);
+//To_Val = NULL;
Slen = 0;
StrLen = &Slen;
Sqlbuf = NULL;
- Bufp = NULL;
- Blkp = NULL;
- Rank = 1;
+//Bufp = NULL;
+//Blkp = NULL;
+//Rank = 1;
} // end of ODBCCOL constructor
/***********************************************************************/
/* ODBCCOL constructor used for copying columns. */
/* tdbp is the pointer to the new table descriptor. */
/***********************************************************************/
-ODBCCOL::ODBCCOL(ODBCCOL *col1, PTDB tdbp) : COLBLK(col1, tdbp)
+ODBCCOL::ODBCCOL(ODBCCOL *col1, PTDB tdbp) : EXTCOL(col1, tdbp)
{
- Crp = col1->Crp;
- Long = col1->Long;
+//Crp = col1->Crp;
+//Long = col1->Long;
//strcpy(F_Date, col1->F_Date);
- To_Val = col1->To_Val;
+//To_Val = col1->To_Val;
Slen = col1->Slen;
StrLen = col1->StrLen;
Sqlbuf = col1->Sqlbuf;
- Bufp = col1->Bufp;
- Blkp = col1->Blkp;
- Rank = col1->Rank;
+//Bufp = col1->Bufp;
+//Blkp = col1->Blkp;
+//Rank = col1->Rank;
} // end of ODBCCOL copy constructor
+#if 0
/***********************************************************************/
/* SetBuffer: prepare a column block for write operation. */
/***********************************************************************/
@@ -1321,6 +1325,7 @@ bool ODBCCOL::SetBuffer(PGLOBAL g, PVAL value, bool ok, bool check)
Status = (ok) ? BUF_EMPTY : BUF_NO;
return false;
} // end of SetBuffer
+#endif // 0
/***********************************************************************/
/* ReadColumn: when SQLFetch is used there is nothing to do as the */
@@ -1526,7 +1531,7 @@ TDBXDBC::TDBXDBC(PTDBXDBC tdbp) : TDBODBC(tdbp)
Nerr = tdbp->Nerr;
} // end of TDBXDBC copy constructor
-PTDB TDBXDBC::CopyOne(PTABS t)
+PTDB TDBXDBC::Clone(PTABS t)
{
PTDB tp;
PXSRCCOL cp1, cp2;
diff --git a/storage/connect/tabodbc.h b/storage/connect/tabodbc.h
index aa6592d8abf..fcefad5647b 100644
--- a/storage/connect/tabodbc.h
+++ b/storage/connect/tabodbc.h
@@ -20,7 +20,7 @@ typedef class TDBSRC *PTDBSRC;
/***********************************************************************/
/* ODBC table. */
/***********************************************************************/
-class DllExport ODBCDEF : public TABDEF { /* Logical table description */
+class DllExport ODBCDEF : public EXTDEF { /* Logical table description */
friend class TDBODBC;
friend class TDBXDBC;
friend class TDBDRV;
@@ -33,14 +33,14 @@ public:
// Implementation
virtual const char *GetType(void) {return "ODBC";}
PSZ GetConnect(void) {return Connect;}
- PSZ GetTabname(void) {return Tabname;}
- PSZ GetTabschema(void) {return Tabschema;}
- PSZ GetTabcat(void) {return Tabcat;}
- PSZ GetSrcdef(void) {return Srcdef;}
- char GetSep(void) {return (Sep) ? *Sep : 0;}
- int GetQuoted(void) {return Quoted;}
+ //PSZ GetTabname(void) {return Tabname;}
+ //PSZ GetTabschema(void) {return Tabschema;}
+ //PSZ GetTabcat(void) {return Tabcat;}
+ //PSZ GetSrcdef(void) {return Srcdef;}
+ //char GetSep(void) {return (Sep) ? *Sep : 0;}
+ //int GetQuoted(void) {return Quoted;}
int GetCatver(void) {return Catver;}
- int GetOptions(void) {return Options;}
+ //int GetOptions(void) {return Options;}
// Methods
virtual int Indexable(void) {return 2;}
@@ -50,27 +50,27 @@ public:
protected:
// Members
PSZ Connect; /* ODBC connection string */
- PSZ Tabname; /* External table name */
- PSZ Tabschema; /* External table schema */
- PSZ Username; /* User connect name */
- PSZ Password; /* Password connect info */
- PSZ Tabcat; /* External table catalog */
- PSZ Tabtyp; /* Catalog table type */
- PSZ Colpat; /* Catalog column pattern */
- PSZ Srcdef; /* The source table SQL definition */
- PSZ Qchar; /* Identifier quoting character */
- PSZ Qrystr; /* The original query */
- PSZ Sep; /* Decimal separator */
+ //PSZ Tabname; /* External table name */
+ //PSZ Tabschema; /* External table schema */
+ //PSZ Username; /* User connect name */
+ //PSZ Password; /* Password connect info */
+ //PSZ Tabcat; /* External table catalog */
+ //PSZ Tabtyp; /* Catalog table type */
+ //PSZ Colpat; /* Catalog column pattern */
+ //PSZ Srcdef; /* The source table SQL definition */
+ //PSZ Qchar; /* Identifier quoting character */
+ //PSZ Qrystr; /* The original query */
+ //PSZ Sep; /* Decimal separator */
int Catver; /* ODBC version for catalog functions */
- int Options; /* Open connection options */
- int Cto; /* Open connection timeout */
- int Qto; /* Query (command) timeout */
- int Quoted; /* Identifier quoting level */
- int Maxerr; /* Maxerr for an Exec table */
- int Maxres; /* Maxres for a catalog table */
- int Memory; /* Put result set in memory */
- bool Scrollable; /* Use scrollable cursor */
- bool Xsrc; /* Execution type */
+ //int Options; /* Open connection options */
+ //int Cto; /* Open connection timeout */
+ //int Qto; /* Query (command) timeout */
+ //int Quoted; /* Identifier quoting level */
+ //int Maxerr; /* Maxerr for an Exec table */
+ //int Maxres; /* Maxres for a catalog table */
+ //int Memory; /* Put result set in memory */
+ //bool Scrollable; /* Use scrollable cursor */
+ //bool Xsrc; /* Execution type */
bool UseCnc; /* Use SQLConnect (!SQLDriverConnect) */
}; // end of ODBCDEF
@@ -81,7 +81,7 @@ public:
/* This is the ODBC Access Method class declaration for files from */
/* other DB drivers to be accessed via ODBC. */
/***********************************************************************/
-class TDBODBC : public TDBASE {
+class TDBODBC : public TDBEXT {
friend class ODBCCOL;
friend class ODBConn;
public:
@@ -95,8 +95,8 @@ class TDBODBC : public TDBASE {
{return (PTDB)new(g) TDBODBC(this);}
// Methods
- virtual PTDB CopyOne(PTABS t);
- virtual int GetRecpos(void);
+ virtual PTDB Clone(PTABS t);
+//virtual int GetRecpos(void);
virtual bool SetRecpos(PGLOBAL g, int recpos);
virtual PSZ GetFile(PGLOBAL g);
virtual void SetFile(PGLOBAL g, PSZ fn);
@@ -108,8 +108,8 @@ class TDBODBC : public TDBASE {
// Database routines
virtual PCOL MakeCol(PGLOBAL g, PCOLDEF cdp, PCOL cprec, int n);
virtual int Cardinality(PGLOBAL g);
- virtual int GetMaxSize(PGLOBAL g);
- virtual int GetProgMax(PGLOBAL g);
+//virtual int GetMaxSize(PGLOBAL g);
+//virtual int GetProgMax(PGLOBAL g);
virtual bool OpenDB(PGLOBAL g);
virtual int ReadDB(PGLOBAL g);
virtual int WriteDB(PGLOBAL g);
@@ -119,10 +119,10 @@ class TDBODBC : public TDBASE {
protected:
// Internal functions
- int Decode(char *utf, char *buf, size_t n);
- bool MakeSQL(PGLOBAL g, bool cnt);
+//int Decode(char *utf, char *buf, size_t n);
+//bool MakeSQL(PGLOBAL g, bool cnt);
bool MakeInsert(PGLOBAL g);
- bool MakeCommand(PGLOBAL g);
+//virtual bool MakeCommand(PGLOBAL g);
//bool MakeFilter(PGLOBAL g, bool c);
bool BindParameters(PGLOBAL g);
//char *MakeUpdate(PGLOBAL g);
@@ -132,46 +132,16 @@ class TDBODBC : public TDBASE {
ODBConn *Ocp; // Points to an ODBC connection class
ODBCCOL *Cnp; // Points to count(*) column
ODBCPARM Ops; // Additional parameters
- PSTRG Query; // Constructed SQL query
char *Connect; // Points to connection string
- char *TableName; // Points to ODBC table name
- char *Schema; // Points to ODBC table Schema
- char *User; // User connect info
- char *Pwd; // Password connect info
- char *Catalog; // Points to ODBC table Catalog
- char *Srcdef; // The source table SQL definition
- char *Count; // Points to count(*) SQL statement
-//char *Where; // Points to local where clause
- char *Quote; // The identifier quoting character
- char *MulConn; // Used for multiple ODBC tables
- char *DBQ; // The address part of Connect string
- char *Qrystr; // The original query
- char Sep; // The decimal separator
- int Options; // Connect options
- int Cto; // Connect timeout
- int Qto; // Query timeout
- int Quoted; // The identifier quoting level
- int Fpos; // Position of last read record
- int Curpos; // Cursor position of last fetch
- int AftRows; // The number of affected rows
- int Rows; // Rowset size
int Catver; // Catalog ODBC version
- int CurNum; // Current buffer line number
- int Rbuf; // Number of lines read in buffer
- int BufSize; // Size of connect string buffer
- int Nparm; // The number of statement parameters
- int Memory; // 0: No 1: Alloc 2: Put 3: Get
- bool Scrollable; // Use scrollable cursor
- bool Placed; // True for position reading
bool UseCnc; // Use SQLConnect (!SQLDriverConnect)
- PQRYRES Qrp; // Points to storage result
}; // end of class TDBODBC
/***********************************************************************/
/* Class ODBCCOL: ODBC access method column descriptor. */
/* This A.M. is used for ODBC tables. */
/***********************************************************************/
-class ODBCCOL : public COLBLK {
+class ODBCCOL : public EXTCOL {
friend class TDBODBC;
public:
// Constructors
@@ -181,12 +151,12 @@ class ODBCCOL : public COLBLK {
// Implementation
virtual int GetAmType(void) {return TYPE_AM_ODBC;}
SQLLEN *GetStrLen(void) {return StrLen;}
- int GetRank(void) {return Rank;}
+// int GetRank(void) {return Rank;}
// PVBLK GetBlkp(void) {return Blkp;}
- void SetCrp(PCOLRES crp) {Crp = crp;}
+// void SetCrp(PCOLRES crp) {Crp = crp;}
// Methods
- virtual bool SetBuffer(PGLOBAL g, PVAL value, bool ok, bool check);
+//virtual bool SetBuffer(PGLOBAL g, PVAL value, bool ok, bool check);
virtual void ReadColumn(PGLOBAL g);
virtual void WriteColumn(PGLOBAL g);
void AllocateBuffers(PGLOBAL g, int rows);
@@ -195,19 +165,19 @@ class ODBCCOL : public COLBLK {
// void Print(PGLOBAL g, FILE *, uint);
protected:
- // Constructor used by GetMaxSize
+ // Constructor for count(*) column
ODBCCOL(void);
// Members
TIMESTAMP_STRUCT *Sqlbuf; // To get SQL_TIMESTAMP's
- PCOLRES Crp; // To storage result
- void *Bufp; // To extended buffer
- PVBLK Blkp; // To Value Block
+//PCOLRES Crp; // To storage result
+//void *Bufp; // To extended buffer
+//PVBLK Blkp; // To Value Block
//char F_Date[12]; // Internal Date format
- PVAL To_Val; // To value used for Insert
+//PVAL To_Val; // To value used for Insert
SQLLEN *StrLen; // As returned by ODBC
SQLLEN Slen; // Used with Fetch
- int Rank; // Rank (position) number in the query
+//int Rank; // Rank (position) number in the query
}; // end of class ODBCCOL
/***********************************************************************/
@@ -228,28 +198,19 @@ class TDBXDBC : public TDBODBC {
{return (PTDB)new(g) TDBXDBC(this);}
// Methods
- virtual PTDB CopyOne(PTABS t);
-//virtual int GetRecpos(void);
-//virtual PSZ GetFile(PGLOBAL g);
-//virtual void SetFile(PGLOBAL g, PSZ fn);
-//virtual void ResetSize(void);
-//virtual int GetAffectedRows(void) {return AftRows;}
-//virtual PSZ GetServer(void) {return "ODBC";}
+ virtual PTDB Clone(PTABS t);
// Database routines
virtual PCOL MakeCol(PGLOBAL g, PCOLDEF cdp, PCOL cprec, int n);
-//virtual int GetProgMax(PGLOBAL g);
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:
// Internal functions
PCMD MakeCMD(PGLOBAL g);
-//bool BindParameters(PGLOBAL g);
// Members
PCMD Cmdlist; // The commands to execute
diff --git a/storage/connect/tabpivot.cpp b/storage/connect/tabpivot.cpp
index 256b454741c..c6d32884417 100644
--- a/storage/connect/tabpivot.cpp
+++ b/storage/connect/tabpivot.cpp
@@ -1,11 +1,11 @@
/************ TabPivot C++ Program Source Code File (.CPP) *************/
/* PROGRAM NAME: TABPIVOT */
/* ------------- */
-/* Version 1.6 */
+/* Version 1.7 */
/* */
/* COPYRIGHT: */
/* ---------- */
-/* (C) Copyright to the author Olivier BERTRAND 2005-2015 */
+/* (C) Copyright to the author Olivier BERTRAND 2005-2017 */
/* */
/* WHAT THIS PROGRAM DOES: */
/* ----------------------- */
@@ -41,6 +41,7 @@
#include "global.h"
#include "plgdbsem.h"
#include "xtable.h"
+#include "tabext.h"
#include "tabcol.h"
#include "colblk.h"
#include "tabmysql.h"
@@ -883,7 +884,7 @@ SRCCOL::SRCCOL(PCOLDEF cdp, PTDB tdbp, PCOL cprec, int n)
/***********************************************************************/
/* Initialize the column as pointing to the source column. */
/***********************************************************************/
-bool SRCCOL::Init(PGLOBAL g, PTDBASE tp)
+bool SRCCOL::Init(PGLOBAL g, PTDB tp)
{
if (PRXCOL::Init(g, tp))
return true;
diff --git a/storage/connect/tabpivot.h b/storage/connect/tabpivot.h
index c397af05234..07d5c3e456b 100644
--- a/storage/connect/tabpivot.h
+++ b/storage/connect/tabpivot.h
@@ -183,7 +183,7 @@ class SRCCOL : public PRXCOL {
using PRXCOL::Init;
virtual void Reset(void) {}
void SetColumn(void);
- virtual bool Init(PGLOBAL g, PTDBASE tp);
+ virtual bool Init(PGLOBAL g, PTDB tp);
bool CompareLast(void);
protected:
diff --git a/storage/connect/tabsys.cpp b/storage/connect/tabsys.cpp
index 76890e84429..2ddd1c3c753 100644
--- a/storage/connect/tabsys.cpp
+++ b/storage/connect/tabsys.cpp
@@ -159,7 +159,7 @@ TDBINI::TDBINI(PTDBINI tdbp) : TDBASE(tdbp)
} // end of TDBINI copy constructor
// Is this really useful ???
-PTDB TDBINI::CopyOne(PTABS t)
+PTDB TDBINI::Clone(PTABS t)
{
PTDB tp;
PINICOL cp1, cp2;
@@ -173,7 +173,7 @@ PTDB TDBINI::CopyOne(PTABS t)
} // endfor cp1
return tp;
- } // end of CopyOne
+ } // end of Clone
/***********************************************************************/
/* Get the section list from the INI file. */
@@ -565,7 +565,7 @@ TDBXIN::TDBXIN(PTDBXIN tdbp) : TDBINI(tdbp)
} // end of TDBXIN copy constructor
// Is this really useful ???
-PTDB TDBXIN::CopyOne(PTABS t)
+PTDB TDBXIN::Clone(PTABS t)
{
PTDB tp;
PXINCOL cp1, cp2;
@@ -579,7 +579,7 @@ PTDB TDBXIN::CopyOne(PTABS t)
} // endfor cp1
return tp;
- } // end of CopyOne
+ } // end of Clone
/***********************************************************************/
/* Get the key list from the INI file. */
diff --git a/storage/connect/tabsys.h b/storage/connect/tabsys.h
index 6b454322906..ff1b8335690 100644
--- a/storage/connect/tabsys.h
+++ b/storage/connect/tabsys.h
@@ -57,7 +57,7 @@ class TDBINI : public TDBASE {
virtual PTDB Duplicate(PGLOBAL g) {return (PTDB)new(g) TDBINI(this);}
// Methods
- virtual PTDB CopyOne(PTABS t);
+ virtual PTDB Clone(PTABS t);
virtual int GetRecpos(void) {return N;}
virtual int GetProgCur(void) {return N;}
//virtual int GetAffectedRows(void) {return 0;}
@@ -136,7 +136,7 @@ class TDBXIN : public TDBINI {
virtual PTDB Duplicate(PGLOBAL g) {return (PTDB)new(g) TDBXIN(this);}
// Methods
- virtual PTDB CopyOne(PTABS t);
+ virtual PTDB Clone(PTABS t);
virtual int GetRecpos(void);
virtual bool SetRecpos(PGLOBAL g, int recpos);
virtual void ResetDB(void)
diff --git a/storage/connect/tabtbl.cpp b/storage/connect/tabtbl.cpp
index e3baf7c3da5..0bf3f6beb43 100644
--- a/storage/connect/tabtbl.cpp
+++ b/storage/connect/tabtbl.cpp
@@ -1,11 +1,11 @@
/************* TabTbl C++ Program Source Code File (.CPP) **************/
/* PROGRAM NAME: TABTBL */
/* ------------- */
-/* Version 1.7 */
+/* Version 1.8 */
/* */
/* COPYRIGHT: */
/* ---------- */
-/* (C) Copyright to PlugDB Software Development 2008-2016 */
+/* (C) Copyright to PlugDB Software Development 2008-2017 */
/* Author: Olivier BERTRAND */
/* */
/* WHAT THIS PROGRAM DOES: */
@@ -70,6 +70,7 @@
#include "tabcol.h"
#include "tabdos.h" // TDBDOS and DOSCOL class dcls
#include "tabtbl.h"
+#include "tabext.h"
#include "tabmysql.h"
#include "ha_connect.h"
@@ -411,9 +412,9 @@ void TDBTBL::ResetDB(void)
colp->COLBLK::Reset();
for (PTABLE tabp = Tablist; tabp; tabp = tabp->GetNext())
- ((PTDBASE)tabp->GetTo_Tdb())->ResetDB();
+ tabp->GetTo_Tdb()->ResetDB();
- Tdbp = (PTDBASE)Tablist->GetTo_Tdb();
+ Tdbp = Tablist->GetTo_Tdb();
Crp = 0;
} // end of ResetDB
@@ -458,7 +459,7 @@ bool TDBTBL::OpenDB(PGLOBAL g)
return TRUE;
if ((CurTable = Tablist)) {
- Tdbp = (PTDBASE)CurTable->GetTo_Tdb();
+ Tdbp = CurTable->GetTo_Tdb();
// Tdbp->SetMode(Mode);
// Tdbp->ResetDB();
// Tdbp->ResetSize();
@@ -515,7 +516,7 @@ int TDBTBL::ReadDB(PGLOBAL g)
/* Continue reading from next table file. */
/***************************************************************/
Tdbp->CloseDB(g);
- Tdbp = (PTDBASE)CurTable->GetTo_Tdb();
+ Tdbp = CurTable->GetTo_Tdb();
// Check and initialize the subtable columns
for (PCOL cp = Columns; cp; cp = cp->GetNext())
@@ -609,13 +610,13 @@ void TDBTBM::ResetDB(void)
// Local tables
for (PTABLE tabp = Tablist; tabp; tabp = tabp->GetNext())
- ((PTDBASE)tabp->GetTo_Tdb())->ResetDB();
+ tabp->GetTo_Tdb()->ResetDB();
// Remote tables
for (PTBMT tp = Tmp; tp; tp = tp->Next)
- ((PTDBASE)tp->Tap->GetTo_Tdb())->ResetDB();
+ tp->Tap->GetTo_Tdb()->ResetDB();
- Tdbp = (Tablist) ? (PTDBASE)Tablist->GetTo_Tdb() : NULL;
+ Tdbp = (Tablist) ? Tablist->GetTo_Tdb() : NULL;
Crp = 0;
} // end of ResetDB
@@ -716,7 +717,7 @@ bool TDBTBM::OpenDB(PGLOBAL g)
/* Proceed with local tables. */
/*********************************************************************/
if ((CurTable = Tablist)) {
- Tdbp = (PTDBASE)CurTable->GetTo_Tdb();
+ Tdbp = CurTable->GetTo_Tdb();
// Tdbp->SetMode(Mode);
// Check and initialize the subtable columns
@@ -808,7 +809,7 @@ int TDBTBM::ReadNextRemote(PGLOBAL g)
} // endif Curtable
- Tdbp = (PTDBASE)Cmp->Tap->GetTo_Tdb();
+ Tdbp = Cmp->Tap->GetTo_Tdb();
// Check and initialize the subtable columns
for (PCOL cp = Columns; cp; cp = cp->GetNext())
diff --git a/storage/connect/tabutil.cpp b/storage/connect/tabutil.cpp
index 4069cdbed2a..762c61bd1a1 100644
--- a/storage/connect/tabutil.cpp
+++ b/storage/connect/tabutil.cpp
@@ -1,7 +1,7 @@
/************* Tabutil cpp Declares Source Code File (.CPP) ************/
-/* Name: TABUTIL.CPP Version 1.1 */
+/* Name: TABUTIL.CPP Version 1.2 */
/* */
-/* (C) Copyright to the author Olivier BERTRAND 2013 - 2016 */
+/* (C) Copyright to the author Olivier BERTRAND 2013 - 2017 */
/* */
/* Utility function used by the PROXY, XCOL, OCCUR, and TBL tables. */
/***********************************************************************/
@@ -45,8 +45,9 @@
#include "myutil.h"
#include "valblk.h"
#include "resource.h"
-#include "reldef.h"
+//#include "reldef.h"
#include "xtable.h"
+#include "tabext.h"
#include "tabmysql.h"
#include "tabcol.h"
#include "tabutil.h"
@@ -356,7 +357,7 @@ TDBPRX::TDBPRX(PTDBPRX tdbp) : TDBASE(tdbp)
} // end of TDBPRX copy constructor
// Method
-PTDB TDBPRX::CopyOne(PTABS t)
+PTDB TDBPRX::Clone(PTABS t)
{
PTDB tp;
PPRXCOL cp1, cp2;
@@ -370,12 +371,12 @@ PTDB TDBPRX::CopyOne(PTABS t)
} // endfor cp1
return tp;
- } // end of CopyOne
+ } // end of Clone
/***********************************************************************/
/* Get the PTDB of the sub-table. */
/***********************************************************************/
-PTDBASE TDBPRX::GetSubTable(PGLOBAL g, PTABLE tabp, bool b)
+PTDB TDBPRX::GetSubTable(PGLOBAL g, PTABLE tabp, bool b)
{
const char *sp = NULL;
char *db, *name;
@@ -456,13 +457,13 @@ PTDBASE TDBPRX::GetSubTable(PGLOBAL g, PTABLE tabp, bool b)
if (trace && tdbp)
htrc("Subtable %s in %s\n",
- name, SVP(((PTDBASE)tdbp)->GetDef()->GetDB()));
+ name, SVP(tdbp->GetDef()->GetDB()));
err:
if (s)
free_table_share(s);
- return (PTDBASE)tdbp;
+ return tdbp;
} // end of GetSubTable
/***********************************************************************/
@@ -560,9 +561,9 @@ bool TDBPRX::OpenDB(PGLOBAL g)
/* its column blocks in mode write (required by XML tables). */
/*********************************************************************/
if (Mode == MODE_UPDATE) {
- PTDBASE utp;
+ PTDB utp;
- if (!(utp= (PTDBASE)Tdbp->Duplicate(g))) {
+ if (!(utp= Tdbp->Duplicate(g))) {
sprintf(g->Message, MSG(INV_UPDT_TABLE), Tdbp->GetName());
return true;
} // endif tp
@@ -681,7 +682,7 @@ char *PRXCOL::Decode(PGLOBAL g, const char *cnm)
/* PRXCOL initialization routine. */
/* Look for the matching column in the object table. */
/***********************************************************************/
-bool PRXCOL::Init(PGLOBAL g, PTDBASE tp)
+bool PRXCOL::Init(PGLOBAL g, PTDB tp)
{
if (!tp)
tp = ((PTDBPRX)To_Tdb)->Tdbp;
diff --git a/storage/connect/tabutil.h b/storage/connect/tabutil.h
index b320d169b36..8e56aecff86 100644
--- a/storage/connect/tabutil.h
+++ b/storage/connect/tabutil.h
@@ -67,7 +67,7 @@ class DllExport TDBPRX : public TDBASE {
{return (PTDB)new(g) TDBPRX(this);}
// Methods
- virtual PTDB CopyOne(PTABS t);
+ virtual PTDB Clone(PTABS t);
virtual int GetRecpos(void) {return Tdbp->GetRecpos();}
virtual void ResetDB(void) {Tdbp->ResetDB();}
virtual int RowNumber(PGLOBAL g, bool b = FALSE);
@@ -83,12 +83,12 @@ class DllExport TDBPRX : public TDBASE {
virtual int WriteDB(PGLOBAL g);
virtual int DeleteDB(PGLOBAL g, int irc);
virtual void CloseDB(PGLOBAL g) {if (Tdbp) Tdbp->CloseDB(g);}
- PTDBASE GetSubTable(PGLOBAL g, PTABLE tabp, bool b = false);
+ PTDB GetSubTable(PGLOBAL g, PTABLE tabp, bool b = false);
void RemoveNext(PTABLE tp);
protected:
// Members
- PTDBASE Tdbp; // The object table
+ PTDB Tdbp; // The object table
}; // end of class TDBPRX
/***********************************************************************/
@@ -115,7 +115,7 @@ class DllExport PRXCOL : public COLBLK {
{return false;}
virtual void ReadColumn(PGLOBAL g);
virtual void WriteColumn(PGLOBAL g);
- virtual bool Init(PGLOBAL g, PTDBASE tp);
+ virtual bool Init(PGLOBAL g, PTDB tp);
protected:
char *Decode(PGLOBAL g, const char *cnm);
diff --git a/storage/connect/tabvct.cpp b/storage/connect/tabvct.cpp
index e788529075f..282fb55a43c 100644
--- a/storage/connect/tabvct.cpp
+++ b/storage/connect/tabvct.cpp
@@ -241,7 +241,7 @@ PTDB VCTDEF::GetTable(PGLOBAL g, MODE mode)
/*********************************************************************/
if (mode != MODE_INSERT)
if (tdbp->GetBlockValues(g))
- PushWarning(g, (PTDBASE)tdbp);
+ PushWarning(g, tdbp);
// return NULL; // causes a crash when deleting index
return tdbp;
@@ -263,7 +263,7 @@ TDBVCT::TDBVCT(PGLOBAL g, PTDBVCT tdbp) : TDBFIX(g, tdbp)
} // end of TDBVCT copy constructor
// Method
-PTDB TDBVCT::CopyOne(PTABS t)
+PTDB TDBVCT::Clone(PTABS t)
{
PTDB tp;
PVCTCOL cp1, cp2;
@@ -277,7 +277,7 @@ PTDB TDBVCT::CopyOne(PTABS t)
} // endfor cp1
return tp;
- } // end of CopyOne
+ } // end of Clone
/***********************************************************************/
/* Allocate VCT column description block. */
diff --git a/storage/connect/tabvct.h b/storage/connect/tabvct.h
index 8ad3c8e21be..189a9ae2221 100644
--- a/storage/connect/tabvct.h
+++ b/storage/connect/tabvct.h
@@ -68,7 +68,7 @@ class DllExport TDBVCT : public TDBFIX {
bool IsSplit(void) {return ((VCTDEF*)To_Def)->Split;}
// Methods
- virtual PTDB CopyOne(PTABS t);
+ virtual PTDB Clone(PTABS t);
virtual bool IsUsingTemp(PGLOBAL g);
// Database routines
diff --git a/storage/connect/tabvir.cpp b/storage/connect/tabvir.cpp
index 356fc981357..155c71fe268 100644
--- a/storage/connect/tabvir.cpp
+++ b/storage/connect/tabvir.cpp
@@ -20,7 +20,7 @@
#include "plgdbsem.h"
#include "filter.h"
#include "xtable.h"
-#include "reldef.h"
+//#include "reldef.h"
#include "colblk.h"
#include "mycat.h" // for FNC_COL
#include "tabvir.h"
diff --git a/storage/connect/tabwmi.cpp b/storage/connect/tabwmi.cpp
index 98a44b9d635..4871a1d66dc 100644
--- a/storage/connect/tabwmi.cpp
+++ b/storage/connect/tabwmi.cpp
@@ -1,5 +1,5 @@
/***********************************************************************/
-/* TABWMI: Author Olivier Bertrand -- PlugDB -- 2012 - 2013 */
+/* TABWMI: Author Olivier Bertrand -- PlugDB -- 2012 - 2017 */
/* TABWMI: Virtual table to get WMI information. */
/***********************************************************************/
#if !defined(__WIN__)
@@ -11,8 +11,9 @@
#include "global.h"
#include "plgdbsem.h"
#include "mycat.h"
-#include "reldef.h"
+//#include "reldef.h"
#include "xtable.h"
+#include "tabext.h"
#include "colblk.h"
//#include "filter.h"
//#include "xindex.h"
@@ -62,7 +63,7 @@ PWMIUT InitWMI(PGLOBAL g, char *nsp, char *classname)
if (FAILED(res)) {
sprintf(g->Message, "Failed to initialize COM library. "
- "Error code = %p", res);
+ "Error code = %x", res);
return NULL;
} // endif res
@@ -85,7 +86,7 @@ PWMIUT InitWMI(PGLOBAL g, char *nsp, char *classname)
(void**) &loc);
if (FAILED(res)) {
sprintf(g->Message, "Failed to create Locator. "
- "Error code = %p", res);
+ "Error code = %x", res);
CoUninitialize();
return NULL;
} // endif res
@@ -94,7 +95,7 @@ PWMIUT InitWMI(PGLOBAL g, char *nsp, char *classname)
NULL, NULL, NULL, 0, NULL, NULL, &wp->Svc);
if (FAILED(res)) {
- sprintf(g->Message, "Could not connect. Error code = %p", res);
+ sprintf(g->Message, "Could not connect. Error code = %x", res);
loc->Release();
CoUninitialize();
return NULL;
@@ -423,7 +424,7 @@ bool TDBWMI::Initialize(PGLOBAL g)
if (FAILED(Res)) {
sprintf(g->Message, "Failed to initialize COM library. "
- "Error code = %p", Res);
+ "Error code = %x", Res);
return true; // Program has failed.
} // endif Res
@@ -436,7 +437,7 @@ bool TDBWMI::Initialize(PGLOBAL g)
if (FAILED(Res)) {
sprintf(g->Message, "Failed to create Locator. "
- "Error code = %p", Res);
+ "Error code = %x", Res);
CoUninitialize();
return true; // Program has failed.
} // endif Res
@@ -448,7 +449,7 @@ bool TDBWMI::Initialize(PGLOBAL g)
NULL, NULL,0, NULL, 0, 0, &Svc);
if (FAILED(Res)) {
- sprintf(g->Message, "Could not connect. Error code = %p", Res);
+ sprintf(g->Message, "Could not connect. Error code = %x", Res);
loc->Release();
CoUninitialize();
return true; // Program has failed.
@@ -463,7 +464,7 @@ bool TDBWMI::Initialize(PGLOBAL g)
RPC_C_IMP_LEVEL_IMPERSONATE, NULL, EOAC_NONE);
if (FAILED(Res)) {
- sprintf(g->Message, "Could not set proxy. Error code = 0x", Res);
+ sprintf(g->Message, "Could not set proxy. Error code = %x", Res);
Svc->Release();
CoUninitialize();
return true; // Program has failed.
@@ -573,7 +574,7 @@ bool TDBWMI::GetWMIInfo(PGLOBAL g)
NULL, &Enumerator);
if (FAILED(Rc)) {
- sprintf(g->Message, "Query %s failed. Error code = %p", cmd, Rc);
+ sprintf(g->Message, "Query %s failed. Error code = %x", cmd, Rc);
Svc->Release();
CoUninitialize();
return true; // Program has failed.
diff --git a/storage/connect/tabxcl.cpp b/storage/connect/tabxcl.cpp
index add61431493..93a24accc3c 100644
--- a/storage/connect/tabxcl.cpp
+++ b/storage/connect/tabxcl.cpp
@@ -1,7 +1,7 @@
/************* TabXcl CPP Declares Source Code File (.CPP) *************/
/* Name: TABXCL.CPP Version 1.0 */
/* */
-/* (C) Copyright to the author Olivier BERTRAND 2013 */
+/* (C) Copyright to the author Olivier BERTRAND 2013-2017 */
/* */
/* XCOL: Table having one column containing several values */
/* comma separated. When creating the table, the name of the X */
@@ -45,12 +45,12 @@
#include "plgdbsem.h"
#include "plgcnx.h" // For DB types
#include "resource.h"
-#include "reldef.h"
+#include "xtable.h"
+#include "tabext.h"
#include "filamtxt.h"
#include "tabdos.h"
#include "tabcol.h"
#include "tabxcl.h"
-#include "xtable.h"
#include "tabmysql.h"
#include "ha_connect.h"
@@ -246,7 +246,7 @@ XCLCOL::XCLCOL(PCOLDEF cdp, PTDB tdbp, PCOL cprec, int i)
/* XCLCOL initialization routine. */
/* Allocate Cbuf that will contain the Colp value. */
/***********************************************************************/
-bool XCLCOL::Init(PGLOBAL g, PTDBASE tp)
+bool XCLCOL::Init(PGLOBAL g, PTDB tp)
{
if (PRXCOL::Init(g, tp))
return true;
diff --git a/storage/connect/tabxcl.h b/storage/connect/tabxcl.h
index 291f0b4263a..fde000ee709 100644
--- a/storage/connect/tabxcl.h
+++ b/storage/connect/tabxcl.h
@@ -91,7 +91,7 @@ class XCLCOL : public PRXCOL {
using PRXCOL::Init;
virtual void Reset(void) {} // Evaluated only by TDBXCL
virtual void ReadColumn(PGLOBAL g);
- virtual bool Init(PGLOBAL g, PTDBASE tp = NULL);
+ virtual bool Init(PGLOBAL g, PTDB tp = NULL);
protected:
// Default constructor not to be used
diff --git a/storage/connect/tabxml.cpp b/storage/connect/tabxml.cpp
index 3b8229fcf51..52cf3d3812f 100644
--- a/storage/connect/tabxml.cpp
+++ b/storage/connect/tabxml.cpp
@@ -42,7 +42,7 @@
/***********************************************************************/
#include "global.h"
#include "plgdbsem.h"
-#include "reldef.h"
+//#include "reldef.h"
#include "xtable.h"
#include "colblk.h"
#include "mycat.h"
@@ -537,6 +537,11 @@ PTDB XMLDEF::GetTable(PGLOBAL g, MODE m)
if (Catfunc == FNC_COL)
return new(g) TDBXCT(this);
+ if (Zipped && !(m == MODE_READ || m == MODE_ANY)) {
+ strcpy(g->Message, "ZIpped XML tables are read only");
+ return NULL;
+ } // endif Zipped
+
PTDBASE tdbp = new(g) TDBXML(this);
if (Multiple)
@@ -655,7 +660,7 @@ TDBXML::TDBXML(PTDBXML tdbp) : TDBASE(tdbp)
} // end of TDBXML copy constructor
// Used for update
-PTDB TDBXML::CopyOne(PTABS t)
+PTDB TDBXML::Clone(PTABS t)
{
PTDB tp;
PXMLCOL cp1, cp2;
@@ -669,7 +674,7 @@ PTDB TDBXML::CopyOne(PTABS t)
} // endfor cp1
return tp;
- } // end of CopyOne
+ } // end of Clone
/***********************************************************************/
/* Allocate XML column description block. */
@@ -926,7 +931,7 @@ bool TDBXML::Initialize(PGLOBAL g)
if (rc)
sprintf(g->Message, "%s: %s", MSG(COM_ERROR), buf);
else
- sprintf(g->Message, "%s hr=%p", MSG(COM_ERROR), e.Error());
+ sprintf(g->Message, "%s hr=%x", MSG(COM_ERROR), e.Error());
goto error;
#endif // __WIN__
diff --git a/storage/connect/tabxml.h b/storage/connect/tabxml.h
index 6c586d79dec..65b353072cb 100644
--- a/storage/connect/tabxml.h
+++ b/storage/connect/tabxml.h
@@ -71,7 +71,7 @@ class DllExport TDBXML : public TDBASE {
virtual PTDB Duplicate(PGLOBAL g) {return (PTDB)new(g) TDBXML(this);}
// Methods
- virtual PTDB CopyOne(PTABS t);
+ virtual PTDB Clone(PTABS t);
virtual int GetRecpos(void);
virtual int GetProgCur(void) {return N;}
virtual PSZ GetFile(PGLOBAL g) {return Xfile;}
diff --git a/storage/connect/tabzip.cpp b/storage/connect/tabzip.cpp
index 11f414ee154..b91059a3843 100644
--- a/storage/connect/tabzip.cpp
+++ b/storage/connect/tabzip.cpp
@@ -70,8 +70,12 @@ PCOL TDBZIP::MakeCol(PGLOBAL g, PCOLDEF cdp, PCOL cprec, int n)
/* param: filename path and the filename of the zip file to open. */
/* return: true if open, false otherwise. */
/***********************************************************************/
-bool TDBZIP::open(PGLOBAL g, const char *filename)
+bool TDBZIP::open(PGLOBAL g, const char *fn)
{
+ char filename[_MAX_PATH];
+
+ PlugSetPath(filename, fn, GetPath());
+
if (!zipfile && !(zipfile = unzOpen64(filename)))
sprintf(g->Message, "Zipfile open error");
@@ -102,7 +106,7 @@ int TDBZIP::Cardinality(PGLOBAL g)
unz_global_info64 ginfo;
int err = unzGetGlobalInfo64(zipfile, &ginfo);
- Cardinal = (err == UNZ_OK) ? ginfo.number_entry : 0;
+ Cardinal = (err == UNZ_OK) ? (int)ginfo.number_entry : 0;
} else
Cardinal = 0;
@@ -221,6 +225,14 @@ void ZIPCOL::ReadColumn(PGLOBAL g)
case 3:
Value->SetValue((int)Tdbz->finfo.compression_method);
break;
+ case 4:
+ Tdbz->finfo.tmu_date.tm_year -= 1900;
+
+ if (((DTVAL*)Value)->MakeTime((tm*)&Tdbz->finfo.tmu_date))
+ Value->SetNull(true);
+
+ Tdbz->finfo.tmu_date.tm_year += 1900;
+ break;
default:
Value->SetValue_psz((PSZ)Tdbz->fn);
} // endswitch flag
diff --git a/storage/connect/tabzip.h b/storage/connect/tabzip.h
index 6f1735258e7..dcec3475371 100644
--- a/storage/connect/tabzip.h
+++ b/storage/connect/tabzip.h
@@ -20,7 +20,7 @@ typedef class ZIPCOL *PZIPCOL;
/***********************************************************************/
class DllExport ZIPDEF : public DOSDEF { /* Table description */
friend class TDBZIP;
- friend class ZIPFAM;
+ friend class UNZFAM;
public:
// Constructor
ZIPDEF(void) {}
diff --git a/storage/connect/user_connect.cc b/storage/connect/user_connect.cc
index 34d192361a5..ca3557666a4 100644
--- a/storage/connect/user_connect.cc
+++ b/storage/connect/user_connect.cc
@@ -11,7 +11,7 @@
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 */
+ Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02111-1301 USA */
/**
@file user_connect.cc
diff --git a/storage/connect/user_connect.h b/storage/connect/user_connect.h
index 7f37973f378..a883eb85934 100644
--- a/storage/connect/user_connect.h
+++ b/storage/connect/user_connect.h
@@ -11,7 +11,7 @@
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 */
+ Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02111-1301 USA */
/** @file user_connect.h
diff --git a/storage/connect/value.h b/storage/connect/value.h
index a670ade4c28..14a568c3549 100644
--- a/storage/connect/value.h
+++ b/storage/connect/value.h
@@ -271,7 +271,7 @@ class DllExport TYPVAL<PSZ>: public VALUE {
virtual void Reset(void) {*Strp = 0;}
virtual int GetValLen(void) {return Len;};
virtual int GetValPrec() {return (Ci) ? 1 : 0;}
- virtual int GetSize(void) {return (Strp) ? strlen(Strp) : 0;}
+ virtual int GetSize(void) {return (Strp) ? (int)strlen(Strp) : 0;}
virtual PSZ GetCharValue(void) {return Strp;}
virtual char GetTinyValue(void);
virtual uchar GetUTinyValue(void);
diff --git a/storage/connect/xindex.cpp b/storage/connect/xindex.cpp
index a2cf4e77b80..15fb71ab88a 100755
--- a/storage/connect/xindex.cpp
+++ b/storage/connect/xindex.cpp
@@ -81,7 +81,7 @@ int PlgMakeIndex(PGLOBAL g, PSZ name, PIXDEF pxdf, bool add)
{
int rc;
PTABLE tablep;
- PTDBASE tdbp;
+ PTDB tdbp;
PCATLG cat = PlgGetCatalog(g, true);
/*********************************************************************/
@@ -89,12 +89,12 @@ int PlgMakeIndex(PGLOBAL g, PSZ name, PIXDEF pxdf, bool add)
/*********************************************************************/
tablep = new(g) XTAB(name);
- if (!(tdbp = (PTDBASE)cat->GetTable(g, tablep)))
+ if (!(tdbp = cat->GetTable(g, tablep)))
rc = RC_NF;
else if (!tdbp->GetDef()->Indexable()) {
sprintf(g->Message, MSG(TABLE_NO_INDEX), name);
rc = RC_NF;
- } else if ((rc = tdbp->MakeIndex(g, pxdf, add)) == RC_INFO)
+ } else if ((rc = ((PTDBASE)tdbp)->MakeIndex(g, pxdf, add)) == RC_INFO)
rc = RC_OK; // No or remote index
return rc;
@@ -2738,7 +2738,7 @@ bool XHUGE::Read(PGLOBAL g, void *buf, int n, int size)
} // endif nbr
} else {
- char *buf[256];
+ char buf[256];
DWORD drc = GetLastError();
FormatMessage(FORMAT_MESSAGE_FROM_SYSTEM |
diff --git a/storage/connect/xindex.h b/storage/connect/xindex.h
index ef2e934e5ee..2d10d72722e 100644
--- a/storage/connect/xindex.h
+++ b/storage/connect/xindex.h
@@ -184,7 +184,7 @@ class DllExport XXBASE : public CSORT, public BLOCK {
virtual bool IsRandom(void) {return true;}
virtual bool IsDynamic(void) {return Dynamic;}
virtual void SetDynamic(bool dyn) {Dynamic = dyn;}
- virtual bool HaveSame(void) {return false;}
+//virtual bool HaveSame(void) {return false;}
virtual int GetCurPos(void) {return Cur_K;}
virtual void SetNval(int n) {assert(n == 1);}
virtual void SetOp(OPVAL op) {Op = op;}
@@ -256,7 +256,7 @@ class DllExport XINDEX : public XXBASE {
// Implementation
virtual IDT GetType(void) {return TYPE_IDX_INDX;}
virtual bool IsMul(void) {return (Nval < Nk) ? true : Mul;}
- virtual bool HaveSame(void) {return Op == OP_SAME;}
+//virtual bool HaveSame(void) {return Op == OP_SAME;}
virtual int GetCurPos(void) {return (Pex) ? Pex[Cur_K] : Cur_K;}
virtual void SetNval(int n) {Nval = n;}
int GetMaxSame(void) {return MaxSame;}
diff --git a/storage/connect/xobject.h b/storage/connect/xobject.h
index d78cd09f9a4..8f6c23c4aeb 100644
--- a/storage/connect/xobject.h
+++ b/storage/connect/xobject.h
@@ -127,7 +127,8 @@ class DllExport STRING : public BLOCK {
// Implementation
inline int GetLength(void) {return (int)Length;}
- inline PSZ GetStr(void) {return Strp;}
+ inline void SetLength(uint n) {Length = n;}
+ inline PSZ GetStr(void) {return Strp;}
inline uint32 GetSize(void) {return Size;}
// Methods
diff --git a/storage/connect/xtable.h b/storage/connect/xtable.h
index e18a08a54b8..4aeea05946a 100644
--- a/storage/connect/xtable.h
+++ b/storage/connect/xtable.h
@@ -1,7 +1,7 @@
/**************** Table H Declares Source Code File (.H) ***************/
-/* Name: TABLE.H Version 2.3 */
+/* Name: TABLE.H Version 2.4 */
/* */
-/* (C) Copyright to the author Olivier BERTRAND 1999-2015 */
+/* (C) Copyright to the author Olivier BERTRAND 1999-2017 */
/* */
/* This file contains the TBX, OPJOIN and TDB class definitions. */
/***********************************************************************/
@@ -17,6 +17,7 @@
#include "block.h"
#include "colblk.h"
#include "m_ctype.h"
+#include "reldef.h"
typedef class CMD *PCMD;
typedef struct st_key_range key_range;
@@ -32,24 +33,30 @@ class CMD : public BLOCK {
char *Cmd;
}; // end of class CMD
+#if 0
// Condition filter structure
class CONDFIL : public BLOCK {
public:
// Constructor
CONDFIL(const Item *cond, uint idx, AMT type)
{
- Cond = cond; Idx = idx; Type = type; Body = NULL; Op = OP_XX; Cmds = NULL;
+ Cond = cond; Idx = idx; Type = type; Op = OP_XX;
+ Cmds = NULL; All = true; Body = NULL, Having = NULL;
}
// Members
const Item *Cond;
AMT Type;
uint Idx;
- char *Body;
OPVAL Op;
PCMD Cmds;
+ bool All;
+ char *Body;
+ char *Having;
}; // end of class CONDFIL
+#endif // 0
+typedef class EXTCOL *PEXTCOL;
typedef class CONDFIL *PCFIL;
typedef class TDBCAT *PTDBCAT;
typedef class CATCOL *PCATCOL;
@@ -64,47 +71,61 @@ class DllExport TDB: public BLOCK { // Table Descriptor Block.
TDB(PTDB tdbp);
// Implementation
- static void SetTnum(int n) {Tnum = n;}
- inline PTDB GetOrig(void) {return To_Orig;}
- inline TUSE GetUse(void) {return Use;}
- inline PCFIL GetCondFil(void) {return To_CondFil;}
- inline LPCSTR GetName(void) {return Name;}
- inline PTABLE GetTable(void) {return To_Table;}
- inline PCOL GetColumns(void) {return Columns;}
- inline int GetDegree(void) {return Degree;}
- inline MODE GetMode(void) {return Mode;}
- inline PFIL GetFilter(void) {return To_Filter;}
- inline void SetFilter(PFIL fp) {To_Filter = fp;}
- inline void SetOrig(PTDB txp) {To_Orig = txp;}
- inline void SetUse(TUSE n) {Use = n;}
- inline void SetCondFil(PCFIL cfp) {To_CondFil = cfp;}
- inline void SetNext(PTDB tdbp) {Next = tdbp;}
- inline void SetName(LPCSTR name) {Name = name;}
- inline void SetTable(PTABLE tablep) {To_Table = tablep;}
- inline void SetColumns(PCOL colp) {Columns = colp;}
- inline void SetDegree(int degree) {Degree = degree;}
- inline void SetMode(MODE mode) {Mode = mode;}
+ static void SetTnum(int n) {Tnum = n;}
+ inline PTABDEF GetDef(void) {return To_Def;}
+ inline PTDB GetOrig(void) {return To_Orig;}
+ inline TUSE GetUse(void) {return Use;}
+ inline PCFIL GetCondFil(void) {return To_CondFil;}
+ inline LPCSTR GetName(void) {return Name;}
+ inline PTABLE GetTable(void) {return To_Table;}
+ inline PCOL GetColumns(void) {return Columns;}
+ inline int GetDegree(void) {return Degree;}
+ inline MODE GetMode(void) {return Mode;}
+ inline PFIL GetFilter(void) {return To_Filter;}
+ inline PCOL GetSetCols(void) {return To_SetCols;}
+ inline void SetSetCols(PCOL colp) {To_SetCols = colp;}
+ inline void SetFilter(PFIL fp) {To_Filter = fp;}
+ inline void SetOrig(PTDB txp) {To_Orig = txp;}
+ inline void SetUse(TUSE n) {Use = n;}
+ inline void SetCondFil(PCFIL cfp) {To_CondFil = cfp;}
+ inline void SetNext(PTDB tdbp) {Next = tdbp;}
+ inline void SetName(LPCSTR name) {Name = name;}
+ inline void SetTable(PTABLE tablep) {To_Table = tablep;}
+ inline void SetColumns(PCOL colp) {Columns = colp;}
+ inline void SetDegree(int degree) {Degree = degree;}
+ inline void SetMode(MODE mode) {Mode = mode;}
// Properties
- virtual AMT GetAmType(void) {return TYPE_AM_ERROR;}
- virtual int GetTdb_No(void) {return Tdb_No;}
- virtual PTDB GetNext(void) {return Next;}
- virtual PCATLG GetCat(void) {return NULL;}
- virtual void SetAbort(bool) {;}
+ virtual AMT GetAmType(void) {return TYPE_AM_ERROR;}
+ virtual bool IsRemote(void) {return false;}
+ virtual bool IsIndexed(void) {return false;}
+ virtual int GetTdb_No(void) {return Tdb_No;}
+ virtual PTDB GetNext(void) {return Next;}
+ virtual PCATLG GetCat(void) {return NULL;}
+ virtual void SetAbort(bool) {;}
+ virtual PKXBASE GetKindex(void) {return NULL;}
// Methods
virtual bool IsSame(PTDB tp) {return tp == this;}
- virtual bool IsSpecial(PSZ name) = 0;
- virtual bool GetBlockValues(PGLOBAL) {return false;}
+ virtual bool IsSpecial(PSZ name);
+ virtual bool IsReadOnly(void) {return Read_Only;}
+ virtual bool IsView(void) {return FALSE;}
+ virtual PSZ GetPath(void);
+ virtual RECFM GetFtype(void) {return RECFM_NAF;}
+ virtual bool GetBlockValues(PGLOBAL) { return false; }
virtual int Cardinality(PGLOBAL) {return 0;}
- virtual int GetMaxSize(PGLOBAL) = 0;
+ virtual int GetRecpos(void) = 0;
+ virtual bool SetRecpos(PGLOBAL g, int recpos);
+ virtual int GetMaxSize(PGLOBAL) = 0;
virtual int GetProgMax(PGLOBAL) = 0;
- virtual int GetProgCur(void) = 0;
- virtual int RowNumber(PGLOBAL g, bool b = false);
- virtual bool IsReadOnly(void) {return true;}
- virtual const CHARSET_INFO *data_charset() {return NULL;}
+ virtual int GetProgCur(void) {return GetRecpos();}
+ virtual PSZ GetFile(PGLOBAL) {return "Not a file";}
+ virtual void SetFile(PGLOBAL, PSZ) {}
+ virtual void ResetDB(void) {}
+ virtual void ResetSize(void) {MaxSize = -1;}
+ virtual int RowNumber(PGLOBAL g, bool b = false);
virtual PTDB Duplicate(PGLOBAL) {return NULL;}
- virtual PTDB CopyOne(PTABS) {return this;}
+ virtual PTDB Clone(PTABS) {return this;}
virtual PTDB Copy(PTABS t);
virtual void PrintAM(FILE *f, char *m)
{fprintf(f, "%s AM(%d)\n", m, GetAmType());}
@@ -112,10 +133,15 @@ class DllExport TDB: public BLOCK { // Table Descriptor Block.
virtual void Print(PGLOBAL g, char *ps, uint z);
virtual PSZ GetServer(void) = 0;
virtual int GetBadLines(void) {return 0;}
+ virtual CHARSET_INFO *data_charset(void);
- // Database pure virtual routines
- virtual PCOL ColDB(PGLOBAL g, PSZ name, int num) = 0;
- virtual void MarkDB(PGLOBAL, PTDB) = 0;
+ // Database routines
+ virtual PCOL ColDB(PGLOBAL g, PSZ name, int num);
+ virtual PCOL MakeCol(PGLOBAL, PCOLDEF, PCOL, int)
+ {assert(false); return NULL;}
+ virtual PCOL InsertSpecialColumn(PCOL colp);
+ virtual PCOL InsertSpcBlk(PGLOBAL g, PCOLDEF cdp);
+ virtual void MarkDB(PGLOBAL g, PTDB tdb2);
virtual bool OpenDB(PGLOBAL) = 0;
virtual int ReadDB(PGLOBAL) = 0;
virtual int WriteDB(PGLOBAL) = 0;
@@ -126,20 +152,26 @@ class DllExport TDB: public BLOCK { // Table Descriptor Block.
protected:
// Members
- PTDB To_Orig; // Pointer to original if it is a copy
- TUSE Use;
- PFIL To_Filter;
- PCFIL To_CondFil; // To condition filter structure
- static int Tnum; // Used to generate Tdb_no's
- const int Tdb_No; // GetTdb_No() is always 0 for OPJOIN
- PTDB Next; // Next in linearized queries
- PTABLE To_Table; // Points to the XTAB object
- LPCSTR Name; // Table name
- PCOL Columns; // Points to the first column of the table
- MODE Mode; // 10 Read, 30 Update, 40 Insert, 50 Delete
- int Degree; // Number of columns
- int Cardinal; // Table number of rows
- }; // end of class TDB
+ PTDB To_Orig; // Pointer to original if it is a copy
+ PTABDEF To_Def; // Points to catalog description block
+ TUSE Use;
+ PFIL To_Filter;
+ PCFIL To_CondFil; // To condition filter structure
+ static int Tnum; // Used to generate Tdb_no's
+ const int Tdb_No; // GetTdb_No() is always 0 for OPJOIN
+ PTDB Next; // Next in linearized queries
+ PTABLE To_Table; // Points to the XTAB object
+ LPCSTR Name; // Table name
+ PCOL Columns; // Points to the first column of the table
+ PCOL To_SetCols; // Points to updated columns
+ MODE Mode; // 10 Read, 30 Update, 40 Insert, 50 Delete
+ int Degree; // Number of columns
+ int Cardinal; // Table number of rows
+ int MaxSize; // Max size in number of lines
+ bool Read_Only; // True for read only tables
+ const CHARSET_INFO *m_data_charset;
+ const char *csname; // Table charset name
+}; // end of class TDB
/***********************************************************************/
/* This is the base class for all query tables (except decode). */
@@ -155,50 +187,50 @@ class DllExport TDBASE : public TDB {
// Implementation
inline int GetKnum(void) {return Knum;}
- inline PTABDEF GetDef(void) {return To_Def;}
- inline PKXBASE GetKindex(void) {return To_Kindex;}
- inline PCOL GetSetCols(void) {return To_SetCols;}
- inline void SetSetCols(PCOL colp) {To_SetCols = colp;}
+//inline PTABDEF GetDef(void) {return To_Def;}
+//inline PCOL GetSetCols(void) {return To_SetCols;}
+//inline void SetSetCols(PCOL colp) {To_SetCols = colp;}
inline void SetKey_Col(PCOL *cpp) {To_Key_Col = cpp;}
inline void SetXdp(PIXDEF xdp) {To_Xdp = xdp;}
inline void SetKindex(PKXBASE kxp) {To_Kindex = kxp;}
// Properties
- void ResetKindex(PGLOBAL g, PKXBASE kxp);
+ virtual PKXBASE GetKindex(void) {return To_Kindex;}
+ void ResetKindex(PGLOBAL g, PKXBASE kxp);
PCOL Key(int i) {return (To_Key_Col) ? To_Key_Col[i] : NULL;}
// Methods
virtual bool IsUsingTemp(PGLOBAL) {return false;}
- virtual bool IsIndexed(void) {return false;}
- virtual bool IsSpecial(PSZ name);
+//virtual bool IsIndexed(void) {return false;}
+//virtual bool IsSpecial(PSZ name);
virtual PCATLG GetCat(void);
- virtual PSZ GetPath(void);
+//virtual PSZ GetPath(void);
virtual void PrintAM(FILE *f, char *m);
- virtual RECFM GetFtype(void) {return RECFM_NAF;}
+//virtual RECFM GetFtype(void) {return RECFM_NAF;}
//virtual int GetAffectedRows(void) {return -1;}
- virtual int GetRecpos(void) = 0;
- virtual bool SetRecpos(PGLOBAL g, int recpos);
- virtual bool IsReadOnly(void) {return Read_Only;}
- virtual bool IsView(void) {return FALSE;}
- virtual CHARSET_INFO *data_charset(void);
+//virtual int GetRecpos(void) = 0;
+//virtual bool SetRecpos(PGLOBAL g, int recpos);
+//virtual bool IsReadOnly(void) {return Read_Only;}
+//virtual bool IsView(void) {return FALSE;}
+//virtual CHARSET_INFO *data_charset(void);
virtual int GetProgMax(PGLOBAL g) {return GetMaxSize(g);}
- virtual int GetProgCur(void) {return GetRecpos();}
- virtual PSZ GetFile(PGLOBAL) {return "Not a file";}
- virtual int GetRemote(void) {return 0;}
- virtual void SetFile(PGLOBAL, PSZ) {}
- virtual void ResetDB(void) {}
- virtual void ResetSize(void) {MaxSize = -1;}
+//virtual int GetProgCur(void) {return GetRecpos();}
+//virtual PSZ GetFile(PGLOBAL) {return "Not a file";}
+//virtual int GetRemote(void) {return 0;}
+//virtual void SetFile(PGLOBAL, PSZ) {}
+//virtual void ResetDB(void) {}
+//virtual void ResetSize(void) {MaxSize = -1;}
virtual void RestoreNrec(void) {}
virtual int ResetTableOpt(PGLOBAL g, bool dop, bool dox);
virtual PSZ GetServer(void) {return "Current";}
// Database routines
- virtual PCOL ColDB(PGLOBAL g, PSZ name, int num);
- virtual PCOL MakeCol(PGLOBAL, PCOLDEF, PCOL, int)
- {assert(false); return NULL;}
- virtual PCOL InsertSpecialColumn(PCOL colp);
- virtual PCOL InsertSpcBlk(PGLOBAL g, PCOLDEF cdp);
- virtual void MarkDB(PGLOBAL g, PTDB tdb2);
+//virtual PCOL ColDB(PGLOBAL g, PSZ name, int num);
+//virtual PCOL MakeCol(PGLOBAL, PCOLDEF, PCOL, int)
+// {assert(false); return NULL;}
+//virtual PCOL InsertSpecialColumn(PCOL colp);
+//virtual PCOL InsertSpcBlk(PGLOBAL g, PCOLDEF cdp);
+//virtual void MarkDB(PGLOBAL g, PTDB tdb2);
virtual int MakeIndex(PGLOBAL g, PIXDEF, bool)
{strcpy(g->Message, "Remote index"); return RC_INFO;}
virtual bool ReadKey(PGLOBAL, OPVAL, const key_range *)
@@ -209,19 +241,19 @@ class DllExport TDBASE : public TDB {
"This function should not be called for this table"); return true;}
// Members
- PTABDEF To_Def; // Points to catalog description block
+//PTABDEF To_Def; // Points to catalog description block
PXOB *To_Link; // Points to column of previous relations
PCOL *To_Key_Col; // Points to key columns in current file
PKXBASE To_Kindex; // Points to table key index
PIXDEF To_Xdp; // To the index definition block
- PCOL To_SetCols; // Points to updated columns
+//PCOL To_SetCols; // Points to updated columns
RECFM Ftype; // File type: 0-var 1-fixed 2-binary (VCT)
- int MaxSize; // Max size in number of lines
+//int MaxSize; // Max size in number of lines
int Knum; // Size of key arrays
- bool Read_Only; // True for read only tables
- const CHARSET_INFO *m_data_charset;
- const char *csname; // Table charset name
- }; // end of class TDBASE
+//bool Read_Only; // True for read only tables
+//const CHARSET_INFO *m_data_charset;
+//const char *csname; // Table charset name
+}; // end of class TDBASE
/***********************************************************************/
/* The abstract base class declaration for the catalog tables. */
@@ -243,7 +275,8 @@ class DllExport TDBCAT : public TDBASE {
// Database routines
virtual PCOL MakeCol(PGLOBAL g, PCOLDEF cdp, PCOL cprec, int n);
- virtual int GetMaxSize(PGLOBAL g);
+ virtual int Cardinality(PGLOBAL) {return 10;} // To avoid assert
+ virtual int GetMaxSize(PGLOBAL g);
virtual bool OpenDB(PGLOBAL g);
virtual int ReadDB(PGLOBAL g);
virtual int WriteDB(PGLOBAL g);
@@ -275,7 +308,7 @@ class DllExport CATCOL : public COLBLK {
virtual int GetAmType(void) {return TYPE_AM_ODBC;}
// Methods
- virtual void ReadColumn(PGLOBAL g);
+ virtual void ReadColumn(PGLOBAL g);
protected:
CATCOL(void) {} // Default constructor not to be used
diff --git a/storage/connect/zip.c b/storage/connect/zip.c
index ea54853e858..4bbe31ab7dd 100644
--- a/storage/connect/zip.c
+++ b/storage/connect/zip.c
@@ -637,7 +637,7 @@ local ZPOS64_T zip64local_SearchCentralDir64(const zlib_filefunc64_32_def* pzlib
return relativeOffset;
}
-int LoadCentralDirectoryRecord(zip64_internal* pziinit)
+static int LoadCentralDirectoryRecord(zip64_internal* pziinit)
{
int err=ZIP_OK;
ZPOS64_T byte_before_the_zipfile;/* byte before the zipfile, (>0 for sfx)*/
@@ -846,7 +846,7 @@ int LoadCentralDirectoryRecord(zip64_internal* pziinit)
/************************************************************/
-extern zipFile ZEXPORT zipOpen3 (const void *pathname, int append, zipcharpc* globalcomment, zlib_filefunc64_32_def* pzlib_filefunc64_32_def)
+static zipFile zipOpen3 (const void *pathname, int append, zipcharpc* globalcomment, zlib_filefunc64_32_def* pzlib_filefunc64_32_def)
{
zip64_internal ziinit;
zip64_internal* zi;
@@ -955,7 +955,7 @@ extern zipFile ZEXPORT zipOpen64 (const void* pathname, int append)
return zipOpen3(pathname,append,NULL,NULL);
}
-int Write_LocalFileHeader(zip64_internal* zi, const char* filename, uInt size_extrafield_local, const void* extrafield_local)
+static int Write_LocalFileHeader(zip64_internal* zi, const char* filename, uInt size_extrafield_local, const void* extrafield_local)
{
/* write the local header */
int err;
@@ -1752,7 +1752,7 @@ extern int ZEXPORT zipCloseFileInZip (zipFile file)
return zipCloseFileInZipRaw (file,0,0);
}
-int Write_Zip64EndOfCentralDirectoryLocator(zip64_internal* zi, ZPOS64_T zip64eocd_pos_inzip)
+static int Write_Zip64EndOfCentralDirectoryLocator(zip64_internal* zi, ZPOS64_T zip64eocd_pos_inzip)
{
int err = ZIP_OK;
ZPOS64_T pos = zip64eocd_pos_inzip - zi->add_position_when_writting_offset;
@@ -1774,7 +1774,7 @@ int Write_Zip64EndOfCentralDirectoryLocator(zip64_internal* zi, ZPOS64_T zip64eo
return err;
}
-int Write_Zip64EndOfCentralDirectoryRecord(zip64_internal* zi, uLong size_centraldir, ZPOS64_T centraldir_pos_inzip)
+static int Write_Zip64EndOfCentralDirectoryRecord(zip64_internal* zi, uLong size_centraldir, ZPOS64_T centraldir_pos_inzip)
{
int err = ZIP_OK;
@@ -1813,7 +1813,7 @@ int Write_Zip64EndOfCentralDirectoryRecord(zip64_internal* zi, uLong size_centra
}
return err;
}
-int Write_EndOfCentralDirectoryRecord(zip64_internal* zi, uLong size_centraldir, ZPOS64_T centraldir_pos_inzip)
+static int Write_EndOfCentralDirectoryRecord(zip64_internal* zi, uLong size_centraldir, ZPOS64_T centraldir_pos_inzip)
{
int err = ZIP_OK;
@@ -1861,7 +1861,7 @@ int Write_EndOfCentralDirectoryRecord(zip64_internal* zi, uLong size_centraldir,
return err;
}
-int Write_GlobalComment(zip64_internal* zi, const char* global_comment)
+static int Write_GlobalComment(zip64_internal* zi, const char* global_comment)
{
int err = ZIP_OK;
uInt size_global_comment = 0;