Exemple #1
0
int main(void)
{
    Node *head = 0;
    head = addNodeAtHead(head, 23);
    head = addNodeAtHead(head, 43);
    head = addNodeAtHead(head, 73);
    head = addNodeAtHead(head, 13);
    head = addNodeAtHead(head, 33);
    dumpList("Completed", head);

    head = removeNode(head, 33);
    dumpList("Remove 33", head);
    head = removeNode(head, 23);
    dumpList("Remove 23", head);
    head = removeNode(head, 13);
    dumpList("Remove 13", head);
    head = removeNode(head, 34);
    dumpList("Remove 34", head);
    head = removeNode(head, 43);
    dumpList("Remove 43", head);
    head = removeNode(head, 73);
    dumpList("Remove 73", head);
    head = removeNode(head, 37);
    dumpList("Remove 37", head);

    return 0;
}
Exemple #2
0
//
// CPreferenceFile
//
// A File comprised of CPreference Items
//
// This is a textfile implementation in the format:
//
// [Section1Identifier]
// PreferenceItem       PreferenceValue
//
// [Section2Identifier]
// PreferenceItem       PreferenceValue
//
CPreferenceFile::CPreferenceFile(const char *inFileName)
{
   fFileName = strdup(inFileName);
   m_list = NULL;
   fModified = FALSE;		
   Load();
#ifdef DEBUG
   qDebug("Loaded Preferences:");
   dumpList(m_list);
#endif
} // end Constructor
Exemple #3
0
/**
 * Deletes the first occurrence of name that matches the movie's title from the
 * given list
 * @param movieNode The list of movies to find and remove the node from
 * @param name The name of the movie to remove
 */
void deleteMovie(MovieNodeType **list, char *title) {

	fprintf(outputFile, "* Entering DeleteMovie *\n");
	dumpList(*list);

	MovieNodeType *current = *list;

	while (current != NULL) {
		int compare = strcmp(current->data->title, title);
		if (compare == 0) {

			// if removing from the beginning
			if (current->prev == NULL) {
				*list = current->next;
			} else {
				current->prev->next = current->next;
			}

			// if removing from the end
			if (current->next != NULL) {
				current->next->prev = current->prev;
			}
			current->next = NULL;
			current->prev = NULL;

			freeNodeAndData(current);

			dumpList(*list);
			fprintf(outputFile, "* Leaving DeleteMovie *\n");
			return;

		} else {
			current = current->next;
		}
	}

	dumpList(*list);
	fprintf(outputFile, "* Leaving DeleteMovie *\n");
	return;

}
int main()
{
    ListNode *node = new ListNode(2);
    ListNode *l1 = node;
    node->next = new ListNode(4);
    node = node->next;
    node->next = new ListNode(3);

    node = new ListNode(5);
    ListNode *l2 = node;
    node->next = new ListNode(6);
    node = node->next;
    node->next = new ListNode(4);

    Solution_1 slu1;
    dumpList(slu1.addTwoNumbers(l1, l2));

    Solution_2 slu2;
    dumpList(slu2.addTwoNumbers(l1, l2));

    return 0;
}
Exemple #5
0
GCHeap::~GCHeap()
{
	printf( "waiting for others to complete\n" );
	
	printf( "Total number of allocations: %d\n", mNumTotalAllocations );
	printf( "Max size of heap: %d\n", mMaxSize );
	
	if ( !mObjects.empty() )
	{
		printf( "LEAKED, %d objects, totaling %d bytes\n", mNumCurrentAllocations, mCurrentSize );
		printf( "The following objects have been leaked\n" );
		dumpList();
	}
}
Exemple #6
0
int main(int argc, const char * argv[]) {
	LinkN *null = NULL;
	LinkN **head = &null;
	const size_t COUNT = 37;
	size_t *data = SafeMalloc(COUNT * sizeof(size_t)), i;
	LinkN *nodes = SafeMalloc(COUNT * sizeof(LinkN));
	rb_red_blk_tree tree;
	RBTreeInit(&tree, &pointerDiff, NULL, &RBNodeAlloc);
	
	for(i = 0; i < COUNT; i++){
		data[i] = i;
		nodes[i].data = data + i;
		linkFront(head, nodes + i);
	}
	
	dumpList(head);
	mergeSort(head, &csT);
	dumpList(head);
	
	qsort(data, 0, COUNT, &qsCompare);
	dumpArray(data, COUNT);
	
	for(i = 0; i < COUNT; i++){
		RBSetAdd(&tree, data + i);
	}
	
	dumpSet(&tree);
	
	dPrintf(("%p - %p = " PDF " ?= (-1 * " PDF ")\n",(void*)&data[2],(void*)&data[3],(&data[2] - &data[3]),(&data[3] - &data[2])));
	dPrintf(("\t ?= %d ?= (-1 * %d)\n",pointerDiff(&data[2], &data[3]),pointerDiff(&data[3], &data[2])));
	
	
	free(nodes);
	free(data);
	
    return 0;
}
//!-----------------------------------
void removeList(header_t *Head)
{
    assert_ok(Head != NULL);
    listElem_t * work = Head->theFirst;

    for (int i = 2; i < Head->ListLen; i++)
    {
        assert(2 <= i && i <= Head->ListLen);
        dtor(work->prev, Head);
        work = work->next;
    }
    work = NULL;

    free(Head);
    dumpList(Head);
}
Exemple #8
0
/**
 * Prints in terminal a human readable representation of the hash-list.
 *
 * @param hl A hash-list structure
 */
