Пример #1
0
static bool CheckJournalDocumentCollection (TRI_document_collection_t* doc) {
  TRI_collection_t* base;
  TRI_datafile_t* journal;
  bool worked;
  size_t i;
  size_t n;

  worked = false;
  base = &doc->base.base;

  if (base->_state != TRI_COL_STATE_WRITE) {
    return false;
  }

  // .............................................................................
  // the only thread MODIFYING the _journals variable is this thread,
  // therefore no locking is required to access the _journals
  // .............................................................................

  TRI_LOCK_JOURNAL_ENTRIES_DOC_COLLECTION(doc);

  n = base->_journals._length;

  for (i = 0;  i < n;) {
    journal = base->_journals._buffer[i];

    if (journal->_full) {
      worked = true;

      LOG_DEBUG("closing full journal '%s'", journal->getName(journal));

      TRI_CloseJournalPrimaryCollection(&doc->base, i);

      n = base->_journals._length;
      i = 0;
    }
    else {
      ++i;
    }
  }

  if (base->_journals._length == 0) {
    journal = TRI_CreateJournalDocumentCollection(doc);

    if (journal != NULL) {
      worked = true;
      LOG_DEBUG("created new journal '%s'", journal->getName(journal));

      TRI_BROADCAST_JOURNAL_ENTRIES_DOC_COLLECTION(doc);
    }
    else {
      // an error occurred when creating the journal file
      LOG_ERROR("could not create journal file");

      // we still must wake up the other thread from time to time, otherwise we'll deadlock
      TRI_BROADCAST_JOURNAL_ENTRIES_DOC_COLLECTION(doc);
    }
  }

  TRI_UNLOCK_JOURNAL_ENTRIES_DOC_COLLECTION(doc);

  return worked;
}
Пример #2
0
static bool CheckJournalDocumentCollection (TRI_document_collection_t* document) {
  TRI_collection_t* base;
  TRI_datafile_t* journal;
  bool worked;
  size_t i;
  size_t n;

  worked = false;
  base = &document->base.base;

  if (base->_state != TRI_COL_STATE_WRITE) {
    return false;
  }

  // .............................................................................
  // the only thread MODIFYING the _journals variable is this thread,
  // therefore no locking is required to access the _journals
  // .............................................................................

  TRI_LOCK_JOURNAL_ENTRIES_DOC_COLLECTION(document);
  n = base->_journals._length;

  for (i = 0;  i < n;) {
    journal = static_cast<TRI_datafile_t*>(base->_journals._buffer[i]);

    if (journal->_full) {
      worked = true;

      LOG_DEBUG("closing full journal '%s'", journal->getName(journal));

      TRI_CloseJournalPrimaryCollection(&document->base, i);

      n = base->_journals._length;
      i = 0;
    }
    else {
      ++i;
    }
  }

  // create a new journal if we do not have one, AND, if there was a request to create one
  // (sometimes we don't need a journal, e.g. directly after db._create(collection); when
  // the collection is still empty)
  if (base->_journals._length == 0 && 
      document->_requestedJournalSize > 0) {
    TRI_voc_size_t targetSize = document->base.base._info._maximalSize;

    if (document->_requestedJournalSize > 0 && 
        document->_requestedJournalSize > targetSize) {
      targetSize = document->_requestedJournalSize;
    }

    journal = TRI_CreateJournalDocumentCollection(document, targetSize);

    if (journal != NULL) {
      worked = true;
      document->_requestedJournalSize = 0;
      document->_rotateRequested      = false;

      LOG_DEBUG("created new journal '%s'", journal->getName(journal));
    }
    else {
      // an error occurred when creating the journal file
      LOG_ERROR("could not create journal file");
    }
  }
  else if (document->_rotateRequested) {
    // only a rotate was requested
    document->_rotateRequested = false;
  }
  
  // always broadcast, otherwise other threads waiting for the broadcast might deadlock!
  TRI_BROADCAST_JOURNAL_ENTRIES_DOC_COLLECTION(document);

  TRI_UNLOCK_JOURNAL_ENTRIES_DOC_COLLECTION(document);

  return worked;
}