void testEndThreadException(CuTest *tc) { const int MAX_DOCS=1500; RAMDirectory ram; WhitespaceAnalyzer an; IndexWriter* writer = _CLNEW IndexWriter(&ram, &an, true); // add some documents Document doc; for (int i = 0; i < MAX_DOCS; i++) { TCHAR * tmp = English::IntToEnglish(i); doc.add(* new Field(_T("content"), tmp, Field::STORE_YES | Field::INDEX_UNTOKENIZED)); writer->addDocument(&doc); doc.clear(); _CLDELETE_ARRAY( tmp ); } CuAssertEquals(tc, MAX_DOCS, writer->docCount()); writer->close(); _CLLDELETE(writer); // this sequence is OK: delete searcher after search thread finish { IndexSearcher * searcher = _CLNEW IndexSearcher(&ram); _LUCENE_THREADID_TYPE thread = _LUCENE_THREAD_CREATE(&searchDocs, searcher); SCOPED_LOCK_MUTEX(searchMutex); CONDITION_WAIT(searchMutex, searchCondition); // _LUCENE_SLEEP(9999); //make sure that deleteMutex is being waited on... CONDITION_NOTIFYALL(deleteCondition); _LUCENE_THREAD_JOIN(thread); searcher->close(); _CLLDELETE(searcher); } // this produces memory exception: delete searcher after search finish but before thread finish { IndexSearcher * searcher = _CLNEW IndexSearcher(&ram); _LUCENE_THREADID_TYPE thread = _LUCENE_THREAD_CREATE(&searchDocs, searcher); SCOPED_LOCK_MUTEX(searchMutex); CONDITION_WAIT(searchMutex, searchCondition); searcher->close(); _CLLDELETE(searcher); CONDITION_NOTIFYALL(deleteCondition); _LUCENE_THREAD_JOIN(thread); } ram.close(); }
THREAD_RETURN pool_runner_thread(THREAD_ARGUMENTS parameters) { /* allocates space for the work thread task */ struct thread_pool_task_t *work_thread_task; /* retrieves the thread pool from the arguments */ struct thread_pool_t *thread_pool = (struct thread_pool_t *) parameters; /* ierates continuously */ while(TRUE) { /* locks the task condition lock */ CONDITION_LOCK(thread_pool->task_condition, thread_pool->task_condition_lock); /* iterates while the task queue is empty */ while(thread_pool->task_queue->size == 0) { /* waits for the task condition */ CONDITION_WAIT(thread_pool->task_condition, thread_pool->task_condition_lock); } /* retrieves the work thread task */ pop_value_linked_list(thread_pool->task_queue, (void **) &work_thread_task, 0); /* unlock the task condition lock */ CONDITION_UNLOCK(thread_pool->task_condition, thread_pool->task_condition_lock); /* calls the start function */ work_thread_task->start_function(NULL); } /* returns valid */ return 0; }
VEvent * vevent_wait_next_vevent(void) { VEvent *vevent; MUTEX_LOCK(vevent_queue_lock); while ((vevent = vevent_dequeue_vevent()) == NULL) { CONDITION_WAIT(vevent_queue_condition, vevent_queue_lock); } MUTEX_UNLOCK(vevent_queue_lock); return vevent; }
_LUCENE_THREAD_FUNC(searchDocs, _searcher) { WhitespaceAnalyzer an; IndexSearcher * searcher = (IndexSearcher *)_searcher; Query * query = QueryParser::parse(_T("one"), _T("content"), &an); Hits * hits = searcher->search(query); // _LUCENE_SLEEP(9999); //make sure that searchMutex is being waited on... CONDITION_NOTIFYALL(searchCondition); SCOPED_LOCK_MUTEX(deleteMutex); _CLLDELETE(hits); _CLLDELETE(query); CONDITION_WAIT(deleteMutex, deleteCondition); // _LUCENE_THREAD_FUNC_RETURN(0); }