void hl_print(HashList *hl)
{
  int i = 0, n = hl->size;
  List *l;

  printf("[\n");
  for ( ; i < n ; i++ )
  {
    l = &(hl->buckets[i]);
    
    printf("  [%3d] List[%d] {\n", i, l->numItems);
    dumpList(l);
    printf("  }\n");
  }
  printf("]\n");
}
//!-----------------------------------
void insert_in(dataType value, int position, int orientation, header_t *Head)
{
    assert_ok(List_ok(Head) == NULL);
    assert_ok(position <= Head->ListLen);

    listElem_t *work = Head->theFirst;
    for (int i = 1; i < position; i++)
    {
        assert(1 <= i && i < position);
        work = work->next;
    }

    listElem_t *target = ctor();
    target->data = value;

    if (orientation  == LEFT)
    {
        listElem_t *previous = work->prev;
        //printf("previous [0x%p]\n", previous);
        if (previous != NULL)
            previous->next = target;
        if (previous == NULL)
            Head->theFirst = target;
        target->prev = previous;

        target->next = work;
        work->prev = target;
        Head->ListLen += 1;
    }

    if (orientation == RIGHT)
    {
        listElem_t * theNext = work->next;
        work->next = target;
        target->prev = work;

        target->next = theNext;
        if (theNext != NULL)
            theNext->prev = target;
        if (theNext == NULL)
            Head->theLast = target;
        Head->ListLen += 1;
    }

    dumpList(Head);
    assert_ok(List_ok(Head) == NULL);
}
Exemple #10
0
void CppContainer::dump(std::ostream & os, int level) const
{
	int newLevel = level + 1;

	dumpList(this->namespaceList, os, newLevel);
	dumpList(this->classList, os, newLevel);
	dumpList(this->fieldList, os, newLevel);
	dumpList(this->methodList, os, newLevel);
	dumpList(this->enumList, os, newLevel);
	dumpList(this->operatorList, os, newLevel);
}
int main(int argc, const char* argv[])
{
    mamaCaptureConfig mCapture = NULL;
    mamaCaptureList mCaptureList     = NULL;
    mamaCaptureConfig_create (&mCapture);

    if (mCapture == NULL)
    {
        mama_log (MAMA_LOG_LEVEL_NORMAL,
                  "Allocation of memory for capture failed!!!!");
        exit (1);
    }

    gCapture  = &mCapture;
    parseCommandLine (mCapture , &mCaptureList, argc, argv);

    /*Set up a signal handler so that we don't
      just stop without cleaning up*/
    gCaptureList = &mCaptureList;
    initializeMama (mCapture);

    mamaCaptureList_parseCommandInput (mCapture,
                                       mCaptureList, gSource);
    mamaCapture_openFile (&mCapture->myCapture,
                       mCapture->myCaptureFilename);


    buildDataDictionary(mCapture);
    dumpDataDictionary (mCapture);

    if (mCapture->myDumpList)
    {
        dumpList (mCaptureList);
    }
    subscribeToSymbols (mCapture,mCaptureList);

    mama_logStdout (MAMA_LOG_LEVEL_NORMAL, "Type CTRL-C to exit.\n\n");

    mama_start (mCapture->myBridge);

    mamaCapture_closeFile(mCapture->myCapture);
    msshutdown (mCapture,mCaptureList);

    return 0;
}
// . return false if blocked, otherwise true
// . sets g_errno on error
bool RdbMerge::resumeMerge ( ) {
	// return true if not suspended
	if ( ! m_isSuspended ) return true;
	// turn off the suspension so getNextList() will work
	m_isSuspended = false;
	// the usual loop
 loop:
	// . this returns false if blocked, true otherwise
	// . sets g_errno on error
	// . we return true if it blocked
	if ( ! getNextList ( ) ) return false;
	// if g_errno is out of memory then msg3 wasn't able to get the lists
	// so we should sleep and retry...
	// or if no thread slots were available...
	if ( g_errno == ENOMEM || g_errno == ENOTHREADSLOTS ) { 
		doSleep(); return false; }
	// if list is empty or we had an error then we're done
	if ( g_errno || m_doneMerging ) { doneMerging(); return true; }
	// . otherwise dump the list we read to our target file
	// . this returns false if blocked, true otherwise
	if ( ! dumpList ( ) ) return false;
	// repeat ad nauseam
	goto loop;
}
Exemple #13
0
void paintCode(pPdf417param p) {
    pdf417class pp;
    arrayList list;
    int maxErr, fixedColumn, lenErr, tot, skipRowColAdjust, pad;
    pp.param = p;
    p->error = 0;
    if (p->options & PDF417_USE_RAW_CODEWORDS) {
        if (p->lenCodewords > MAX_DATA_CODEWORDS || p->lenCodewords < 1 || p->lenCodewords != p->codewords[0]) {
            p->error = PDF417_ERROR_INVALID_PARAMS;
            return;
        }
    }
    else {
        if (p->lenText < 0)
            p->lenText = strlen(p->text);
        if (p->lenText > ABSOLUTE_MAX_TEXT_SIZE) {
            p->error = PDF417_ERROR_TEXT_TOO_BIG;
            return;
        }
        listInit(&list);
        breakString(&pp, &list);
        dumpList(&pp, &list);
        assemble(&pp, &list);
        listFree(&list);
        if (p->error)
            return;
        p->codewords[0] = p->lenCodewords = pp.cwPtr;
    }
    maxErr = maxPossibleErrorLevel(MAX_DATA_CODEWORDS + 2 - p->lenCodewords);
    if (!(p->options & PDF417_USE_ERROR_LEVEL)) {
        if (p->lenCodewords < 41)
            p->errorLevel = 2;
        else if (p->lenCodewords < 161)
            p->errorLevel = 3;
        else if (p->lenCodewords < 321)
            p->errorLevel = 4;
        else
            p->errorLevel = 5;
    }
    if (p->errorLevel < 0)
        p->errorLevel = 0;
    else if (p->errorLevel > maxErr)
        p->errorLevel = maxErr;
    if (p->codeColumns < 1)
        p->codeColumns = 1;
    else if (p->codeColumns > 30)
        p->codeColumns = 30;
    if (p->codeRows < 3)
        p->codeRows = 3;
    else if (p->codeRows > 90)
        p->codeRows = 90;
    lenErr = 2 << p->errorLevel;
    fixedColumn = !(p->options & PDF417_FIXED_ROWS);
    skipRowColAdjust = 0;
    tot = p->lenCodewords + lenErr;
    if (p->options & PDF417_FIXED_RECTANGLE) {
        tot = p->codeColumns * p->codeRows;
        if (tot > MAX_DATA_CODEWORDS + 2) {
            tot = getMaxSquare(p);
        }
        if (tot < p->lenCodewords + lenErr)
            tot = p->lenCodewords + lenErr;
        else
            skipRowColAdjust = 1;
    }
    else if (!(p->options & (PDF417_FIXED_COLUMNS | PDF417_FIXED_ROWS))) {
        double c, b;
        fixedColumn = 1;
        if (p->aspectRatio < 0.001)
            p->aspectRatio = 0.001f;
        else if (p->aspectRatio > 1000)
            p->aspectRatio = 1000;
        b = 73 * p->aspectRatio - 4;
        c = (-b + sqrt(b * b + 4 * 17 * p->aspectRatio * (p->lenCodewords + lenErr) * p->yHeight)) / (2 * 17 * p->aspectRatio);
        p->codeColumns = (int)(c + 0.5);
        if (p->codeColumns < 1)
            p->codeColumns = 1;
        else if (p->codeColumns > 30)
            p->codeColumns = 30;
    }
    if (!skipRowColAdjust) {
        if (fixedColumn) {
            p->codeRows = (tot - 1) / p->codeColumns + 1;
            if (p->codeRows < 3)
                p->codeRows = 3;
            else if (p->codeRows > 90) {
                p->codeRows = 90;
                p->codeColumns = (tot - 1) / 90 + 1;
            }
        }
        else {
            p->codeColumns = (tot - 1) / p->codeRows + 1;
            if (p->codeColumns > 30) {
                p->codeColumns = 30;
                p->codeRows = (tot - 1) / 30 + 1;
            }
        }
        tot = p->codeRows * p->codeColumns;
    }
    if (tot > MAX_DATA_CODEWORDS + 2) {
        tot = getMaxSquare(p);
    }
    p->errorLevel = maxPossibleErrorLevel(tot - p->lenCodewords);
    lenErr = 2 << p->errorLevel;
    pad = tot - lenErr - p->lenCodewords;
    pp.cwPtr = p->lenCodewords;
    while (pad--)
        p->codewords[pp.cwPtr++] = TEXT_MODE;
    p->codewords[0] = p->lenCodewords = pp.cwPtr;
    calculateErrorCorrection(&pp, pp.param->lenCodewords);
    pp.param->lenCodewords = tot;
    outPaintCode(&pp);
}
//!-----------------------------------
void remove_in(int position, int orientation, header_t *Head)
{
    assert_ok(List_ok(Head) == NULL);
    assert_ok(position <= Head->ListLen);
    assert_ok(orientation == LEFT || orientation == RIGHT);

    listElem_t *work = Head->theFirst;
    for (int i = 1; i < position; i++)
    {
        assert(1 <= i && i < position);
        work = work->next;
    }

    if (Head->ListLen == 1)
    {
        printf("Unable to delete!\n");
        exit(3);
    }

    if (orientation  == LEFT)
    {
        if (work->prev == NULL)
        {
            printf("FAIL! You are trying to delete unexisted element\n");
            return;
        }

        listElem_t *previous = work->prev;

        if (previous == Head->theFirst)
        {
            Head->theFirst = work;
            work->prev = NULL;
            dtor(previous, Head);

            Head->ListLen -= 1;
            dumpList(Head);
            return;
        }

        work->prev = previous->prev;
        previous->prev->next = work;
        dtor(previous, Head);
        Head->ListLen -= 1;
    }

    if (orientation == RIGHT)
    {
        if (work->next == NULL)
        {
            printf("ERROR! You are trying to delete unexisted element!\n");
            exit(1);
        }

        listElem_t * theNext = work->next;

        if (theNext == Head->theLast)
        {
            Head->theLast = work;
            work->next = NULL;
            dtor(theNext, Head);

            Head->ListLen -= 1;
            dumpList(Head);
            return;
        }

        work->next = theNext->next;
        theNext->next->prev = work;
        dtor(theNext, Head);
        Head->ListLen -= 1;
    }
    else
    {
        printf("ERROR! WRONG ORIENTATION!\n");
        exit(2);
    }

    assert_ok(List_ok(Head) == NULL);
    dumpList(Head);
}
bool palListTest()
{
  palList<int> il;
  il.SetAllocator(g_DefaultHeapAllocator);
  dumpList(il);

  il.PushFront(4);
  dumpList(il);
  il.PushFront(5);
  dumpList(il);
  il.PushFront(6);
  dumpList(il);
  il.PushFront(9);
  dumpList(il);
  il.PushFront(13);
  dumpList(il);
  il.PopFront();
  dumpList(il);
  il.PopBack();
  dumpList(il);
  il.Remove(6);
  dumpList(il);

#if 0
  palList<int> il_spliced_head;
  il_spliced_head.SetAllocator(g_DefaultHeapAllocator);
  il_spliced_head.PushFront(9);
  il_spliced_head.PushBack(21);
  palList<int> il_spliced_tail;
  il_spliced_tail.SetAllocator(g_DefaultHeapAllocator);
  il_spliced_tail.PushFront(99);
  il_spliced_tail.PushBack(13);

  printf("head:\n");
  dumpList(il_spliced_head);
  printf("tail:\n");
  dumpList(il_spliced_tail);

  il.SpliceHead(&il_spliced_head);
  dumpList(il);
  il.SpliceTail(&il_spliced_tail);
  dumpList(il);
#endif
#if 0
  palList<int> sublist;

  il.MakeSublist(&sublist, p_21, p_99);

  printf("original:\n");
  dumpList(il);
  printf("sublist:\n");
  dumpList(sublist);
#endif
  return true;
}
Exemple #16
0
void main(void)
{
	int		i,count;
	MyNode	*n1,*middle,*beforeMiddle,*last;

	cout << "Memory at start: " << coreleft() << " bytes\n";

	// Create a linked list of 10 nodes adding at the head of the list.

	for (i = 0; i < 10; i++) {
		n1 = new MyNode(i);
		l.addToHead(n1);
		if (i == 0)
			last = n1;
		if (i == 5)
			beforeMiddle = n1;
		if (i == 4)
			middle = n1;
		}

	cout << "Memory after creating list: " << coreleft() << " bytes\n";

	dumpList(l);

	// Add a new node after the head of the list and after a middle node

	n1 = new MyNode(20);
	l.addAfter(n1,l.peekHead());
	n1 = new MyNode(21);
	l.addAfter(n1,last);
	n1 = new MyNode(22);
	l.addAfter(n1,middle);

	dumpList(l);

	// Remove the middle object from the list using beforeMiddle as the
	// previous node in the list.

	delete l.removeNext(beforeMiddle);
	dumpList(l);

	// Remove all remaining nodes with removeFromHead().

	count = l.numberOfItems();
	for (i = 0; i < count+5; i++)
		delete l.removeFromHead();

	dumpList(l);

	cout << "Memory: " << coreleft() << " bytes\n";

	for (i = 0; i < 10; i++) {
		n1 = new MyNode(i);
		l.addToHead(n1);
		}

	// Display the list using iterators to move through the list.

	SimpleListIterator<MyNode> it1;

	for (it1 = l; it1; it1++)
		cout << it1.node()->id() << " ";
	cout << endl;

	for (it1.restart(); it1;)
		cout << it1++->id() << " ";
	cout << endl;

	l.empty();

	cout << "Memory at end: " << coreleft() << " bytes\n\n";
}
Exemple #17
0
void GFF3Dumper::dumpField(const Aurora::GFF3Struct &strct, const Common::UString &field) {
	Aurora::GFF3Struct::FieldType type = strct.getType(field);

	Common::UString typeName;
	if (((size_t) type) < ARRAYSIZE(kGFF3FieldTypeNames))
		typeName = kGFF3FieldTypeNames[(int)type];
	else
		typeName = "filetype" + Common::composeString((uint64) type);

	Common::UString label = field;

	// Structs already open their own tag
	if (type != Aurora::GFF3Struct::kFieldTypeStruct) {
		_xml->openTag(typeName);
		_xml->addProperty("label", label);
	}

	switch (type) {
		case Aurora::GFF3Struct::kFieldTypeChar:
			_xml->setContents(Common::composeString(strct.getUint(field)));
			break;

		case Aurora::GFF3Struct::kFieldTypeByte:
		case Aurora::GFF3Struct::kFieldTypeUint16:
		case Aurora::GFF3Struct::kFieldTypeUint32:
		case Aurora::GFF3Struct::kFieldTypeUint64:
			_xml->setContents(Common::composeString(strct.getUint(field)));
			break;

		case Aurora::GFF3Struct::kFieldTypeSint16:
		case Aurora::GFF3Struct::kFieldTypeSint32:
		case Aurora::GFF3Struct::kFieldTypeSint64:
			_xml->setContents(Common::composeString(strct.getSint(field)));
			break;

		case Aurora::GFF3Struct::kFieldTypeFloat:
		case Aurora::GFF3Struct::kFieldTypeDouble:
			_xml->setContents(Common::UString::format("%.6f", strct.getDouble(field)));
			break;

		case Aurora::GFF3Struct::kFieldTypeStrRef:
			_xml->setContents(strct.getString(field));
			break;

		case Aurora::GFF3Struct::kFieldTypeExoString:
		case Aurora::GFF3Struct::kFieldTypeResRef:
			try {
				_xml->setContents(strct.getString(field));
			} catch (...) {
				_xml->addProperty("base64", "true");

				Common::SeekableReadStream *data = strct.getData(field);
				_xml->setContents(*data);
				delete data;
			}
			break;

		case Aurora::GFF3Struct::kFieldTypeLocString:
			{
				Aurora::LocString locString;

				strct.getLocString(field, locString);
				_xml->addProperty("strref", Common::composeString(locString.getID()));

				dumpLocString(locString);
			}
			break;

		case Aurora::GFF3Struct::kFieldTypeVoid:
			_xml->setContents(*strct.getData(field));
			break;

		case Aurora::GFF3Struct::kFieldTypeStruct:
			dumpStruct(strct.getStruct(field), label);
			break;

		case Aurora::GFF3Struct::kFieldTypeList:
			dumpList(strct.getList(field));
			break;

		case Aurora::GFF3Struct::kFieldTypeOrientation:
			{
				double a = 0.0, b = 0.0, c = 0.0, d = 0.0;

				strct.getOrientation(field, a, b, c, d);

				_xml->breakLine();

				_xml->openTag("double");
				_xml->setContents(Common::UString::format("%.6f", a));
				_xml->closeTag();
				_xml->breakLine();

				_xml->openTag("double");
				_xml->setContents(Common::UString::format("%.6f", b));
				_xml->closeTag();
				_xml->breakLine();

				_xml->openTag("double");
				_xml->setContents(Common::UString::format("%.6f", c));
				_xml->closeTag();
				_xml->breakLine();

				_xml->openTag("double");
				_xml->setContents(Common::UString::format("%.6f", d));
				_xml->closeTag();
				_xml->breakLine();
			}
			break;

		case Aurora::GFF3Struct::kFieldTypeVector:
			{
				double x = 0.0, y = 0.0, z = 0.0;

				strct.getVector(field, x, y, z);

				_xml->breakLine();

				_xml->openTag("double");
				_xml->setContents(Common::UString::format("%.6f", x));
				_xml->closeTag();
				_xml->breakLine();

				_xml->openTag("double");
				_xml->setContents(Common::UString::format("%.6f", y));
				_xml->closeTag();
				_xml->breakLine();

				_xml->openTag("double");
				_xml->setContents(Common::UString::format("%.6f", z));
				_xml->closeTag();
				_xml->breakLine();
			}
			break;

		default:
			break;
	}

	// Structs already close their own tag
	if (type != Aurora::GFF3Struct::kFieldTypeStruct) {
		_xml->closeTag();
		_xml->breakLine();
	}
}
Exemple #18
0
//
// Save()
//
// Save values from cache to file
//
void
CPreferenceFile::Save()
{
#ifdef DEBUG
   printf("CPreferenceFile::Save() %s\n", fModified?"Modified":"Not Modified");
   dumpList(m_list);
#endif

   if (fModified)
   {
      FILE *in;
      FILE *out;
      char msg[MAXLEN];
      char *p;
      int count = 0;
      bool bQuoted = FALSE;
      bool bSaved = FALSE;
 
      // Open source and destination files
      char *outfilename = NULL;
      const char *infilename = fFileName;

      outfilename = (char *) malloc(strlen(infilename) + 64);
      sprintf(outfilename, "%s%s", fFileName, ".new");
      in = fopen (infilename, "r");
      out = fopen (outfilename, "w+");
      if (in == 0)
      {
         fprintf (stderr, "Couldn't open current config file. '%s' - %s\n",
           infilename, strerror(errno));
      }
      if (out == 0)
      {
         fprintf (stderr, "Couldn't open new config file. '%s' - %s\n",
           outfilename, strerror(errno));
      }
      else
      {
         char *sType = NULL;

         // build a copy of all the args we want to save
         CPreferenceList *pTempList = new QList<CPrefItem>;
         CPrefItem *pref;
         for( pref = m_list->first(); pref != 0; pref=m_list->next() )
         {
            if (pref->Persistent())
              pTempList->append(pref);
         }
#ifdef DEBUGSAVE
printf("CPreferenceFile::Save() Saving list:\n");
dumpList(pTempList);
#endif

         if (in)
         {
           // Parse source file
           while (fgets (msg, sizeof(msg), in) != NULL)
           {
              // terminate on CF or LF 
              p = index (msg, '\n');
              if (p)
                *p = 0;
              p = index (msg, '\r');
              if (p)
                *p = 0;
                                       
              // end of section - dump all items left in list that belong here
              if (sType && !msg[0])
              {
                bool bRemoved;
                do
                {
                  bRemoved = FALSE;
                  // done copying filters that existed in file already
                  // dump whatever is left in list
                  for( pref = pTempList->first(); pref != 0; pref = pTempList->next() )
                  {
                     char *tempStr = strdup(pref->Identifier());
//                     p = index(tempStr, '_');
                     p = rindex(tempStr, '_');
                     if (p)
                       *p++ = 0;
                     if (!strcasecmp(sType, tempStr))
                     {
                        struct timeval tv;
                        if (!gettimeofday(&tv, NULL))
                           fprintf(out, "%s\t%s\t# Added %s", p, pref->Text(), 
                               ctime(&tv.tv_sec));
                        else
                           fprintf(out, "%s\t%s\t# Added\n", p,pref->Text());
#ifdef DEBUGSAVE
  fprintf(stdout, "CPreferenceFile::Save(): '%s\t%s' - added\n", 
         pref->Identifier(), pref->Text());
#endif
                        count++;
                        pTempList->remove(pref);
                        bRemoved = TRUE;
                        break; // repeat search for more to remove
                     } // if this belongs in this section
                  } // end for all prefs in unsaved list
                } while (bRemoved);

                free(sType);
                sType = 0;

              } // end if end of section

              // Check for section name
              if (msg[0] == '[')
              {
                p = index(msg, ']');
                if (p)
                  *p = 0;
                p = index(msg, '\r');
                if (p)
                  *p = 0;
                if (sType)
                  free(sType);
                sType = strdup(msg + 1);
                fprintf(out, "[%s]", sType);  // cr will get tacked on later
#ifdef DEBUGSAVE
  fprintf(stdout, "CPreferenceFile::Save(): '[%s]' - sectionname\n", sType);
#endif
                msg[0] = 0;  // skip this line
              } // end if section name

              // treat lines beginning with # or ; as comments
              if ( (msg[0] == '#') || (msg[0] == ';'))
              {
#ifdef DEBUGSAVE
  fprintf(stdout, "CPreferenceFile::Save(): '%s' - comment\n", msg);
#endif
                 fprintf(out, "%s", msg);
                 msg[0] = 0;
              } // end if comment

              if (msg[0])
              {
                 char *tempstr = strdup(msg);
                 char *valueend = 0;
                 char *name = 0;
                 char *value = 0;
                 char *ioLine = tempstr;

                 // strip leading whitespace from line
                 while(*ioLine && isspace(*ioLine)) ioLine++;
                 name = ioLine;

                 // advance to whitespace
                 while(*ioLine && !isspace(*ioLine)) ioLine++;
                 if(*ioLine)
                   *ioLine++ = 0;

                 // strip whitespace in front of value 
                 while(*ioLine && isspace(*ioLine)) ioLine++;
                 value = ioLine;

                 // if value is quoted, parse to end of it 
                 bQuoted = FALSE;
                 if (value[0] == '"')
                 {
                    bQuoted = TRUE;
                    value++;
                    char *endquote = index(value, '\"');
                    if (endquote) 
                    {
                      *endquote = 0;
                      ioLine = endquote;
                    }
                 }

                 // advance to whitespace and terminate
                 while(*ioLine && !isspace(*ioLine)) ioLine++;
                 if(*ioLine)
                   *ioLine = 0;

                // look for a match, if found put it in the file 
                //  and remove it from the list
                char *tempstr1;
                if (sType)
                {
                   tempstr1 = (char *) malloc(strlen(sType)+strlen(name)+2);
                   sprintf(tempstr1, "%s_%s", sType, name);
                }
                else
                   tempstr1 = strdup(name);
                bSaved = FALSE;
                for(pref = pTempList->first();pref != 0;pref=pTempList->next())
                {
                  // if this is the same identifier as the one in the file 
                  if (!strcmp(pref->Identifier(), tempstr1))
                  {
                     char *ioLine1 = msg;
                     char *restofline = 0;   // everything after value
                     char *whitespace = 0;   // start of whitespace after name

                     // advance to text (name)
                     while(*ioLine1 && isspace(*ioLine1)) ioLine1++; 
                     // advance to whitespace
                     while(*ioLine1 && !isspace(*ioLine1)) ioLine1++; 
                     whitespace = ioLine1;

                     // advance to text (value)
                     while(*ioLine1 && isspace(*ioLine1)) ioLine1++; 
                     bQuoted = (ioLine1[0] == '"');
                     *ioLine1++ = 0;  // terminate it

                     if (bQuoted)
                     {
                        char *endquote = index(ioLine1, '\"');
                        if (endquote) 
                        {
                          ioLine1 = endquote;
                          ioLine1++;
                        }
                     }

                     // advance to whitespace
                     while(*ioLine1 && !isspace(*ioLine1)) ioLine1++; 
                     restofline = ioLine1;
                     if (!bQuoted)
                     {
                       fprintf(out, "%s%s%s%s\n", name, 
                                 whitespace, pref->Text(), restofline);
#ifdef DEBUGSAVE
  fprintf(stdout, "CPreferenceFile::Save(): '%s%s%s%s\n' - updated\n", 
         name, whitespace, pref->Text(), restofline);  
#endif
                     }
                     else
                     {
                       fprintf(out, "%s%s\"%s\"%s\n", name, 
                                 whitespace, pref->Text(), restofline);
#ifdef DEBUGSAVE
  fprintf(stdout, "CPreferenceFile::Save(): '%s%s%s%s\n' - updated\n", 
         name, whitespace, pref->Text(), restofline);  
#endif
                     }
                     bSaved = TRUE;
                     count++;
                     pTempList->remove(pref);
                     break;  // match found, done looking
                  } // end if match

                } // end for all entries in temp list

                // if we didn't find a match, save whatever the line was
                if (!bSaved)
                {
#ifdef DEBUGSAVE
  fprintf(stdout, "CPreferenceFile::Save(): '%s\n' - saved non update\n", 
         msg);  
#endif
                  fprintf(out, "%s\n", msg);
                }
                free(tempstr);
                free(tempstr1);

              } // end if pref 
              else
              {
                fprintf(out, "\n");
              }
            }  // end while lines in source file          
#ifdef DEBUGSAVE
  printf("\nCPreferenceFile::Save() - done parsing file-saving leftovers\n\n");
  dumpList(pTempList);
#endif
          // done copying filters that existed in file already
          // dump whatever is left in list
          if (pTempList->count() > 0)
          {
             struct timeval tv;
             if (!gettimeofday(&tv, NULL))
                fprintf(out, "\n# Added Items %s", ctime(&tv.tv_sec));
             else
                fprintf(out, "\n# Added Items\n");
             for( pref = pTempList->first(); pref != 0; pref = pTempList->next() )
             {
                fprintf(out, "%s\t%s\n", pref->Identifier(), pref->Text());
#ifdef DEBUGSAVE
  fprintf(stdout, "CPreferenceFile::Save(): '%s\t%s\n", 
         pref->Identifier(), pref->Text());
#endif
             } // end for all items in remaining list
          } // if items to be added
          if (fflush (out))
            fprintf (stderr, "Couldn't flush file. '%s' - %s\n",
              outfilename, strerror(errno));
          if (fclose (out))
            fprintf (stderr, "Couldn't flush file. '%s' - %s\n",
              outfilename, strerror(errno));                  if (in)
            fclose (in);

//          printf ("file saved '%s'\n", outfilename);

#if 1
          // rename files
          char *tempstr = (char*) malloc( (strlen(infilename) * 2) 
                              + strlen(outfilename) + 25); // should be enough
          sprintf(tempstr, "cp %s %s.bak", infilename, infilename);
#ifdef DEBUG
  printf("%s\n", tempstr);
#endif
          if (-1 == system(tempstr))
          {
            fprintf(stderr, "'%s' - failed\n", tempstr);
          }
          sprintf(tempstr, "mv -f %s %s", outfilename, infilename);
#ifdef DEBUG
   printf("%s\n", tempstr);
#endif
          if (-1 == system(tempstr))
          {
            fprintf(stderr, "'%s' - failed\n", tempstr);
          }
#endif
          free(tempstr);
          if (sType)
            free(sType);
        }
        if (outfilename)
          free(outfilename);
      } // end else file handles good

      fModified = FALSE;

   } // end if modified

} // end Save()
Exemple #19
0
/**
 * Asks the user to add a user specified amount of movies and their respective
 * data. Adds all movies to the specified movieList
 * @param movieList The list to add movies to
 */
