From: Mapi B. <ma...@us...> - 2009-08-06 21:41:12
|
Update of /cvsroot/easycalc/PPCport/compat In directory 23jxhf1.ch3.sourceforge.com:/tmp/cvs-serv22113 Modified Files: DataManager.cpp DataManager.h PalmOS.h Log Message: More complex DataManager, and some other updates Index: PalmOS.h =================================================================== RCS file: /cvsroot/easycalc/PPCport/compat/PalmOS.h,v retrieving revision 1.3 retrieving revision 1.4 diff -C2 -d -r1.3 -r1.4 *** PalmOS.h 5 Jul 2009 20:52:48 -0000 1.3 --- PalmOS.h 6 Aug 2009 21:41:01 -0000 1.4 *************** *** 42,53 **** #define StrPrintF _stprintf #define StrIToA(s,i) _itot(i,s,10) ! #define MemPtrNew malloc ! #define MemPtrFree free ! typedef void *MemHandle; typedef void *WinHandle; typedef void *ListPtr; - #define MemHandleLock(a) ((MemHandle) a) - #define MemHandleUnlock(a) #define noListSelection -1 --- 42,52 ---- #define StrPrintF _stprintf #define StrIToA(s,i) _itot(i,s,10) + // No _tcsicoll / _wcsicoll /_stricoll in MSVC for Pocket PC unfortunately, + // so for now, using _tcsicmp. + #define StrCaselessCompare _tcsicmp ! #include "MemoryManager.h" typedef void *WinHandle; typedef void *ListPtr; #define noListSelection -1 Index: DataManager.h =================================================================== RCS file: /cvsroot/easycalc/PPCport/compat/DataManager.h,v retrieving revision 1.2 retrieving revision 1.3 diff -C2 -d -r1.2 -r1.3 *** DataManager.h 5 Jul 2009 20:52:48 -0000 1.2 --- DataManager.h 6 Aug 2009 21:41:01 -0000 1.3 *************** *** 5,8 **** --- 5,9 ---- #include "PalmOS.h" + #include <stdio.h> #define dmModeReadWrite 1 *************** *** 14,25 **** UInt32 magic; UInt32 size; ! char *ptr; DataRecord *next; DataRecord(void); ! DataRecord(UINT32 s, void *p, DataRecord *n); ~DataRecord(void); }; class DataManager { public: --- 15,41 ---- UInt32 magic; UInt32 size; ! int num; ! MemHandle h; DataRecord *next; DataRecord(void); ! DataRecord(UINT32 s, MemHandle p, DataRecord *n); ~DataRecord(void); + int serialize(FILE *f); + int deSerialize(FILE *f); }; + typedef struct { + UInt8 attributes; + UInt8 uniqueID[3]; + } SortRecordInfoType; + + typedef SortRecordInfoType *SortRecordInfoPtr; + + typedef Int16 DmComparF (void *rec1, void *rec2, Int16 other, + SortRecordInfoPtr rec1SortInfo, + SortRecordInfoPtr rec2SortInfo, + MemHandle appInfoH); + class DataManager { public: *************** *** 31,51 **** UInt16 numRecords; DataRecord *head; DataManager(void); ~DataManager(void); }; - typedef struct { - UInt8 attributes; - UInt8 uniqueID[3]; - } SortRecordInfoType; - - typedef SortRecordInfoType *SortRecordInfoPtr; - - typedef DataManager *DmOpenRef; typedef void *LocalID; ! void registerDmDatabase (UINT16 cardNo, const TCHAR *nameP, LocalID dbId); LocalID DmFindDatabase (UINT16 cardNo, const TCHAR *nameP); --- 47,63 ---- UInt16 numRecords; DataRecord *head; + DataRecord **sortArray; // To support binary searches in DmFindSortPosition + TCHAR *name; DataManager(void); ~DataManager(void); + int serialize(FILE *f); + int deSerialize(FILE *f); }; typedef DataManager *DmOpenRef; typedef void *LocalID; ! void registerDmDatabase (UINT16 cardNo, const TCHAR *nameP, DataManager *dbId); LocalID DmFindDatabase (UINT16 cardNo, const TCHAR *nameP); *************** *** 66,72 **** --- 78,88 ---- UInt16 DmNumRecords (DmOpenRef dbP); MemHandle DmNewRecord (DmOpenRef dbP, UInt16 *atP, UInt32 size); + MemHandle DmGetRecord (DmOpenRef dbP, UInt16 index); Err DmWrite (void *recordP, UInt32 offset, const void *srcP, UInt32 bytes); Err DmRemoveRecord (DmOpenRef dbP, UInt16 index); MemHandle DmQueryRecord (DmOpenRef dbP, UInt16 index); + UInt16 DmFindSortPosition (DmOpenRef dbP, void *newRecord, SortRecordInfoPtr newRecordInfo, + DmComparF *compar, Int16 other); + //Err DmReleaseRecord (DmOpenRef dbP, UInt16 index, Boolean dirty); Index: DataManager.cpp =================================================================== RCS file: /cvsroot/easycalc/PPCport/compat/DataManager.cpp,v retrieving revision 1.1 retrieving revision 1.2 diff -C2 -d -r1.1 -r1.2 *** DataManager.cpp 22 Jun 2009 21:57:16 -0000 1.1 --- DataManager.cpp 6 Aug 2009 21:41:00 -0000 1.2 *************** *** 12,70 **** numRecords = 0; head = NULL; } DataManager::~DataManager(void) { } ! static DataManager *stateMgrHistDB; // This one comes from EasyCalc.cpp ! void registerDmDatabase (UINT16 cardNo, const TCHAR *nameP, LocalID dbId) { ! stateMgrHistDB = (DataManager *) dbId; } LocalID DmFindDatabase (UINT16 cardNo, const TCHAR *nameP) { ! return ((LocalID) stateMgrHistDB); } ! int DmDatabaseInfo ( ! UINT16 cardNo, ! LocalID dbID, ! TCHAR *nameP, ! UINT16 *attributesP, ! UINT16 *versionP, ! UINT32 *crDateP, ! UINT32 *modDateP, ! UINT32 *bckUpDateP, ! UINT32 *modNumP, ! LocalID *appInfoIDP, ! LocalID *sortInfoIDP, ! UINT32 *typeP, ! UINT32 *creatorP) { ! if (dbID == (LocalID) stateMgrHistDB) { ! *attributesP = stateMgrHistDB->attr; ! *versionP = (UINT16) (stateMgrHistDB->version); ! *typeP = stateMgrHistDB->type; ! *creatorP = stateMgrHistDB->creator; } ! return (0); } ! int DmSetDatabaseInfo ( ! UINT16 cardNo, ! LocalID dbID, ! const TCHAR *nameP, ! UINT16 *attributesP, ! UINT16 *versionP, ! UINT32 *crDateP, ! UINT32 *modDateP, ! UINT32 *bckUpDateP, ! UINT32 *modNumP, ! LocalID appInfoIDP, ! LocalID sortInfoIDP, ! UINT32 *typeP, ! UINT32 *creatorP) { if (dbID == (LocalID) stateMgrHistDB) { stateMgrHistDB->attr = *attributesP; stateMgrHistDB->version = *versionP; } return (0); --- 12,231 ---- numRecords = 0; head = NULL; + sortArray = NULL; + name = NULL; } DataManager::~DataManager(void) { + if (head != NULL) { + // Free all records in the DB + DataRecord *temp; + do { + temp = head->next; + MemHandleFree(head->h); + delete head; + head = temp; + } while (temp != NULL); + } + if (sortArray != NULL) free(sortArray); + if (name != NULL) free(name); } ! /*********************************************************************** ! * Store the DataManager object to a file, in binary mode. ! ***********************************************************************/ ! int DataManager::serialize(FILE *f) { ! // Save previous file mode for restoring later. ! int prev_mode = _setmode(f, _O_BINARY); ! // Save object itself ! if (fwrite(&in_state, sizeof(in_state), 1, f) != 1) ! return (-1); ! if (fwrite(&attr, sizeof(attr), 1, f) != 1) ! return (-1); ! if (fwrite(&type, sizeof(type), 1, f) != 1) ! return (-1); ! if (fwrite(&creator, sizeof(creator), 1, f) != 1) ! return (-1); ! if (fwrite(&version, sizeof(version), 1, f) != 1) ! return (-1); ! if (fwrite(&numRecords, sizeof(numRecords), 1, f) != 1) ! return (-1); ! if (fwrite(&head, sizeof(head), 1, f) != 1) ! return (-1); ! if (fwrite(&sortArray, sizeof(sortArray), 1, f) != 1) ! return (-1); ! if (fwrite(&name, sizeof(name), 1, f) != 1) ! return (-1); ! ! // Save elements pointed at by the object. ! // First, the name ! if (name != NULL) { ! size_t siz = _msize(name); ! if (fwrite(&siz, sizeof(siz), 1, f) != 1) ! return (-1); ! if (fwrite(name, siz, 1, f) != 1) ! return (-1); ! } ! // Then, the records, numbering them ! int num = 0; ! if (head != NULL) { ! DataRecord *temp = head; ! while (temp != NULL) { ! temp->num = num++; ! if (temp->serialize(f) != 0) ! return (-1); ! temp = temp->next; ! } ! } ! // And last, the sort array. Save record numbers instead of addresses, ! // for rebuild at read. ! if (sortArray != NULL) { ! // size_t siz = _msize(sortArray); ! // if (fwrite(&siz, sizeof(siz), 1, f) != 1) ! // return (-1); ! // if (fwrite(sortArray, siz, 1, f) != 1) ! // return (-1); ! size_t siz = num * sizeof(int); ! if (fwrite(&siz, sizeof(siz), 1, f) != 1) ! for (int i=0 ; i<num ; i++) { ! if (fwrite(&(sortArray[i]->num), sizeof(int), 1, f) != 1) ! return (-1); ! } ! } ! ! // Restore previous file mode. ! _setmode(f, prev_mode); ! ! return (0); ! } ! ! /*********************************************************************** ! * Retrieve the DataManager object from a file, in binary mode. ! ***********************************************************************/ ! int DataManager::deSerialize(FILE *f) { ! // Save previous file mode for restoring later. ! int prev_mode = _setmode(f, _O_BINARY); ! ! // Load object itself ! if (fread(&in_state, sizeof(in_state), 1, f) != 1) ! return (-1); ! if (fread(&attr, sizeof(attr), 1, f) != 1) ! return (-1); ! if (fread(&type, sizeof(type), 1, f) != 1) ! return (-1); ! if (fread(&creator, sizeof(creator), 1, f) != 1) ! return (-1); ! if (fread(&version, sizeof(version), 1, f) != 1) ! return (-1); ! if (fread(&numRecords, sizeof(numRecords), 1, f) != 1) ! return (-1); ! if (fread(&head, sizeof(head), 1, f) != 1) ! return (-1); ! if (fread(&sortArray, sizeof(sortArray), 1, f) != 1) ! return (-1); ! if (fread(&name, sizeof(name), 1, f) != 1) ! return (-1); ! ! // Load elements pointed at by the object. ! // First, the name ! if (name != NULL) { ! size_t siz; ! if (fread(&siz, sizeof(siz), 1, f) != 1) ! return (-1); ! name = (TCHAR *) malloc(siz); ! if (fread(name, siz, 1, f) != 1) ! return (-1); ! } ! // Then, numbered records, storing their allocated address ! DataRecord **listArray = (DataRecord **) malloc (numRecords * sizeof(DataRecord *)); ! if (head != NULL) { ! DataRecord *temp1 = NULL, *temp2; ! for (int i=0 ; i<numRecords ; i++) { ! temp2 = new DataRecord; ! if (temp2->deSerialize(f) != 0) ! return (-1); ! // Remember its address by index ! listArray[temp2->num] = temp2; ! if (temp1 == NULL) { ! head = temp1 = temp2; ! } else { ! temp1->next = temp2; ! temp1 = temp2; ! } ! } ! } ! // And last, the sort array. Record numbers have been saved instead of addresses. ! if (sortArray != NULL) { ! size_t siz; ! if (fread(&siz, sizeof(siz), 1, f) != 1) ! return (-1); ! // sortArray = (DataRecord **) malloc(siz); ! // if (fread(sortArray, siz, 1, f) != 1) ! // return (-1); ! sortArray = (DataRecord **) malloc(numRecords * sizeof(DataRecord **)); ! int index; ! for (int i=0 ; i<numRecords ; i++) { ! if (fwrite(&index, sizeof(int), 1, f) != 1) ! return (-1); ! // We got the record number, now convert it to its allocated ! // address in memory. ! sortArray[i] = listArray[index]; ! } ! } ! free (listArray); ! ! // Restore the previous file mode. ! _setmode(f, prev_mode); ! ! return (0); ! } ! ! static DataManager *stateMgrDB = NULL; // This one comes from CalcDB.cpp ! static DataManager *stateMgrHistDB = NULL; // This one comes from EasyCalc.cpp ! ! void registerDmDatabase (UINT16 cardNo, const TCHAR *nameP, DataManager *dbId) { ! if (wcscmp (nameP, HISTORYDBNAME) == 0) { ! stateMgrHistDB = (DataManager *) dbId; ! } else if (wcscmp (nameP, DBNAME) == 0) { ! stateMgrDB = (DataManager *) dbId; ! } } LocalID DmFindDatabase (UINT16 cardNo, const TCHAR *nameP) { ! LocalID dbId = NULL; ! if (wcscmp (nameP, HISTORYDBNAME) == 0) { ! dbId = (LocalID) stateMgrHistDB; ! } else if (wcscmp (nameP, DBNAME) == 0) { ! dbId = (LocalID) stateMgrDB; ! } ! return (dbId); } ! int DmDatabaseInfo (UINT16 cardNo, LocalID dbID, TCHAR *nameP, UINT16 *attributesP, ! UINT16 *versionP, UINT32 *crDateP, UINT32 *modDateP, UINT32 *bckUpDateP, ! UINT32 *modNumP, LocalID *appInfoIDP, LocalID *sortInfoIDP, ! UINT32 *typeP, UINT32 *creatorP) { ! int rc = -1; ! DataManager *db = (DataManager *) dbID; ! if ((db == stateMgrHistDB) || (db == stateMgrDB)) { ! *attributesP = db->attr; ! *versionP = (UINT16) (db->version); ! *typeP = db->type; ! *creatorP = db->creator; ! rc = 0; } ! return (rc); } ! int DmSetDatabaseInfo (UINT16 cardNo, LocalID dbID, const TCHAR *nameP, UINT16 *attributesP, ! UINT16 *versionP, UINT32 *crDateP, UINT32 *modDateP, UINT32 *bckUpDateP, ! UINT32 *modNumP, LocalID appInfoIDP, LocalID sortInfoIDP, ! UINT32 *typeP, UINT32 *creatorP) { if (dbID == (LocalID) stateMgrHistDB) { stateMgrHistDB->attr = *attributesP; stateMgrHistDB->version = *versionP; + } else if (dbID == (LocalID) stateMgrDB) { + stateMgrDB->attr = *attributesP; + stateMgrDB->version = *versionP; } return (0); *************** *** 74,77 **** --- 235,240 ---- if (dbID == (LocalID) stateMgrHistDB) { return (stateMgrHistDB); + } else if (dbID == (LocalID) stateMgrDB) { + return (stateMgrDB); } return (NULL); *************** *** 82,96 **** } ! int DmCreateDatabase ( ! UINT16 cardNo, ! const TCHAR *nameP, ! UINT32 creator, ! UINT32 type, ! bool resDB) { if (wcscmp (nameP, HISTORYDBNAME) == 0) { stateMgrHistDB->creator = creator; stateMgrHistDB->type = type; } ! return (0); } --- 245,271 ---- } ! int DmCreateDatabase (UINT16 cardNo, const TCHAR *nameP, UINT32 creator, ! UINT32 type, bool resDB) { ! int rc = 0; if (wcscmp (nameP, HISTORYDBNAME) == 0) { + if (stateMgrHistDB == NULL) + stateMgrHistDB = new DataManager; stateMgrHistDB->creator = creator; stateMgrHistDB->type = type; + int l = _tcslen(nameP); + stateMgrDB->name = (TCHAR *) malloc(2*l+1); + _tcscpy (stateMgrDB->name, nameP); + rc = 0; + } else if (wcscmp (nameP, DBNAME) == 0) { + if (stateMgrHistDB == NULL) + stateMgrDB = new DataManager; + stateMgrDB->creator = creator; + stateMgrDB->type = type; + int l = _tcslen(nameP); + stateMgrDB->name = (TCHAR *) malloc(2*l+1); + _tcscpy (stateMgrDB->name, nameP); + rc = 0; } ! return (rc); } *************** *** 100,103 **** --- 275,284 ---- int DmDeleteDatabase (UINT16 cardNo, LocalID dbID) { + DataManager *db = (DataManager *) dbID; + if ((db == stateMgrHistDB) || (db == stateMgrDB)) { + if (db == stateMgrHistDB) stateMgrHistDB = NULL; + else stateMgrDB = NULL; + delete db; + } return (0); } *************** *** 108,145 **** MemHandle DmNewRecord (DmOpenRef dbP, UInt16 *atP, UInt32 size) { ! if (dbP == stateMgrHistDB) { ! char *p = (char *) malloc ((size+8) & 0xFFFFFFFC); // Add 4 bytes, round up to next 4 bytes limit ! if (p == NULL) return (NULL); ! DataRecord *prec = NULL; ! DataRecord *temp = stateMgrHistDB->head; ! if (*atP > stateMgrHistDB->numRecords) *atP = stateMgrHistDB->numRecords; ! for (int i=0 ; (i<*atP) && (temp != NULL) ; i++) temp = (prec = temp)->next; ! stateMgrHistDB->numRecords++; ! if (prec == NULL) { // Insert at head ! temp = stateMgrHistDB->head = new DataRecord(size, p, stateMgrHistDB->head); ! } else { ! temp = prec->next = new DataRecord(size, p, temp); } - // Put the father record address at beginning of the allocated space - *((UInt32 *) p) = (UInt32) temp; - return (p+4); } ! return (NULL); } Err DmRemoveRecord (DmOpenRef dbP, UInt16 index) { ! if (dbP == stateMgrHistDB) { DataRecord *prec = NULL; ! DataRecord *temp = stateMgrHistDB->head; ! if (index >= stateMgrHistDB->numRecords) return (-1); ! for (int i=0 ; (i<index) && (temp != NULL) ; i++) temp = (prec = temp)->next; ! stateMgrHistDB->numRecords--; if (prec == NULL) { // Delete at head ! stateMgrHistDB->head = stateMgrHistDB->head->next; } else { prec->next = temp->next; } ! free (temp->ptr); delete temp; return (0); --- 289,397 ---- MemHandle DmNewRecord (DmOpenRef dbP, UInt16 *atP, UInt32 size) { ! MemHandle p = NULL; ! if ((dbP == stateMgrHistDB) || (dbP == stateMgrDB)) { ! // Add 4 bytes, round up to next 4 bytes limit ! // char *p = (char *) malloc ((size+8) & 0xFFFFFFFC); ! if ((p = MemHandleNew((size+8) & 0xFFFFFFFC)) != NULL) { ! DataRecord *prec = NULL; ! DataRecord *temp = dbP->head; ! if (*atP > dbP->numRecords) ! *atP = dbP->numRecords; ! dbP->numRecords++; ! // Locate the records around the one to insert ! if (dbP->sortArray == NULL) { // No sort array to maintain, and no direct access ! for (int i=0 ; (i<*atP)&&(temp!=NULL) ; i++) ! temp = (prec = temp)->next; ! } else { // Maintain the sort array in sync ! DataRecord **destArray = (DataRecord **) malloc(dbP->numRecords * sizeof(DataRecord **)); ! if (*atP > 0) { ! memcpy (destArray, ! dbP->sortArray, ! *atP * sizeof(DataRecord **)); ! prec = dbP->sortArray[*atP-1]; ! } ! if (1 < dbP->numRecords - *atP) { ! memcpy (destArray+*atP+1, ! dbP->sortArray+*atP, ! (dbP->numRecords-*atP-1) * sizeof(DataRecord **)); ! temp = dbP->sortArray[*atP]; ! } else ! temp = NULL; // Insert at end. ! // Switch sortArray to the new allocated array ! free(dbP->sortArray); ! dbP->sortArray = destArray; ! } ! if (prec == NULL) { // Insert at head ! temp = dbP->head = new DataRecord(size, p, dbP->head); ! } else { ! temp = prec->next = new DataRecord(size, p, temp); ! } ! // Put the metadata DataRecord address in the allocated memory ! *((UInt32 *) p->memPtr) = (UInt32) temp; ! // And update the new sortArray entry with the new DataRecord address, if needed ! if (dbP->sortArray != NULL) { ! dbP->sortArray[*atP] = temp; ! } ! } ! } ! return (p); ! } ! MemHandle DmGetRecord (DmOpenRef dbP, UInt16 index) { ! MemHandle p = NULL; ! if ((dbP == stateMgrHistDB) || (dbP == stateMgrDB)) { ! DataRecord *temp = dbP->head; ! // Find the record ! if (dbP->sortArray == NULL) { // No sort array, no direct access ! if (index < dbP->numRecords) { ! for (int i=0 ; i<index ; i++) ! temp = temp->next; ! p = temp->h; ! } ! } else { // Direct access ! p = dbP->sortArray[(int)index]->h; } } ! return (p); } Err DmRemoveRecord (DmOpenRef dbP, UInt16 index) { ! if ((dbP == stateMgrHistDB) || (dbP == stateMgrDB)) { DataRecord *prec = NULL; ! DataRecord *temp = dbP->head; ! if (index >= dbP->numRecords) ! return (-1); ! dbP->numRecords--; ! // Locate the record to delete ! if (dbP->sortArray == NULL) { // No sort array to maintain, and no direct access ! for (int i=0 ; (i<index)&&(temp!=NULL) ; i++) ! temp = (prec = temp)->next; ! } else { // Maintain the sort array in sync ! DataRecord **destArray = NULL; ! if (dbP->numRecords > 0) { // Do not allocate a new array if size is 0 ! destArray = (DataRecord **) malloc(dbP->numRecords * sizeof(DataRecord **)); ! if (index > 0) { ! memcpy (destArray, ! dbP->sortArray, ! index * sizeof(DataRecord **)); ! prec = dbP->sortArray[index-1]; ! } ! if (index < dbP->numRecords) { ! memcpy (destArray+index, ! dbP->sortArray+index+1, ! (dbP->numRecords-index) * sizeof(DataRecord **)); ! } ! temp = dbP->sortArray[index]; ! } ! // Switch sortArray to the new allocated array ! free(dbP->sortArray); ! dbP->sortArray = destArray; ! } if (prec == NULL) { // Delete at head ! dbP->head = dbP->head->next; } else { prec->next = temp->next; } ! MemHandleFree(temp->h); delete temp; return (0); *************** *** 148,156 **** } ! Err DmWrite ( ! void *recordP, ! UInt32 offset, ! const void *srcP, ! UInt32 bytes) { char *p = (char *) recordP; --- 400,404 ---- } ! Err DmWrite (void *recordP, UInt32 offset, const void *srcP, UInt32 bytes) { char *p = (char *) recordP; *************** *** 164,176 **** MemHandle DmQueryRecord (DmOpenRef dbP, UInt16 index) { ! if (dbP == stateMgrHistDB) { ! DataRecord *temp = stateMgrHistDB->head; ! if (index >= stateMgrHistDB->numRecords) return (NULL); for (int i=0 ; (i<index) && (temp != NULL) ; i++) temp = temp->next; ! return (temp->ptr+4); } return (NULL); } //Err DmReleaseRecord (DmOpenRef dbP, UInt16 index, Boolean dirty) { // return (0); --- 412,573 ---- MemHandle DmQueryRecord (DmOpenRef dbP, UInt16 index) { ! if ((dbP == stateMgrHistDB) || (dbP == stateMgrDB)) { ! DataRecord *temp = dbP->head; ! if (index >= dbP->numRecords) return (NULL); for (int i=0 ; (i<index) && (temp != NULL) ; i++) temp = temp->next; ! return (temp->h); } return (NULL); } + /*********************************************************** + * Binary search on a non empty sorted array. * + ***********************************************************/ + int binSearch (DataRecord **sortArray, int numRecords, + void *newRecord, SortRecordInfoPtr newRecordInfo, + DmComparF *compar, Int16 other) { + int i, imin, imax; + imax = numRecords - 1; + imin = 0; + int c; + + // First, initiate conditions on boundaries of the recurring algorithm + if (compar(newRecord, + sortArray[imax]->h->memPtr, + other, + NULL, // newRecordInfo, not used, so not implemented + NULL, // sortArray[imax]->, not used, so not implemented + NULL // Not used, so not implemented + ) >= 0) { + // After last one + i = numRecords; + } else if ((numRecords == 1) // First == last ! No need to redo the comparison. + || (c = compar(newRecord, + sortArray[0]->h->memPtr, + other, + NULL, // newRecordInfo, not used, so not implemented + NULL, // sortArray[0]->, not used, so not implemented + NULL // Not used, so not implemented + ) + ) < 0) { + // Before first one + i = 0; + } else if ((c == 0) // Matches with first one + || (numRecords == 2)) { // Optimization .. We know it's neither 0 or 1, + // but between them ... means insert at 1. + i = 1; + // If several with the same key, then insert after all of them + while ((i < imax) // We already compared with imax, and if we reach this point, + // we already know that they are not equal. + // And note: when numRecords == 2, imax is 1. + && (compar(newRecord, + sortArray[i]->h->memPtr, + other, + NULL, // newRecordInfo, not used, so not implemented + NULL, // sortArray[i]->, not used, so not implemented + NULL // Not used, so not implemented + ) == 0) + ) { + i++; + } + } else { // Regular condition as of now: somewhere between imin and imax, + // neither of them, and imax - imin > 1. + // This will be the recursive and propagated property. + bool found = false; + while (!found) { + // Get to the middle point of current scope + i = (imax + imin) >> 1; + c = compar(newRecord, + sortArray[i]->h->memPtr, + other, + NULL, // newRecordInfo, not used, so not implemented + NULL, // sortArray[i]->, not used, so not implemented + NULL // Not used, so not implemented + ); + if (c == 0) { + // If several with the same key, then insert after all of them + while ((i < numRecords) + && (compar(newRecord, + sortArray[i]->h->memPtr, + other, + NULL, // newRecordInfo, not used, so not implemented + NULL, // sortArray[i]->, not used, so not implemented + NULL // Not used, so not implemented + ) == 0) + ) { + i++; + } + found = true; + } else if (c < 0) { // Between imin and i, and neither of them. + // We didn't find it yet, but if scope is reduced to 0, + // we have found the place to insert. + if (i - imin <= 1) { + // Insert at i (i.e. it will shift i by 1) + found = true; + } else { + imax = i; + } + } else { // Between i and imax, and neither of them. + // We didn't find it yet, but if scope is reduced to 0, + // we have found the place to insert. + if (imax - i <= 1) { + // Insert at imax (i.e., just after i) + i = imax; + found = true; + } else { + imin = i; + } + } + } + } + + return (i); + } + + UInt16 DmFindSortPosition (DmOpenRef dbP, void *newRecord, SortRecordInfoPtr newRecordInfo, + DmComparF *compar, Int16 other) { + int i = -1; + if ((dbP == stateMgrHistDB) || (dbP == stateMgrDB)) { + // If DB is empty .. do nothing ! + if (dbP->numRecords == 0) + i = 0; + else { // There something in the DB to compare to + // If not yet sorted, then sort the DB + if (dbP->sortArray == NULL) { + // Allocate the sort array + dbP->sortArray = (DataRecord **) malloc(dbP->numRecords * sizeof(DataRecord **)); + // Then fill it by adding elements to it in a sorted manner. + // Add the first element from the list. + dbP->sortArray[0] = dbP->head; + // Add next elements of the linked list + int num = 1; + DataRecord *temp = dbP->head->next; + while (temp != NULL) { + // Find position + i = binSearch(dbP->sortArray, num, + newRecord, NULL, // newRecord Info is not used + compar, other); + // Insert in the array + if (i+1 < num) { + memcpy (dbP->sortArray+i+1, + dbP->sortArray+i, + (num-i-1) * sizeof(DataRecord **)); + } + dbP->sortArray[i] = temp; + + // Next element + num++; + temp = temp->next; + } + } + // Find the record by a binary search. + i = binSearch(dbP->sortArray, dbP->numRecords, + newRecord, newRecordInfo, + compar, other); + } + } + return (i); + } + //Err DmReleaseRecord (DmOpenRef dbP, UInt16 index, Boolean dirty) { // return (0); *************** *** 180,193 **** magic = RECORD_MAGIC; size = 0; ! ptr = NULL; next = NULL; } ! DataRecord::DataRecord(UINT32 s, void *p, DataRecord *n) { ! size = s; ! ptr = (char *) p; ! next = n; } DataRecord::~DataRecord(void) { ! } \ No newline at end of file --- 577,622 ---- magic = RECORD_MAGIC; size = 0; ! h = NULL; next = NULL; } ! DataRecord::DataRecord(UINT32 s, MemHandle p, DataRecord *n) { ! size = s; ! h = p; ! next = n; } DataRecord::~DataRecord(void) { ! } ! ! /*********************************************************************** ! * Store the DataRecord object to a file, in binary mode. ! ***********************************************************************/ ! int DataRecord::serialize(FILE *f) { ! if (fwrite(&magic, sizeof(magic), 1, f) != 1) ! return (-1); ! if (fwrite(&size, sizeof(size), 1, f) != 1) ! return (-1); ! if (fwrite(&num, sizeof(num), 1, f) != 1) ! return (-1); ! if (h->serialize(f) != 0) ! return (-1); ! ! return (0); ! } ! ! /*********************************************************************** ! * Retrieve the DataRecord object from a file, in binary mode. ! ***********************************************************************/ ! int DataRecord::deSerialize(FILE *f) { ! if (fread(&magic, sizeof(magic), 1, f) != 1) ! return (-1); ! if (fread(&size, sizeof(size), 1, f) != 1) ! return (-1); ! if (fread(&num, sizeof(num), 1, f) != 1) ! return (-1); ! if (h->deSerialize(f) != 0) ! return (-1); ! ! return (0); ! } |