/***********************************************************************/ /* Include application header files: */ /***********************************************************************/ #include"global.h"// global declarations #include"plgdbsem.h"// DB application declarations #include"reldef.h"// DB definition declares #include"filamtxt.h" #include"tabdos.h"// TDBDOS and DOSCOL class dcls #include"tabmul.h"// TDBMUL and MULCOL classes dcls
/* ------------------------- Class TDBMUL ---------------------------- */
/***********************************************************************/ /* TABMUL constructors. */ /***********************************************************************/
TDBMUL::TDBMUL(PTDB tdbp) : TDBASE(tdbp->GetDef())
{
Tdbp = tdbp;
Filenames = NULL;
Rows = 0;
Mul = tdbp->GetDef()->GetMultiple();
NumFiles = 0;
iFile = 0;
} // end of TDBMUL standard constructor
TDBMUL::TDBMUL(PTDBMUL tdbp) : TDBASE(tdbp)
{
Tdbp = tdbp->Tdbp;
Filenames = tdbp->Filenames;
Rows = tdbp->Rows;
Mul = tdbp->Mul;
NumFiles = tdbp->NumFiles;
iFile = tdbp->iFile;
} // end of TDBMUL copy constructor
// Method
PTDB TDBMUL::Clone(PTABS t)
{
PTDBMUL tp;
PGLOBAL g = t->G; // Is this really useful ???
tp = new(g) TDBMUL(this);
tp->Tdbp = Tdbp->Clone(t);
tp->Columns = tp->Tdbp->GetColumns(); return tp;
} // end of Clone
tmup->Tdbp = Tdbp->Duplicate(g); return tmup;
} // end of Duplicate
/***********************************************************************/ /* Initializes the table filename list. */ /* Note: tables created by concatenating the file components without */ /* specifying the LRECL value (that should be restricted to _MAX_PATH)*/ /* have a LRECL that is the sum of the lengths of all components. */ /* This is why we use a big filename array to take care of that. */ /***********************************************************************/
if (trace(1))
htrc("InitFileName: fn='%s'\n", filename);
if (Mul != 2) { /*******************************************************************/ /* To_File is a multiple name with special characters */ /*******************************************************************/ if (Mul == 1)
dirp = new(g) TDBDIR(PlugDup(g, filename)); else// Mul == 3 (Subdir)
dirp = new(g) TDBSDR(PlugDup(g, filename));
if (dirp->OpenDB(g)) returntrue;
if (trace(1) && Mul == 3) { int nf = ((PTDBSDR)dirp)->FindInDir(g);
htrc("Number of files = %d\n", nf);
} // endif trace
} else { /*******************************************************************/ /* To_File is the name of a file containing the file name list */ /*******************************************************************/ char *p;
FILE *stream;
if (!(stream= global_fopen(g, MSGID_OPEN_MODE_STRERROR, filename, "r"))) returntrue;
while (n < PFNZ) { if (!fgets(filename, FNSZ, stream)) {
fclose(stream); break;
} // endif fgets
p = filename + strlen(filename) - 1;
// Data files can have CRLF if (*p == '\n' || *p == '\r') {
p--; // Eliminate ending CR or LF character
if (p >= filename) if (*p == '\n' || *p == '\r')
p--; // Eliminate ending CR or LF character
} // endif p // Trim rightmost blanks for (; p >= filename && *p == ' '; p--) ;
*(++p) = '\0';
// Suballocate the file name
pfn[n++] = PlugDup(g, filename);
} // endfor n
} // endif Mul
if (n) {
Filenames = (char**)PlugSubAlloc(g, NULL, n * sizeof(char*));
for (int i = 0; i < n; i++)
Filenames[i] = pfn[i];
NumFiles = n; returnfalse;
} // end of InitFileNames
PRAGMA_REENABLE_CHECK_STACK_FRAME
/***********************************************************************/ /* The table column list is the sub-table column list. */ /***********************************************************************/
PCOL TDBMUL::ColDB(PGLOBAL g, PSZ name, int num)
{
PCOL cp;
/*********************************************************************/ /* Because special columns are directly added to the MUL block, */ /* make sure that the sub-table has the same column list, before */ /* and after the call to the ColDB function. */ /*********************************************************************/
Tdbp->SetColumns(Columns);
cp = Tdbp->ColDB(g, name, num);
Columns = Tdbp->GetColumns(); return cp;
} // end of ColDB
/***********************************************************************/ /* MUL GetProgMax: get the max value for progress information. */ /***********************************************************************/ int TDBMUL::GetProgMax(PGLOBAL g)
{ if (!Filenames && InitFileNames(g)) return -1;
return NumFiles; // This is a temporary setting
} // end of GetProgMax
/***********************************************************************/ /* MUL GetProgCur: get the current value for progress information. */ /***********************************************************************/ int TDBMUL::GetProgCur(void)
{ return iFile; // This is a temporary setting
} // end of GetProgMax
/***********************************************************************/ /* MUL 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). */ /* Can be used on Multiple FIX table only. */ /***********************************************************************/ int TDBMUL::Cardinality(PGLOBAL g)
{ if (!g) return Tdbp->Cardinality(g);
if (!Filenames && InitFileNames(g)) return -1;
int n, card = 0;
for (int i = 0; i < NumFiles; i++) {
Tdbp->SetFile(g, Filenames[i]);
Tdbp->ResetSize();
if ((n = Tdbp->Cardinality(g)) < 0) { // strcpy(g->Message, MSG(BAD_CARDINALITY)); return -1;
} // endif n
card += n;
} // endfor i
return card;
} // end of Cardinality
/***********************************************************************/ /* Sum up the sizes of all sub-tables. */ /***********************************************************************/ int TDBMUL::GetMaxSize(PGLOBAL g)
{ if (MaxSize < 0) { int i; int mxsz;
if (trace(1))
htrc("TDBMUL::GetMaxSize: Filenames=%p\n", Filenames);
/***********************************************************************/ /* Reset read/write position values. */ /***********************************************************************/ void TDBMUL::ResetDB(void)
{ for (PCOL colp = Columns; colp; colp = colp->GetNext()) if (colp->GetAmType() == TYPE_AM_FILID)
colp->COLBLK::Reset();
Tdbp->ResetDB();
} // end of ResetDB
/***********************************************************************/ /* Returns RowId if b is false or Rownum if b is true. */ /***********************************************************************/ int TDBMUL::RowNumber(PGLOBAL g, bool b)
{ return ((b) ? 0 : Rows)
+ ((iFile < NumFiles) ? Tdbp->RowNumber(g, b) : 1);
} // end of RowNumber
/***********************************************************************/ /* MUL Access Method opening routine. */ /* Open first file, other will be opened sequencially when reading. */ /***********************************************************************/ bool TDBMUL::OpenDB(PGLOBAL g)
{ if (trace(1))
htrc("MUL OpenDB: tdbp=%p tdb=R%d use=%d key=%p mode=%d\n", this, Tdb_No, Use, To_Key_Col, Mode);
if (Use == USE_OPEN) { /*******************************************************************/ /* Table already open, replace it at its beginning. */ /*******************************************************************/ if (Filenames[iFile = 0]) {
Tdbp->CloseDB(g);
Tdbp->SetUse(USE_READY);
Tdbp->SetFile(g, Filenames[iFile = 0]);
Tdbp->ResetSize();
Rows = 0;
ResetDB(); return Tdbp->OpenDB(g); // Re-open with new file name
} else returnfalse;
} // endif use
/*********************************************************************/ /* We need to calculate MaxSize before opening the query. */ /*********************************************************************/ if (GetMaxSize(g) < 0) returntrue;
/*********************************************************************/ /* Open the first table file of the list. */ /*********************************************************************/ //if (!Filenames && InitFileNames(g)) // was done in GetMaxSize // return true;
if (Filenames[iFile = 0]) {
Tdbp->SetFile(g, Filenames[0]);
Tdbp->SetMode(Mode);
Tdbp->ResetDB();
Tdbp->ResetSize();
if (Tdbp->OpenDB(g)) returntrue;
} // endif *Filenames
Use = USE_OPEN; returnfalse;
} // end of OpenDB
/***********************************************************************/ /* ReadDB: Data Base read routine for MUL access method. */ /***********************************************************************/ int TDBMUL::ReadDB(PGLOBAL g)
{ int rc;
if (NumFiles == 0) return RC_EF; elseif (To_Kindex) { /*******************************************************************/ /* Reading is by an index table. */ /*******************************************************************/
strcpy(g->Message, MSG(NO_INDEX_READ));
rc = RC_FX;
} else { /*******************************************************************/ /* Now start the reading process. */ /*******************************************************************/
retry:
rc = Tdbp->ReadDB(g);
if (rc == RC_EF) { if (Tdbp->GetDef()->GetPseudo() & 1) // Total number of rows met so far
Rows += Tdbp->RowNumber(g) - 1;
if (++iFile < NumFiles) { /***************************************************************/ /* Continue reading from next table file. */ /***************************************************************/
Tdbp->CloseDB(g);
Tdbp->SetUse(USE_READY);
Tdbp->SetFile(g, Filenames[iFile]);
Tdbp->ResetSize();
ResetDB();
if (Tdbp->OpenDB(g)) // Re-open with new file name return RC_FX;
/***********************************************************************/ /* Data Base write routine for MUL access method. */ /***********************************************************************/ int TDBMUL::WriteDB(PGLOBAL g)
{ return Tdbp->WriteDB(g); // strcpy(g->Message, MSG(TABMUL_READONLY)); // return RC_FX; // NIY
} // end of WriteDB
/***********************************************************************/ /* Data Base delete line routine for MUL access method. */ /***********************************************************************/ int TDBMUL::DeleteDB(PGLOBAL g, int)
{ // When implementing DELETE_MODE InitFileNames must be updated to // eliminate CRLF under Windows if the file is read in binary.
strcpy(g->Message, MSG(TABMUL_READONLY)); return RC_FX; // NIY
} // end of DeleteDB
/***********************************************************************/ /* Data Base close routine for MUL access method. */ /***********************************************************************/ void TDBMUL::CloseDB(PGLOBAL g)
{ if (NumFiles > 0) {
Tdbp->CloseDB(g);
iFile = NumFiles;
} // endif NumFiles
} // end of CloseDB
#if0 /* ------------------------- Class TDBMSD ---------------------------- */
// Method
PTDB TDBMSD::Clone(PTABS t)
{
PTDBMSD tp;
PGLOBAL g = t->G; // Is this really useful ???
tp = new(g) TDBMSD(this);
tp->Tdbp = Tdbp->Clone(t);
tp->Columns = tp->Tdbp->GetColumns(); return tp;
} // end of Clone
tmup->Tdbp = Tdbp->Duplicate(g); return tmup;
} // end of Duplicate
/***********************************************************************/ /* Initializes the table filename list. */ /* Note: tables created by concatenating the file components without */ /* specifying the LRECL value (that should be restricted to _MAX_PATH)*/ /* have a LRECL that is the sum of the lengths of all components. */ /* This is why we use a big filename array to take care of that. */ /***********************************************************************/ bool TDBMSD::InitFileNames(PGLOBAL g)
{ #define PFNZ 4096 #define FNSZ (_MAX_DRIVE+_MAX_DIR+_MAX_FNAME+_MAX_EXT)
PTDBSDR dirp;
PSZ pfn[PFNZ];
PSZ filename; int rc, n = 0;
if (trace(1))
htrc("in InitFileName: fn[]=%d\n", FNSZ);
filename = (char*)PlugSubAlloc(g, NULL, FNSZ);
// The sub table may need to refer to the Table original block
Tdbp->SetTable(To_Table); // Was not set at construction
NumFiles = n; returnfalse;
} // end of InitFileNames #endif// 0
/* --------------------------- Class DIRDEF -------------------------- */
/***********************************************************************/ /* DefineAM: define specific AM block values from XDB file. */ /***********************************************************************/ bool DIRDEF::DefineAM(PGLOBAL g, LPCSTR, int)
{
Desc = Fn = GetStringCatInfo(g, "Filename", NULL);
Incl = GetBoolCatInfo("Subdir", false);
Huge = GetBoolCatInfo("Huge", false);
Nodir = GetBoolCatInfo("Nodir", true); returnfalse;
} // end of DefineAM
/***********************************************************************/ /* GetTable: makes a new Table Description Block. */ /***********************************************************************/
PTDB DIRDEF::GetTable(PGLOBAL g, MODE)
{ #if0 if (Huge) returnnew(g) TDBDHR(this); // Not implemented yet else #endif if (Incl) returnnew(g) TDBSDR(this); // Including sub-directory files else returnnew(g) TDBDIR(this); // Not Including sub-directory files
} // end of GetTable
/* ------------------------- Class TDBDIR ---------------------------- */
/***********************************************************************/ /* Allocate DIR column description block. */ /***********************************************************************/
PCOL TDBDIR::MakeCol(PGLOBAL g, PCOLDEF cdp, PCOL cprec, int n)
{ returnnew(g) DIRCOL(cdp, this, cprec, n);
} // end of MakeCol
/***********************************************************************/ /* DIR GetMaxSize: returns the number of retrieved files. */ /***********************************************************************/ int TDBDIR::GetMaxSize(PGLOBAL g)
{ if (MaxSize < 0) { int n = -1; #ifdefined(_WIN32) int rc; // Start searching files in the target directory.
hSearch = FindFirstFile(Path(g), &FileData);
if (hSearch == INVALID_HANDLE_VALUE) {
rc = GetLastError();
// Close the search handle.
FindClose(hSearch); #else// !_WIN32
Path(g);
// Start searching files in the target directory. if (!(Dir = opendir(Direc))) {
snprintf(g->Message, sizeof(g->Message), MSG(BAD_DIRECTORY), Direc, strerror(errno)); return -1;
} // endif dir
while ((Entry = readdir(Dir))) {
strcat(strcpy(Fpath, Direc), Entry->d_name);
if (lstat(Fpath, &Fileinfo) < 0) {
snprintf(g->Message, sizeof(g->Message), "%s: %s", Fpath, strerror(errno)); return -1;
} elseif (S_ISREG(Fileinfo.st_mode)) // Test whether the file name matches the table name filter if (!fnmatch(Pattern, Entry->d_name, 0))
n++; // We have a match
} // endwhile Entry
// Close the DIR handle.
closedir(Dir); #endif// !_WIN32
MaxSize = n;
} // endif MaxSize
return MaxSize;
} // end of GetMaxSize
/***********************************************************************/ /* DIR Access Method opening routine. */ /* Open first file, other will be opened sequencially when reading. */ /***********************************************************************/ bool TDBDIR::OpenDB(PGLOBAL g)
{ if (trace(1))
htrc("DIR OpenDB: tdbp=%p tdb=R%d use=%d mode=%d\n", this, Tdb_No, Use, Mode);
if (Use == USE_OPEN) { /*******************************************************************/ /* Table already open, reopen it. */ /*******************************************************************/
CloseDB(g);
SetUse(USE_READY);
} // endif use
Use = USE_OPEN; #if !defined(_WIN32)
Path(g); // Be sure it is done
Dir = NULL; // For ReadDB #endif// !_WIN32 returnfalse;
} // end of OpenDB
/***********************************************************************/ /* Data Base read routine for DIR access method. */ /***********************************************************************/ int TDBDIR::ReadDB(PGLOBAL g)
{ int rc = RC_OK;
#ifdefined(_WIN32) do { if (hSearch == INVALID_HANDLE_VALUE) { /*****************************************************************/ /* Start searching files in the target directory. The use of */ /* the Path function is required when called from TDBSDR. */ /*****************************************************************/
hSearch = FindFirstFile(Path(g), &FileData);
} else { if (!FindNextFile(hSearch, &FileData)) { // Restore file name and type pattern
_splitpath(To_File, NULL, NULL, Fname, Ftype);
rc = RC_EF; break;
} else
iFile++;
} // endif hSearch
} while (Nodir && FileData.dwFileAttributes & FILE_ATTRIBUTE_DIRECTORY);
if (rc == RC_OK)
_splitpath(FileData.cFileName, NULL, NULL, Fname, Ftype);
#else// !Win32
rc = RC_NF;
if (!Dir) // Start searching files in the target directory. if (!(Dir = opendir(Direc))) {
snprintf(g->Message, sizeof(g->Message), MSG(BAD_DIRECTORY), Direc, strerror(errno));
rc = RC_FX;
} // endif dir
while (rc == RC_NF) if ((Entry = readdir(Dir))) { // We need the Fileinfo structure to get info about the file
strcat(strcpy(Fpath, Direc), Entry->d_name);
if (lstat(Fpath, &Fileinfo) < 0) {
snprintf(g->Message, sizeof(g->Message), "%s: %s", Fpath, strerror(errno));
rc = RC_FX;
} elseif (S_ISREG(Fileinfo.st_mode)) // Test whether the file name matches the table name filter if (!fnmatch(Pattern, Entry->d_name, 0)) {
iFile++; // We have a match
_splitpath(Entry->d_name, NULL, NULL, Fname, Ftype);
rc = RC_OK;
} // endif fnmatch
} else { // Restore file name and type pattern
_splitpath(To_File, NULL, NULL, Fname, Ftype);
rc = RC_EF;
} // endif Entry
#endif// !_WIN32
return rc;
} // end of ReadDB
/***********************************************************************/ /* Data Base write routine for DIR access method. */ /***********************************************************************/ int TDBDIR::WriteDB(PGLOBAL g)
{
strcpy(g->Message, MSG(TABDIR_READONLY)); return RC_FX; // NIY
} // end of WriteDB
/***********************************************************************/ /* Data Base delete line routine for DIR access method. */ /***********************************************************************/ int TDBDIR::DeleteDB(PGLOBAL g, int)
{
strcpy(g->Message, MSG(TABDIR_READONLY)); return RC_FX; // NIY
} // end of DeleteDB
/***********************************************************************/ /* Data Base close routine for MUL access method. */ /***********************************************************************/ void TDBDIR::CloseDB(PGLOBAL)
{ #ifdefined(_WIN32) // Close the search handle.
FindClose(hSearch);
hSearch = INVALID_HANDLE_VALUE; #else// !_WIN32 // Close the DIR handle if (Dir) {
closedir(Dir);
Dir = NULL;
} // endif dir #endif// !_WIN32
iFile = 0;
} // end of CloseDB
/***********************************************************************/ /* DIRCOL public constructor. */ /***********************************************************************/
DIRCOL::DIRCOL(PCOLDEF cdp, PTDB tdbp, PCOL cprec, int i, PCSZ)
: COLBLK(cdp, tdbp, i)
{ if (cprec) {
Next = cprec->GetNext();
cprec->SetNext(this);
} else {
Next = tdbp->GetColumns();
tdbp->SetColumns(this);
} // endif cprec
// Set additional DIR access method information for column.
Tdbp = (PTDBDIR)tdbp;
N = cdp->GetOffset();
} // end of DIRCOL constructor
/***********************************************************************/ /* DIRCOL constructor used for copying columns. */ /* tdbp is the pointer to the new table descriptor. */ /***********************************************************************/
DIRCOL::DIRCOL(DIRCOL *col1, PTDB tdbp) : COLBLK(col1, tdbp)
{
Tdbp = (PTDBDIR)tdbp;
N = col1->N;
} // end of DIRCOL copy constructor
#ifdefined(_WIN32) /***********************************************************************/ /* Retrieve time information from FileData. */ /***********************************************************************/ void DIRCOL::SetTimeValue(PGLOBAL g, FILETIME& ftime)
{ char tsp[24];
SYSTEMTIME stp;
/***********************************************************************/ /* ReadColumn: what this routine does is to access the information */ /* corresponding to this column and convert it to buffer type. */ /***********************************************************************/ void DIRCOL::ReadColumn(PGLOBAL g)
{ if (trace(1))
htrc("DIR ReadColumn: col %s R%d use=%.4X status=%.4X type=%d N=%d\n",
Name, Tdbp->GetTdb_No(), ColUse, Status, Buf_Type, N);
/* ------------------------- Class TDBSDR ---------------------------- */
/***********************************************************************/ /* SDR GetMaxSize: returns the number of retrieved files. */ /***********************************************************************/ int TDBSDR::GetMaxSize(PGLOBAL g)
{ if (MaxSize < 0) {
Path(g);
MaxSize = FindInDir(g);
} // endif MaxSize
return MaxSize;
} // end of GetMaxSize
/***********************************************************************/ /* SDR FindInDir: returns the number of retrieved files. */ /***********************************************************************/ int TDBSDR::FindInDir(PGLOBAL g)
{ int n = 0;
size_t m = strlen(Direc);
// Start searching files in the target directory. #ifdefined(_WIN32) int rc;
HANDLE h;
#ifdefined(PATHMATCHSPEC) if (!*Drive)
Path(g);
_makepath(Fpath, Drive, Direc, "*", "*");
h = FindFirstFile(Fpath, &FileData);
if (h == INVALID_HANDLE_VALUE) {
rc = GetLastError();
// Now search files in sub-directories.
_makepath(Fpath, Drive, Direc, "*", ".");
h = FindFirstFile(Fpath, &FileData);
if (h != INVALID_HANDLE_VALUE) { while (true) { if ((FileData.dwFileAttributes & FILE_ATTRIBUTE_DIRECTORY) &&
*FileData.cFileName != '.') { // Look in the name sub-directory
strcat(strcat(Direc, FileData.cFileName), "/");
n += FindInDir(g);
Direc[m] = '\0'; // Restore path
} // endif SUBDIR
if (!FindNextFile(h, &FileData)) break;
} // endwhile
} // endif h #endif// !PATHMATCHSPEC
// Close the search handle.
FindClose(h); #else// !_WIN32 int k;
DIR *dir = opendir(Direc);
if (!dir) {
snprintf(g->Message, sizeof(g->Message), MSG(BAD_DIRECTORY), Direc, strerror(errno)); return -1;
} // endif dir
while ((Entry = readdir(dir))) {
strcat(strcpy(Fpath, Direc), Entry->d_name);
if (lstat(Fpath, &Fileinfo) < 0) {
snprintf(g->Message, sizeof(g->Message), "%s: %s", Fpath, strerror(errno));
closedir(dir); return -1;
} elseif (S_ISDIR(Fileinfo.st_mode) && *Entry->d_name != '.') { // Look in the name sub-directory
strcat(strcat(Direc, Entry->d_name), "/");
if ((k= FindInDir(g)) < 0) {
closedir(dir); return k;
} else
n += k;
Direc[m] = '\0'; // Restore path
} elseif (S_ISREG(Fileinfo.st_mode)) // Test whether the file name matches the table name filter if (!fnmatch(Pattern, Entry->d_name, 0))
n++; // We have a match
} // endwhile readdir
// Close the DIR handle.
closedir(dir); #endif// !_WIN32
return n;
} // end of FindInDir
/***********************************************************************/ /* DIR Access Method opening routine. */ /* Open first file, other will be opened sequencially when reading. */ /***********************************************************************/ bool TDBSDR::OpenDB(PGLOBAL g)
{ if (!Sub) {
Path(g);
Sub = (PSUBDIR)PlugSubAlloc(g, NULL, sizeof(SUBDIR));
Sub->Next = NULL;
Sub->Prev = NULL; #ifdefined(_WIN32)
Sub->H = INVALID_HANDLE_VALUE;
Sub->Len = strlen(Direc); #else// !_WIN32
Sub->D = NULL;
Sub->Len = 0; #endif// !_WIN32
} // endif To_Sub
return TDBDIR::OpenDB(g);
} // end of OpenDB
/***********************************************************************/ /* Data Base read routine for SDR access method. */ /***********************************************************************/ int TDBSDR::ReadDB(PGLOBAL g)
{ int rc;
#ifdefined(_WIN32)
again:
rc = TDBDIR::ReadDB(g);
if (rc == RC_EF) { // Are there more files in sub-directories
retry: do { if (Sub->H == INVALID_HANDLE_VALUE) { // _makepath(Fpath, Drive, Direc, "*", "."); why was this made?
_makepath(Fpath, Drive, Direc, "*", NULL);
Sub->H = FindFirstFile(Fpath, &FileData);
} elseif (!FindNextFile(Sub->H, &FileData)) {
FindClose(Sub->H);
Sub->H = INVALID_HANDLE_VALUE;
*FileData.cFileName= '\0'; break;
} // endif findnext
Sub = Sub->Next;
strcat(strcat(Direc, FileData.cFileName), "/");
Sub->Len = strlen(Direc);
// Reset Hsearch used by TDBDIR::ReadDB
FindClose(hSearch);
hSearch = INVALID_HANDLE_VALUE; goto again;
} // endif H
} // endif rc #else// !_WIN32
rc = RC_NF;
again: if (!Sub->D) // Start searching files in the target directory. if (!(Sub->D = opendir(Direc))) {
snprintf(g->Message, sizeof(g->Message), MSG(BAD_DIRECTORY), Direc, strerror(errno));
rc = RC_FX;
} // endif dir
while (rc == RC_NF) if ((Entry = readdir(Sub->D))) { // We need the Fileinfo structure to get info about the file
strcat(strcpy(Fpath, Direc), Entry->d_name);
if (lstat(Fpath, &Fileinfo) < 0) {
snprintf(g->Message, sizeof(g->Message), "%s: %s", Fpath, strerror(errno));
rc = RC_FX;
} elseif (S_ISDIR(Fileinfo.st_mode) && strcmp(Entry->d_name, ".")
&& strcmp(Entry->d_name, "..")) { // Look in the name sub-directory if (!Sub->Next) {
PSUBDIR sup;
Sub = Sub->Next;
Sub->D = NULL;
Sub->Len = strlen(Direc);
strcat(strcat(Direc, Entry->d_name), "/"); goto again;
} elseif (S_ISREG(Fileinfo.st_mode)) // Test whether the file name matches the table name filter if (!fnmatch(Pattern, Entry->d_name, 0)) {
iFile++; // We have a match
_splitpath(Entry->d_name, NULL, NULL, Fname, Ftype);
rc = RC_OK;
} // endif fnmatch
} else { // No more files. Close the DIR handle.
closedir(Sub->D);
// Are we in a sub-directory? if (Sub->Prev) { // Yes, we must continue in the parent directory
Direc[Sub->Len] = '\0';
Sub = Sub->Prev;
} else
rc = RC_EF; // No, all is finished
} // endif Entry
#endif// !_WIN32
return rc;
} // end of ReadDB
#if0 /* ------------------------- Class TDBDHR ---------------------------- */
// Method
PTDB TDBDHR::Clone(PTABS t)
{
PTDB tp;
PGLOBAL g = t->G; // Is this really useful ???
tp = new(g) TDBDHR(this);
tp->Columns = Columns; return tp;
} // end of Clone
/***********************************************************************/ /* Allocate DHR column description block. */ /***********************************************************************/
PCOL TDBDHR::MakeCol(PGLOBAL g, PCOLDEF cdp, PCOL cprec, int n)
{ returnnew(g) DHRCOL(cdp, this, cprec, n);
} // end of MakeCol
/***********************************************************************/ /* DHR GetMaxSize: returns the number of retrieved files. */ /***********************************************************************/ int TDBDHR::GetMaxSize(PGLOBAL g)
{ if (MaxSize < 0) { char filename[_MAX_PATH]; int i, rc; int n = -1;
HANDLE h;
PDBUSER dup = PlgGetUser(g);
PlugSetPath(filename, To_File, dup->Path);
// Start searching files in the target directory.
h = FindFirstFile(filename, &FileData);
if (h == INVALID_HANDLE_VALUE) { switch (rc = GetLastError()) { case ERROR_NO_MORE_FILES: case ERROR_FILE_NOT_FOUND:
n = 0; break; default:
FormatMessage(FORMAT_MESSAGE_FLAGS, NULL, rc, 0,
(LPTSTR)&filename, sizeof(filename), NULL);
snprintf(g->Message, sizeof(g->Message), MSG(BAD_FILE_HANDLE), filename);
} // endswitch rc
} else { for (n = 1;; n++) if (!FindNextFile(h, &FileData)) {
rc = GetLastError();
if (rc != ERROR_NO_MORE_FILES) {
snprintf(g->Message, sizeof(g->Message), MSG(NEXT_FILE_ERROR), rc);
n = -1;
} // endif rc
break;
} // endif FindNextFile
// Close the search handle. if (!FindClose(h) && n != -1)
strcpy(g->Message, MSG(SRCH_CLOSE_ERR));
} // endif Hsearch
MaxSize = n;
} // endif MaxSize
return MaxSize;
} // end of GetMaxSize
/***********************************************************************/ /* DHR Access Method opening routine. */ /* Open first file, other will be opened sequencially when reading. */ /***********************************************************************/ bool TDBDHR::OpenDB(PGLOBAL g)
{ if (trace(1))
htrc("DHR OpenDB: tdbp=%p tdb=R%d use=%d mode=%d\n", this, Tdb_No, Use, Mode);
if (Use == USE_OPEN) { /*******************************************************************/ /* Table already open, reopen it. */ /*******************************************************************/
CloseDB(g);
SetUse(USE_READY);
} // endif use
/*********************************************************************/ /* Direct access needed for join or sorting. */ /*********************************************************************/ if (NeedIndexing(g)) { // Direct access of DHR tables is not implemented yet
snprintf(g->Message, sizeof(g->Message), MSG(NO_DIR_INDX_RD), "DHR"); returntrue;
} // endif NeedIndexing
Use = USE_OPEN; returnfalse;
} // end of OpenDB
/***********************************************************************/ /* Data Base read routine for DHR access method. */ /***********************************************************************/ int TDBDHR::ReadDB(PGLOBAL g)
{ int rc = RC_OK;
DWORD erc;
if (rc == RC_OK)
_splitpath(FileData.cFileName, NULL, NULL, Fname, Ftype);
return rc;
} // end of ReadDB
/***********************************************************************/ /* Data Base close routine for MUL access method. */ /***********************************************************************/ void TDBDHR::CloseDB(PGLOBAL g)
{ // Close the search handle. if (!FindClose(Hsearch)) {
strcpy(g->Message, MSG(SRCH_CLOSE_ERR)); throw GetAmType();
} // endif FindClose
iFile = 0;
Hsearch = INVALID_HANDLE_VALUE;
} // end of CloseDB
/***********************************************************************/ /* DHRCOL public constructor. */ /***********************************************************************/
DHRCOL::DHRCOL(PCOLDEF cdp, PTDB tdbp, PCOL cprec, int i, PCSZ am)
: COLBLK(cdp, tdbp, i)
{ if (cprec) {
Next = cprec->GetNext();
cprec->SetNext(this);
} else {
Next = tdbp->GetColumns();
tdbp->SetColumns(this);
} // endif cprec
// Set additional DHR access method information for column.
N = cdp->GetOffset();
} // end of DOSCOL constructor
/***********************************************************************/ /* DHRCOL constructor used for copying columns. */ /* tdbp is the pointer to the new table descriptor. */ /***********************************************************************/
DHRCOL::DHRCOL(DHRCOL *col1, PTDB tdbp) : COLBLK(col1, tdbp)
{
N = col1->N;
} // end of DHRCOL copy constructor
/***********************************************************************/ /* ReadColumn: what this routine does is to access the information */ /* corresponding to this column and convert it to buffer type. */ /***********************************************************************/ void DHRCOL::ReadColumn(PGLOBAL g)
{ int rc;
PTDBDHR tdbp = (PTDBDHR)To_Tdb;
if (trace(1))
htrc("DHR ReadColumn: col %s R%d use=%.4X status=%.4X type=%d N=%d\n",
Name, tdbp->GetTdb_No(), ColUse, Status, Buf_Type, N);
/*********************************************************************/ /* Retrieve the information corresponding to the column number. */ /*********************************************************************/ switch (N) { case0: // Drive
Value->SetValue(Drive, _MAX_DRIVE); break; case1: // Path
Value->SetValue(Direc, _MAX_DHR); break; case2: // Name
Value->SetValue(Fname, _MAX_FNAME); break; case3: // Extention
Value->SetValue(Ftype, _MAX_EXT); break; case4: // Extention
Value->SetValue(tdbp->FileData.cAlternateFileName, 14); break; case5:
Value->SetValue(tdbp->FileData.dwFileAttributes); break; case6:
Value->SetValue(..................
} // end of ReadColumn #endif// 0
Messung V0.5 in Prozent
¤ Dauer der Verarbeitung: 0.20 Sekunden
(vorverarbeitet am 2026-10-08)
¤
Die Informationen auf dieser Webseite wurden
nach bestem Wissen sorgfältig zusammengestellt. Es wird jedoch weder Vollständigkeit, noch Richtigkeit,
noch Qualität der bereit gestellten Informationen zugesichert.
Bemerkung:
Die farbliche Syntaxdarstellung und die Messung sind noch experimentell.