void getMovieData(MovieNodeType **movieList) {

	fprintf(outputFile, "* Entering getMovieData *\n");
	dumpList(*movieList);

	/*
	 * Ask the user how many movies they want to input
	 */
	int returnVal, numMovies;
	const int SCANF_UNSUCCESSFUL = 1;

	do {
		printf("Enter the number of movies to be entered: ");
		returnVal = scanf("%d", &numMovies);
		clearStdin();

	} while (returnVal != SCANF_UNSUCCESSFUL || numMovies < 0);

	/*
	 * Get the user to input the movie data
	 */
	int i = 0;
	for (i = 0; i < numMovies; ++i) {
		char title[MAX_STR];
		int year;
		GenreType genre;

		// get movie name
		printf("Enter the name of movie %d:\n", i + 1);

		fgets(title, MAX_STR, stdin);
		title[strlen(title) - 1] = '\0';

		// get movie year
		do {
			printf("Enter the year of movie %d:\n", i + 1);
			returnVal = scanf("%d", &year);
			clearStdin();

		} while (returnVal != SCANF_UNSUCCESSFUL || year < 0);

		// get movie genre
		char genreInput[MAX_STR];
		do {
			printf(
					"Enter the genre of movie %d\nAvailable choices are 'comedy', 'drama', 'action', 'horror', 'science-fiction', 'adventure', 'western':\n",
					i + 1);

			fgets(genreInput, MAX_STR, stdin);
			genreInput[strlen(genreInput) - 1] = '\0';

			if (strcmp(genreInput, "comedy") == 0) {
				genre = C_COMEDY;
				break;
			} else if (strcmp(genreInput, "drama") == 0) {
				genre = C_DRAMA;
				break;
			} else if (strcmp(genreInput, "action") == 0) {
				genre = C_ACTION;
				break;
			} else if (strcmp(genreInput, "horror") == 0) {
				genre = C_HORROR;
				break;
			} else if (strcmp(genreInput, "science-fiction") == 0) {
				genre = C_SF;
				break;
			} else if (strcmp(genreInput, "adventure") == 0) {
				genre = C_ADVENTURE;
				break;
			} else if (strcmp(genreInput, "western") == 0) {
				genre = C_WESTERN;
				break;
			} else {
				continue;
			}

		} while (1);

		// add movie to list
		MovieType *movie;
		initMovie(&movie, title, year, genre);
		addToMovieList(movieList, movie);
	}

	dumpList(*movieList);
	fprintf(outputFile, "* Leaving getMovieData *\n");
}
// . returns false if blocked, true otherwise
// . sets g_errno on error
// . dumps the RdbTree, m_tree, into m_file
// . also sets and writes the RdbMap for m_file
// . we methodically get RdbLists from the RdbTree 
// . dumped recs are ordered by key if "orderedDump" was true in call to set()
//   otherwise, lists are ordered by node #
// . we write each list of recs to the file until the whole tree has been done
// . we delete all records in list from the tree after we've written the list
// . if a cache was provided we incorporate the list into the cache before
//   deleting it from the tree to keep the cache in sync. NO we do NOT!
// . called again by writeBuf() when it's done writing the whole list
bool RdbDump::dumpTree ( bool recall ) {
	// set up some vars
	//int32_t  nextNode;
	//key_t maxEndKey;
	//maxEndKey.setMax();
	char maxEndKey[MAX_KEY_BYTES];
	KEYMAX(maxEndKey,m_ks);
	// if dumping statsdb, we can only dump records 30 seconds old or
	// more because Statsdb.cpp can "back modify" such records in the tree
	// because it may have a query that took 10 seconds come in then it
	// needs to add a partial stat to the last 10 stats for those 10 secs.
	// we use Global time at this juncture
	if ( m_rdb->m_rdbId == RDB_STATSDB ) {
		int32_t nowSecs = getTimeGlobal();
		StatKey *sk = (StatKey *)maxEndKey;
		sk->m_zero      = 0x01;
		sk->m_labelHash = 0xffffffff;
		// leave last 60 seconds in there just to be safe
		sk->m_time1     = nowSecs - 60;
	}

	// this list will hold the list of nodes/recs from m_tree
	m_list = &m_ourList;
	// convert coll to collnum
	//collnum_t collnum = g_collectiondb.getCollnum ( m_coll );
	// a collnum of -1 is for collectionless rdbs
	//if ( collnum < 0 ) {
	//	//if ( g_catdb->getRdb() == m_rdb )
	//	if ( ! m_rdb->m_isCollectionLess ) {
	//		char *xx=NULL;*xx=0; //return true;
	//	}
	//	g_errno = 0;
	//	collnum = 0;
	//}
	// getMemOccupiedForList2() can take some time, so breathe
	int32_t niceness = 1;
 loop:
	// if the lastKey was the max end key last time then we're done
	if ( m_rolledOver     ) return true;
	// this is set to -1 when we're done with our unordered dump
	if ( m_nextNode == -1 ) return true;
	// . NOTE: list's buffer space should be re-used!! (TODO)
	// . "lastNode" is set to the last node # in the list
	bool status = true;
	//if ( ! m_orderedDump ) {
	//	status = ((RdbTree *)m_tree)->getListUnordered ( m_nextNode ,
	//							 m_maxBufSize ,
	//							 m_list , 
	//							 &nextNode );
	//	// this is -1 when no more nodes are left
	//	m_nextNode = nextNode;
	//}
	// "lastKey" is set to the last key in the list
	//else {
	{

		// can we remove neg recs?
		// class RdbBase *base = m_rdb->getBase(m_collnum);
		// bool removeNegRecs = false;
		// if ( base->m_numFiles <= 0 ) removeNegRecs = true;

		if ( recall ) goto skip;

		// debug msg
		//log("RdbDump:: getting list");
		m_t1 = gettimeofdayInMilliseconds();
		if(m_tree)
			status = m_tree->getList ( m_collnum       ,
					   m_nextKey     , 
					   maxEndKey     ,
					   m_maxBufSize  , // max recSizes
					   m_list        , 
					   &m_numPosRecs   ,
					   &m_numNegRecs   ,
					   m_useHalfKeys ,
						   niceness );
		else if(m_buckets)
			status = m_buckets->getList ( m_collnum,
					   m_nextKey     , 
					   maxEndKey     ,
					   m_maxBufSize  , // max recSizes
					   m_list        , 
					   &m_numPosRecs   ,
					   &m_numNegRecs   ,
					   m_useHalfKeys );


		// don't dump out any neg recs if it is our first time dumping
		// to a file for this rdb/coll. TODO: implement this later.
		//if ( removeNegRecs )
		//	m_list.removeNegRecs();

 		// if(!m_list->checkList_r ( false , // removeNegRecs?
 		// 			 false , // sleep on problem?
 		// 			 m_rdb->m_rdbId )) {
 		// 	log("db: list to dump is not sane!");
		// 	char *xx=NULL;*xx=0;
 		// }


	skip:
		int64_t t2;
		//key_t lastKey;
		char *lastKey;
		// if error getting list (out of memory?)
		if ( ! status ) goto hadError;
		// debug msg
		t2 = gettimeofdayInMilliseconds();
		log(LOG_INFO,"db: Get list took %"INT64" ms. "
		    "%"INT32" positive. %"INT32" negative.",
		    t2 - m_t1 , m_numPosRecs , m_numNegRecs );
		// keep a total count for reporting when done
		m_totalPosDumped += m_numPosRecs;
		m_totalNegDumped += m_numNegRecs;
		// . check the list we got from the tree for problems
		// . ensures keys are ordered from lowest to highest as well
		//#ifdef GBSANITYCHECK
		if ( g_conf.m_verifyWrites ) {
			char *s = "none";
			if ( m_rdb ) s = getDbnameFromId(m_rdb->m_rdbId);
			log("dump: verifying list before dumping (rdb=%s)",s);
			m_list->checkList_r ( false , // removeNegRecs?
					      false , // sleep on problem?
					      m_rdb->m_rdbId );
		}
		// if list is empty, we're done!
		if ( status && m_list->isEmpty() ) {
			// consider that a rollover?
			if ( m_rdb->m_rdbId == RDB_STATSDB )
				m_rolledOver = true;
			return true;
		}
		// get the last key of the list
		lastKey = m_list->getLastKey();
		// advance m_nextKey
		//m_nextKey  = lastKey ;
		//m_nextKey += (uint32_t)1;
		//if ( m_nextKey < lastKey ) m_rolledOver = true;
		KEYSET(m_nextKey,lastKey,m_ks);
		KEYADD(m_nextKey,1,m_ks);
		if (KEYCMP(m_nextKey,lastKey,m_ks)<0) m_rolledOver = true;
	      // debug msg
	      //log(0,"RdbDump:lastKey.n1=%"UINT32",n0=%"UINT64"",lastKey.n1,lastKey.n0);
	      //log(0,"RdbDump:next.n1=%"UINT32",n0=%"UINT64"",m_nextKey.n1,m_nextKey.n0);
	}
	// . return true on error, g_errno should have been set
	// . this is probably out of memory error
	if ( ! status ) {
	hadError:
		log("db: Had error getting data for dump: %s. Retrying.", 
		    mstrerror(g_errno));
		// debug msg
		//log("RdbDump::getList: sleeping and retrying");
		// retry for the remaining two types of errors
		if (!g_loop.registerSleepCallback(1000,this,tryAgainWrapper2)){
			log(
			    "db: Retry failed. Could not register callback.");
			return true;
		}
		// wait for sleep
		return false;
	}
	// if list is empty, we're done!
	if ( m_list->isEmpty() ) return true;
	// . set m_firstKeyInQueue and m_lastKeyInQueue
	// . this doesn't work if you're doing an unordered dump, but we should
	//   not allow adds when closing
	m_lastKeyInQueue  = m_list->getLastKey();
	//m_firstKeyInQueue = m_list->getCurrentKey();
	m_list->getCurrentKey(m_firstKeyInQueue);
	// . write this list to disk
	// . returns false if blocked, true otherwise
	// . sets g_errno on error
	// . if this blocks it should call us (dumpTree() back)
	if ( ! dumpList ( m_list , m_niceness , false ) ) return false;
	// close up shop on a write/dumpList error
	if ( g_errno ) return true;
	// . if dumpList() did not block then keep on truckin'
	// . otherwise, wait for callback of dumpTree()
	goto loop;
}
// . delete list from tree, incorporate list into cache, add to map
// . returns false if blocked, true otherwise, sets g_errno on error
bool RdbDump::doneDumpingList ( bool addToMap ) {
	// we can get suspended when gigablast is shutting down, in which
	// case the map may have been deleted. only RdbMerge suspends its
	// m_dump class, not Rdb::m_dump. return false so caller nevers
	// gets called back. we can not resume from this suspension!
	//if ( m_isSuspended ) return false;
	// . if error was EFILECLOSE (file got closed before we wrote to it)
	//   then try again. file can close because fd pool needed more fds
	// . we cannot do this retry in BigFile.cpp because the BigFile
	//   may have been deleted/unlinked from a merge, but we could move
	//   this check to Msg3... and do it for writes, too...
	// . seem to be getting EBADFD errors now, too (what code is it?)
	//   i don't remember, just do it on *all* errors for now!
	//if ( g_errno == EFILECLOSED || g_errno == EBADFD ) {
	if ( g_errno && ! m_isSuspended ) {
		log(LOG_INFO,"db: Had error dumping data: %s. Retrying.",
		    mstrerror(g_errno));
		// . deal with the EBADF bug, it will loop forever on this
		// . i still don't know how the fd gets closed and s_fds[vfd]
		//   is not set to -1?!?!?!
		if ( g_errno == EBADF ) {
			// note it
			log(LOG_LOGIC,"db: setting fd for vfd to -1.");
			// mark our fd as not there...
			//int32_t i=(m_offset-m_bytesToWrite) / MAX_PART_SIZE;
			// sets s_fds[vfd] to -1
			// MDW: no, can't do this now
			// if ( m_file->m_files[i] )
			// 	releaseVfd ( m_file->m_files[i]->m_vfd );
		}
		//log("RdbDump::doneDumpingList: retrying.");
		return dumpList ( m_list , m_niceness , true );
	}
	// bail on error
	if ( g_errno ) {
		log("db: Had error dumping data: %s.", mstrerror(g_errno));
		//log("RdbDump::doneDumpingList: %s",mstrerror(g_errno));
		return true;
	}
	// . don't delete the list if we were dumping an unordered list
	// . we only dump unordered lists when we do a save
	// . it saves time not having to delete the list and it also allows
	//   us to do saves without deleting our data! good!
	if ( ! m_orderedDump ) return true; //--turn this off until save works

	// save for verify routine
	m_addToMap = addToMap;

	// should we verify what we wrote? useful for preventing disk 
	// corruption from those pesky Western Digitals and Maxtors?
	if ( g_conf.m_verifyWrites ) {
		// a debug message, if log disk debug messages is enabled
		log(LOG_DEBUG,"disk: Verifying %"INT32" bytes written.",
		    m_bytesToWrite);
		// make a read buf
		if ( m_verifyBuf && m_verifyBufSize < m_bytesToWrite ) {
			mfree ( m_verifyBuf , m_verifyBufSize , "RdbDump3" );
			m_verifyBuf = NULL;
			m_verifyBufSize = 0;
		}
		if ( ! m_verifyBuf ) {
			m_verifyBuf = (char *)mmalloc ( m_bytesToWrite , 
							"RdbDump3" );
			m_verifyBufSize = m_bytesToWrite;
		}
		// out of mem? if so, skip the write verify
		if ( ! m_verifyBuf ) return doneReadingForVerify();
		// read what we wrote
		bool isDone = m_file->read ( m_verifyBuf    ,
					     m_bytesToWrite ,
					     m_offset - m_bytesToWrite ,
					     &m_fstate      ,
					     this           ,
					     doneReadingForVerifyWrapper ,
					     m_niceness      );
		// debug msg
		//log("RdbDump dumped %"INT32" bytes, done=%"INT32"\n",
		//	m_bytesToWrite,isDone); 
		// return false if it blocked
		if ( ! isDone ) return false;
	}
	return doneReadingForVerify();
}
bool RdbDump::doneReadingForVerify ( ) {

	// if someone reset/deleted the collection we were dumping...
	CollectionRec *cr = g_collectiondb.getRec ( m_collnum );
	// . do not do this for statsdb/catdb which always use collnum of 0
	// . RdbMerge also calls us but gives a NULL m_rdb so we can't
	//   set m_isCollectionless to false
	if ( ! cr && m_doCollCheck ) {
		g_errno = ENOCOLLREC;
		// m_file is invalid if collrec got nuked because so did
		// the Rdbbase which has the files
		log("db: lost collection while dumping to disk. making "
		    "map null so we can stop.");
		m_map = NULL;
	}


	// see if what we wrote is the same as what we read back
	if ( m_verifyBuf && g_conf.m_verifyWrites &&
	     memcmp(m_verifyBuf,m_buf,m_bytesToWrite) != 0 &&
	     ! g_errno ) {
		log("disk: Write verification of %"INT32" bytes to file %s "
		    "failed at offset=%"INT64". Retrying.",
		    m_bytesToWrite,
		    m_file->getFilename(),
		    m_offset - m_bytesToWrite);
		// try writing again
		return dumpList ( m_list , m_niceness , true );
	}
	// time dump to disk (and tfndb bins)
	int64_t t ;
	// start timing on first call only
	if ( m_addToMap ) t = gettimeofdayInMilliseconds();
	// sanity check
	if ( m_list->m_ks != m_ks ) { char *xx = NULL; *xx = 0; }

	bool triedToFix = false;

 tryAgain:
	// . register this with the map now
	// . only register AFTER it's ALL on disk so we don't get partial
	//   record reads and we don't read stuff on disk that's also in tree
	// . add the list to the rdb map if we have one
	// . we don't have maps when we do unordered dumps
	// . careful, map is NULL if we're doing unordered dump
	if ( m_addToMap && m_map && ! m_map->addList ( m_list ) ) {
		// keys  out of order in list from tree?
		if ( g_errno == ECORRUPTDATA ) {
			log("db: trying to fix tree or buckets");
			if ( m_tree ) m_tree->fixTree();
			//if ( m_buckets ) m_buckets->fixBuckets();
			if ( m_buckets ) { char *xx=NULL;*xx=0; }
			if ( triedToFix ) { char *xx=NULL;*xx=0; }
			triedToFix = true;
			goto tryAgain;
		}
		g_errno = ENOMEM; 
		log("db: Failed to add data to map.");
		// undo the offset update, the write failed, the parent
		// should retry. i know RdbMerge.cpp does, but not sure
		// what happens when Rdb.cpp is dumping an RdbTree
		//m_offset -= m_bytesToWrite ;
		// this should never happen now since we call prealloc() above
		char *xx = NULL; *xx = 0;
		return true;
	}

	// debug msg
	int64_t now = gettimeofdayInMilliseconds();
	log(LOG_TIMING,"db: adding to map took %"UINT64" ms" , now - t );

	// . Msg5.cpp and RdbList::merge_r() should remove titleRecs
	//   that are not supported by tfndb, so we only need to add tfndb
	//   records at this point to update the tfndb recs to point to the
	//   new tfn we are dumping into for the existing titlerecs
	// . we just add one tfndb rec per positive titleRec in m_list
	// . negative TitleRec keys should have had a negative tfndb key
	//   added to tfndb in Rdb.cpp::addRecord() already, and ...
	// . RdbList::indexMerge_r() will take care of merging properly
	//   so as to not treat the tfn bits as part of the key when comparing
	// . this will re-call this doneDumpingList(false) if it blocks
	// . returns false if blocks, true otherwise
	//if ( ! updateTfndbLoop() ) return false;

	// . HACK: fix hacked lists before deleting from tree
	// . iff the first key has the half bit set
	if ( m_hacked ) {
		//char tmp[6];
		char tmp[MAX_KEY_BYTES];
		char *p = m_list->getList() - 6 ;
		//gbmemcpy ( tmp   , p     , 6 );
		//gbmemcpy ( p     , p + 6 , 6 );
		//gbmemcpy ( p + 6 , tmp   , 6 );
		gbmemcpy ( tmp          , p     , 6 );
		gbmemcpy ( p            , p + 6 , m_ks-6 );
		gbmemcpy ( p + (m_ks-6) , tmp   , 6 );
		// undo the big hack
		m_list->m_list       = p ;
		m_list->m_listPtr    = p ;
		// make this work for POSDB...
		m_list->m_listPtrLo  = p + m_ks - 12;
		m_list->m_listPtrHi  = p + m_ks - 6;
		m_list->m_listSize  += 6 ;
		// hack off the half bit, we're 12 bytes again
		*p &= 0xfd ;
		// turn it off again just in case
		m_hacked = false;
	}

	if ( m_hacked12 ) {
		char tmp[MAX_KEY_BYTES];
		char *p = m_list->getList() - 12 ;
		// swap high 12 bytes with low 6 bytes for first key
		gbmemcpy ( tmp   , p            , 12 );
		gbmemcpy ( p     , p + 12 ,      6 );
		gbmemcpy ( p + 6, tmp          , 12 );
		// big hack here
		m_list->m_list         = p ;
		m_list->m_listPtr      = p ;
		m_list->m_listPtrLo    = p + 6;
		m_list->m_listPtrHi    = p + 12;
		m_list->m_listSize    += 12 ;
		// hack off the half bit, we're 12 bytes again
		*p &= 0xf9 ;
		m_hacked12 = false;
	}


	// verify keys are in order after we hack it back
	//if ( m_orderedDump ) m_list->checkList_r ( false , true );

	// if we're NOT dumping a tree then return control to RdbMerge
	if ( ! m_tree && !m_buckets ) return true;

	// . merge the writeBuf into the cache at this point or after deleting
	// . m_list should have it's m_lastKey set since we got called from
	//   RdbMerge if m_cache is non-NULL and it called RdbList::merge()
	//   through Msg5 at one point to form this list
	// . right now i just made this clear the cache... it's easier
	//if ( m_cache ) m_cache->incorporateList ( m_list , m_dedup ,
	//					  m_list->getLastKey() );
	// . delete these nodes from the tree now that they're on the disk
	//   now that they can be read from list since addList() was called
	// . however, while we were writing to disk a key that we were
	//   writing could have been deleted from the tree. To prevent
	//   problems we should only delete nodes that are present in tree...
	// . actually i fixed that problem by not deleting any nodes that
	//   might be in the middle of being dumped 
	// . i changed Rdb::addNode() and Rdb::deleteNode() to do this
	// . since we made it here m_list MUST be ordered, therefore
	//   let's try the new, faster deleteOrderedList and let's not do
	//   balancing to make it even faster 
	// . balancing will be restored once we're done deleting this list
	// debug msg
	//log("RdbDump:: deleting list");
	int64_t t1 = gettimeofdayInMilliseconds();
	// convert to number, this is -1 if no longer exists
	//collnum_t collnum = g_collectiondb.getCollnum ( m_coll );
	//if ( collnum < 0 && m_rdb->m_isCollectionLess ) {
	//	collnum = 0;
	//	g_errno = 0;
	//}
	//m_tree->deleteOrderedList ( m_list , false /*do balancing?*/ );
	// tree delete is slow due to checking for leaks, not balancing
	bool s;
	if(m_tree) {
		s = m_tree->deleteList(m_collnum,m_list,true/*do balancing?*/);
	}
	else if(m_buckets) {
		s = m_buckets->deleteList(m_collnum, m_list);
	}
	// problem?
	if ( ! s && ! m_tried ) {
		m_tried = true;
		log("db: Corruption in tree detected when dumping to %s. "
		    "Fixing. Your memory had an error. Consider replacing it.",
		    m_file->getFilename());
		log("db: was collection restarted/reset/deleted before we "
		    "could delete list from tree? collnum=%"INT32"",
		    (int32_t)m_collnum);
		// reset error in that case
		g_errno = 0;
		// if ( m_rdb && m_rdb->m_rdbId != RDB_DOLEDB ) {
		// 	// core now to debug this for sectiondb
		// 	char *xx=NULL;*xx=0;
		// 	((RdbTree *)m_tree)->fixTree ( );
		// }
	}
	// tell rdb he needs saving now
	//if ( m_rdb ) m_rdb->m_needsSave = true;
	// debug msg
	int64_t t2 = gettimeofdayInMilliseconds();
	log(LOG_TIMING,"db: dump: deleteList: took %"INT64"",t2-t1);
	return true;
}
/**
 * dumps the list to the recovery log
 * expired events are not dumped
 * @param reason
 * **/
void straightQueue::dumpQueue( const char* reason )
{
  int numProcessed = dumpList( &eventList, reason );
  listSize -= numProcessed;
} // dumpQueue