374 unsigned char *pabyBuf;
375 int nFields, nHeadLen, iField, i;
376 char *pszBasename, *pszFullname;
382 if (strcmp(pszAccess,
"r") != 0 && strcmp(pszAccess,
"r+") != 0 && strcmp(pszAccess,
"rb") != 0 &&
383 strcmp(pszAccess,
"rb+") != 0 && strcmp(pszAccess,
"r+b") != 0)
386 if (strcmp(pszAccess,
"r") == 0)
389 if (strcmp(pszAccess,
"r+") == 0)
396 pszBasename = (
char *)
malloc(strlen(pszFilename) + 5);
397 strcpy(pszBasename, pszFilename);
398 for (i = strlen(pszBasename) - 1;
399 i > 0 && pszBasename[i] !=
'.' && pszBasename[i] !=
'/' && pszBasename[i] !=
'\\';
403 if (pszBasename[i] ==
'.')
404 pszBasename[i] =
'\0';
406 pszFullname = (
char *)
malloc(strlen(pszBasename) + 5);
407 sprintf(pszFullname,
"%s.dbf", pszBasename);
409 psDBF = (DBFHandle)calloc(1,
sizeof(DBFInfo));
410 psDBF->fp = psHooks->
FOpen(pszFullname, pszAccess);
411 memcpy(&(psDBF->sHooks), psHooks,
sizeof(
SAHooks));
413 if (psDBF->fp == NULL)
415 sprintf(pszFullname,
"%s.DBF", pszBasename);
416 psDBF->fp = psDBF->sHooks.FOpen(pszFullname, pszAccess);
419 sprintf(pszFullname,
"%s.cpg", pszBasename);
420 pfCPG = psHooks->
FOpen(pszFullname,
"r");
423 sprintf(pszFullname,
"%s.CPG", pszBasename);
424 pfCPG = psHooks->
FOpen(pszFullname,
"r");
430 if (psDBF->fp == NULL)
438 psDBF->bNoHeader =
FALSE;
439 psDBF->nCurrentRecord = -1;
440 psDBF->bCurrentRecordModified =
FALSE;
445 pabyBuf = (
unsigned char *)
malloc(nBufSize);
446 if (psDBF->sHooks.FRead(pabyBuf, 32, 1, psDBF->fp) != 1)
448 psDBF->sHooks.FClose(psDBF->fp);
450 psDBF->sHooks.FClose(pfCPG);
456 psDBF->nRecords = pabyBuf[4] + pabyBuf[5] * 256 + pabyBuf[6] * 256 * 256 + pabyBuf[7] * 256 * 256 * 256;
458 psDBF->nHeaderLength = nHeadLen = pabyBuf[8] + pabyBuf[9] * 256;
459 psDBF->nRecordLength = pabyBuf[10] + pabyBuf[11] * 256;
460 psDBF->iLanguageDriver = pabyBuf[29];
464 psDBF->sHooks.FClose(psDBF->fp);
466 psDBF->sHooks.FClose(pfCPG);
472 psDBF->nFields = nFields = (nHeadLen - 32) / 32;
474 psDBF->pszCurrentRecord = (
char *)
malloc(psDBF->nRecordLength);
480 psDBF->pszCodePage = NULL;
484 memset(pabyBuf, 0, nBufSize);
485 psDBF->sHooks.FRead(pabyBuf, nBufSize - 1, 1, pfCPG);
486 n = strcspn((
char *)pabyBuf,
"\n\r");
490 psDBF->pszCodePage = (
char *)
malloc(n + 1);
491 memcpy(psDBF->pszCodePage, pabyBuf, n + 1);
493 psDBF->sHooks.FClose(pfCPG);
495 if ((psDBF->pszCodePage == NULL) && (psDBF->iLanguageDriver != 0))
497 sprintf((
char *)pabyBuf,
"LDID/%d", psDBF->iLanguageDriver);
498 psDBF->pszCodePage = (
char *)
malloc(strlen((
char *)pabyBuf) + 1);
499 strcpy(psDBF->pszCodePage, (
char *)pabyBuf);
506 pabyBuf = (
unsigned char *)
SfRealloc(pabyBuf, nHeadLen);
507 psDBF->pszHeader = (
char *)pabyBuf;
509 psDBF->sHooks.FSeek(psDBF->fp, 32, 0);
510 if (psDBF->sHooks.FRead(pabyBuf, nHeadLen - 32, 1, psDBF->fp) != 1)
512 psDBF->sHooks.FClose(psDBF->fp);
514 free(psDBF->pszCurrentRecord);
519 psDBF->panFieldOffset = (
int *)
malloc(
sizeof(
int) * nFields);
520 psDBF->panFieldSize = (
int *)
malloc(
sizeof(
int) * nFields);
521 psDBF->panFieldDecimals = (
int *)
malloc(
sizeof(
int) * nFields);
522 psDBF->pachFieldType = (
char *)
malloc(
sizeof(
char) * nFields);
524 for (iField = 0; iField < nFields; iField++)
526 unsigned char *pabyFInfo;
528 pabyFInfo = pabyBuf + iField * 32;
530 if (pabyFInfo[11] ==
'N' || pabyFInfo[11] ==
'F')
532 psDBF->panFieldSize[iField] = pabyFInfo[16];
533 psDBF->panFieldDecimals[iField] = pabyFInfo[17];
537 psDBF->panFieldSize[iField] = pabyFInfo[16];
538 psDBF->panFieldDecimals[iField] = 0;
550 psDBF->pachFieldType[iField] = (char)pabyFInfo[11];
552 psDBF->panFieldOffset[iField] = 1;
554 psDBF->panFieldOffset[iField] =
555 psDBF->panFieldOffset[iField - 1] + psDBF->panFieldSize[iField - 1];
static void * SfRealloc(void *pMem, int nNewSize)
SAFile(* FOpen)(const char *filename, const char *access)
int(* FClose)(SAFile file)