Pulled base class AbstractModelLoader out of ModelLoader.
git-svn-id: file:///srv/svn/repos/haiku/haiku/trunk@30427 a95241bf-73f2-0310-859d-f6bbb57e9c96
This commit is contained in:
@@ -62,7 +62,8 @@ MainWindow::MainWindow(DataSource* dataSource)
|
|||||||
|
|
||||||
MainWindow::~MainWindow()
|
MainWindow::~MainWindow()
|
||||||
{
|
{
|
||||||
delete fModelLoader;
|
if (fModelLoader != NULL)
|
||||||
|
fModelLoader->Delete();
|
||||||
|
|
||||||
if (fModel != NULL)
|
if (fModel != NULL)
|
||||||
fModel->RemoveReference();
|
fModel->RemoveReference();
|
||||||
@@ -79,7 +80,7 @@ MainWindow::MessageReceived(BMessage* message)
|
|||||||
{
|
{
|
||||||
printf("MSG_MODEL_LOADED_SUCCESSFULLY\n");
|
printf("MSG_MODEL_LOADED_SUCCESSFULLY\n");
|
||||||
Model* model = fModelLoader->DetachModel();
|
Model* model = fModelLoader->DetachModel();
|
||||||
delete fModelLoader;
|
fModelLoader->Delete();
|
||||||
fModelLoader = NULL;
|
fModelLoader = NULL;
|
||||||
_SetModel(model);
|
_SetModel(model);
|
||||||
model->RemoveReference();
|
model->RemoveReference();
|
||||||
@@ -90,7 +91,7 @@ printf("MSG_MODEL_LOADED_SUCCESSFULLY\n");
|
|||||||
case MSG_MODEL_LOADED_ABORTED:
|
case MSG_MODEL_LOADED_ABORTED:
|
||||||
{
|
{
|
||||||
printf("MSG_MODEL_LOADED_FAILED/MSG_MODEL_LOADED_ABORTED\n");
|
printf("MSG_MODEL_LOADED_FAILED/MSG_MODEL_LOADED_ABORTED\n");
|
||||||
delete fModelLoader;
|
fModelLoader->Delete();
|
||||||
fModelLoader = NULL;
|
fModelLoader = NULL;
|
||||||
// TODO: User feedback (in failed case)!
|
// TODO: User feedback (in failed case)!
|
||||||
break;
|
break;
|
||||||
@@ -128,7 +129,7 @@ MainWindow::Show()
|
|||||||
|
|
||||||
status_t error = fModelLoader->StartLoading();
|
status_t error = fModelLoader->StartLoading();
|
||||||
if (error != B_OK) {
|
if (error != B_OK) {
|
||||||
delete fModelLoader;
|
fModelLoader->Delete();
|
||||||
fModelLoader = NULL;
|
fModelLoader = NULL;
|
||||||
// TODO: User feedback!
|
// TODO: User feedback!
|
||||||
}
|
}
|
||||||
|
|||||||
@@ -0,0 +1,150 @@
|
|||||||
|
/*
|
||||||
|
* Copyright 2009, Ingo Weinhold, [email protected].
|
||||||
|
* Distributed under the terms of the MIT License.
|
||||||
|
*/
|
||||||
|
|
||||||
|
#include "AbstractModelLoader.h"
|
||||||
|
|
||||||
|
#include <AutoLocker.h>
|
||||||
|
|
||||||
|
#include "MessageCodes.h"
|
||||||
|
|
||||||
|
|
||||||
|
AbstractModelLoader::AbstractModelLoader(const BMessenger& target,
|
||||||
|
void* targetCookie)
|
||||||
|
:
|
||||||
|
fLock("main model loader"),
|
||||||
|
fTarget(target),
|
||||||
|
fTargetCookie(targetCookie),
|
||||||
|
fLoaderThread(-1),
|
||||||
|
fLoading(false),
|
||||||
|
fAborted(false)
|
||||||
|
{
|
||||||
|
}
|
||||||
|
|
||||||
|
|
||||||
|
AbstractModelLoader::~AbstractModelLoader()
|
||||||
|
{
|
||||||
|
}
|
||||||
|
|
||||||
|
|
||||||
|
status_t
|
||||||
|
AbstractModelLoader::StartLoading()
|
||||||
|
{
|
||||||
|
// check initialization
|
||||||
|
status_t error = fLock.InitCheck();
|
||||||
|
if (error != B_OK)
|
||||||
|
return error;
|
||||||
|
|
||||||
|
AutoLocker<BLocker> locker(fLock);
|
||||||
|
|
||||||
|
if (fLoading)
|
||||||
|
return B_BAD_VALUE;
|
||||||
|
|
||||||
|
// prepare for loading
|
||||||
|
error = PrepareForLoading();
|
||||||
|
if (error != B_OK)
|
||||||
|
return error;
|
||||||
|
|
||||||
|
// spawn the loader thread
|
||||||
|
fLoaderThread = spawn_thread(&_LoaderEntry, "model loader",
|
||||||
|
B_NORMAL_PRIORITY, this);
|
||||||
|
if (fLoaderThread < 0)
|
||||||
|
return fLoaderThread;
|
||||||
|
|
||||||
|
fLoading = true;
|
||||||
|
fAborted = false;
|
||||||
|
|
||||||
|
resume_thread(fLoaderThread);
|
||||||
|
|
||||||
|
return B_OK;
|
||||||
|
}
|
||||||
|
|
||||||
|
|
||||||
|
void
|
||||||
|
AbstractModelLoader::Abort(bool wait)
|
||||||
|
{
|
||||||
|
AutoLocker<BLocker> locker(fLock);
|
||||||
|
|
||||||
|
if (fLoaderThread < 0)
|
||||||
|
return;
|
||||||
|
|
||||||
|
thread_id thread = fLoaderThread;
|
||||||
|
|
||||||
|
if (fLoading)
|
||||||
|
fAborted = true;
|
||||||
|
|
||||||
|
locker.Unlock();
|
||||||
|
|
||||||
|
if (wait)
|
||||||
|
wait_for_thread(thread, NULL);
|
||||||
|
}
|
||||||
|
|
||||||
|
|
||||||
|
void
|
||||||
|
AbstractModelLoader::Delete()
|
||||||
|
{
|
||||||
|
Abort(true);
|
||||||
|
delete this;
|
||||||
|
}
|
||||||
|
|
||||||
|
|
||||||
|
/*! Called from StartLoading() with the lock held.
|
||||||
|
*/
|
||||||
|
status_t
|
||||||
|
AbstractModelLoader::PrepareForLoading()
|
||||||
|
{
|
||||||
|
return B_OK;
|
||||||
|
}
|
||||||
|
|
||||||
|
|
||||||
|
status_t
|
||||||
|
AbstractModelLoader::Load()
|
||||||
|
{
|
||||||
|
return B_OK;
|
||||||
|
}
|
||||||
|
|
||||||
|
|
||||||
|
/*! Called after loading Load() is done with the lock held.
|
||||||
|
*/
|
||||||
|
void
|
||||||
|
AbstractModelLoader::FinishLoading(bool success)
|
||||||
|
{
|
||||||
|
}
|
||||||
|
|
||||||
|
|
||||||
|
void
|
||||||
|
AbstractModelLoader::NotifyTarget(bool success)
|
||||||
|
{
|
||||||
|
BMessage message(success
|
||||||
|
? MSG_MODEL_LOADED_SUCCESSFULLY
|
||||||
|
: fAborted ? MSG_MODEL_LOADED_ABORTED : MSG_MODEL_LOADED_FAILED);
|
||||||
|
|
||||||
|
message.AddPointer("loader", this);
|
||||||
|
message.AddPointer("targetCookie", fTargetCookie);
|
||||||
|
fTarget.SendMessage(&message);
|
||||||
|
}
|
||||||
|
|
||||||
|
|
||||||
|
/*static*/ status_t
|
||||||
|
AbstractModelLoader::_LoaderEntry(void* data)
|
||||||
|
{
|
||||||
|
return ((AbstractModelLoader*)data)->_Loader();
|
||||||
|
}
|
||||||
|
|
||||||
|
|
||||||
|
status_t
|
||||||
|
AbstractModelLoader::_Loader()
|
||||||
|
{
|
||||||
|
bool success = Load() == B_OK;
|
||||||
|
|
||||||
|
// clean up and notify the target
|
||||||
|
AutoLocker<BLocker> locker(fLock);
|
||||||
|
|
||||||
|
FinishLoading(success);
|
||||||
|
NotifyTarget(success);
|
||||||
|
fLoading = false;
|
||||||
|
|
||||||
|
return B_OK;
|
||||||
|
|
||||||
|
}
|
||||||
@@ -0,0 +1,46 @@
|
|||||||
|
/*
|
||||||
|
* Copyright 2009, Ingo Weinhold, [email protected].
|
||||||
|
* Distributed under the terms of the MIT License.
|
||||||
|
*/
|
||||||
|
#ifndef ABSTRACT_MODEL_LOADER_H
|
||||||
|
#define ABSTRACT_MODEL_LOADER_H
|
||||||
|
|
||||||
|
#include <Locker.h>
|
||||||
|
#include <Messenger.h>
|
||||||
|
|
||||||
|
|
||||||
|
class AbstractModelLoader {
|
||||||
|
public:
|
||||||
|
AbstractModelLoader(const BMessenger& target,
|
||||||
|
void* targetCookie);
|
||||||
|
|
||||||
|
protected:
|
||||||
|
~AbstractModelLoader();
|
||||||
|
|
||||||
|
public:
|
||||||
|
virtual status_t StartLoading();
|
||||||
|
virtual void Abort(bool wait);
|
||||||
|
virtual void Delete();
|
||||||
|
|
||||||
|
protected:
|
||||||
|
virtual status_t PrepareForLoading();
|
||||||
|
virtual status_t Load();
|
||||||
|
virtual void FinishLoading(bool success);
|
||||||
|
|
||||||
|
void NotifyTarget(bool success);
|
||||||
|
|
||||||
|
private:
|
||||||
|
static status_t _LoaderEntry(void* data);
|
||||||
|
status_t _Loader();
|
||||||
|
|
||||||
|
protected:
|
||||||
|
BLocker fLock;
|
||||||
|
BMessenger fTarget;
|
||||||
|
void* fTargetCookie;
|
||||||
|
thread_id fLoaderThread;
|
||||||
|
bool fLoading;
|
||||||
|
bool fAborted;
|
||||||
|
};
|
||||||
|
|
||||||
|
|
||||||
|
#endif // ABSTRACT_MODEL_LOADER_H
|
||||||
@@ -8,5 +8,6 @@ UseHeaders $(HAIKU_DEBUG_ANALYZER_HEADERS) ;
|
|||||||
|
|
||||||
MergeObject DebugAnalyzer_model_loader.o
|
MergeObject DebugAnalyzer_model_loader.o
|
||||||
:
|
:
|
||||||
|
AbstractModelLoader.cpp
|
||||||
ModelLoader.cpp
|
ModelLoader.cpp
|
||||||
;
|
;
|
||||||
|
|||||||
@@ -70,80 +70,20 @@ ModelLoader::_UpdateLastEventTime(bigtime_t time)
|
|||||||
ModelLoader::ModelLoader(DataSource* dataSource,
|
ModelLoader::ModelLoader(DataSource* dataSource,
|
||||||
const BMessenger& target, void* targetCookie)
|
const BMessenger& target, void* targetCookie)
|
||||||
:
|
:
|
||||||
fLock("main model loader"),
|
AbstractModelLoader(target, targetCookie),
|
||||||
fModel(NULL),
|
fModel(NULL),
|
||||||
fDataSource(dataSource),
|
fDataSource(dataSource)
|
||||||
fTarget(target),
|
|
||||||
fTargetCookie(targetCookie),
|
|
||||||
fLoaderThread(-1),
|
|
||||||
fLoading(false),
|
|
||||||
fAborted(false)
|
|
||||||
{
|
{
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
||||||
ModelLoader::~ModelLoader()
|
ModelLoader::~ModelLoader()
|
||||||
{
|
{
|
||||||
Abort(true);
|
|
||||||
|
|
||||||
delete fDataSource;
|
delete fDataSource;
|
||||||
delete fModel;
|
delete fModel;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
||||||
status_t
|
|
||||||
ModelLoader::StartLoading()
|
|
||||||
{
|
|
||||||
// check initialization
|
|
||||||
status_t error = fLock.InitCheck();
|
|
||||||
if (error != B_OK)
|
|
||||||
return error;
|
|
||||||
|
|
||||||
AutoLocker<BLocker> locker(fLock);
|
|
||||||
|
|
||||||
if (fModel != NULL || fLoading || fDataSource == NULL)
|
|
||||||
return B_BAD_VALUE;
|
|
||||||
|
|
||||||
// init the hash tables
|
|
||||||
error = fThreads.Init();
|
|
||||||
if (error != B_OK)
|
|
||||||
return error;
|
|
||||||
|
|
||||||
// spawn the loader thread
|
|
||||||
fLoaderThread = spawn_thread(&_LoaderEntry, "main model loader",
|
|
||||||
B_NORMAL_PRIORITY, this);
|
|
||||||
if (fLoaderThread < 0)
|
|
||||||
return fLoaderThread;
|
|
||||||
|
|
||||||
fLoading = true;
|
|
||||||
fAborted = false;
|
|
||||||
|
|
||||||
resume_thread(fLoaderThread);
|
|
||||||
|
|
||||||
return B_OK;
|
|
||||||
}
|
|
||||||
|
|
||||||
|
|
||||||
void
|
|
||||||
ModelLoader::Abort(bool wait)
|
|
||||||
{
|
|
||||||
AutoLocker<BLocker> locker(fLock);
|
|
||||||
|
|
||||||
if (fLoaderThread < 0)
|
|
||||||
return;
|
|
||||||
|
|
||||||
thread_id thread = fLoaderThread;
|
|
||||||
|
|
||||||
if (fLoading)
|
|
||||||
fAborted = true;
|
|
||||||
|
|
||||||
locker.Unlock();
|
|
||||||
|
|
||||||
if (wait)
|
|
||||||
wait_for_thread(thread, NULL);
|
|
||||||
}
|
|
||||||
|
|
||||||
|
|
||||||
Model*
|
Model*
|
||||||
ModelLoader::DetachModel()
|
ModelLoader::DetachModel()
|
||||||
{
|
{
|
||||||
@@ -159,26 +99,35 @@ ModelLoader::DetachModel()
|
|||||||
}
|
}
|
||||||
|
|
||||||
|
|
||||||
/*static*/ status_t
|
status_t
|
||||||
ModelLoader::_LoaderEntry(void* data)
|
ModelLoader::PrepareForLoading()
|
||||||
{
|
{
|
||||||
return ((ModelLoader*)data)->_Loader();
|
if (fModel != NULL || fDataSource == NULL)
|
||||||
|
return B_BAD_VALUE;
|
||||||
|
|
||||||
|
// init the hash tables
|
||||||
|
status_t error = fThreads.Init();
|
||||||
|
if (error != B_OK)
|
||||||
|
return error;
|
||||||
|
|
||||||
|
return B_OK;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
||||||
status_t
|
status_t
|
||||||
ModelLoader::_Loader()
|
ModelLoader::Load()
|
||||||
{
|
{
|
||||||
status_t error;
|
|
||||||
try {
|
try {
|
||||||
error = _Load();
|
return _Load();
|
||||||
} catch(...) {
|
} catch(...) {
|
||||||
error = B_ERROR;
|
return B_ERROR;
|
||||||
}
|
}
|
||||||
|
}
|
||||||
|
|
||||||
// clean up and notify the target
|
|
||||||
AutoLocker<BLocker> locker(fLock);
|
|
||||||
|
|
||||||
|
void
|
||||||
|
ModelLoader::FinishLoading(bool success)
|
||||||
|
{
|
||||||
ThreadInfo* threadInfo = fThreads.Clear(true);
|
ThreadInfo* threadInfo = fThreads.Clear(true);
|
||||||
while (threadInfo != NULL) {
|
while (threadInfo != NULL) {
|
||||||
ThreadInfo* nextInfo = threadInfo->fNext;
|
ThreadInfo* nextInfo = threadInfo->fNext;
|
||||||
@@ -186,24 +135,10 @@ ModelLoader::_Loader()
|
|||||||
threadInfo = nextInfo;
|
threadInfo = nextInfo;
|
||||||
}
|
}
|
||||||
|
|
||||||
BMessage message;
|
if (!success) {
|
||||||
if (error == B_OK) {
|
|
||||||
message.what = MSG_MODEL_LOADED_SUCCESSFULLY;
|
|
||||||
} else {
|
|
||||||
delete fModel;
|
delete fModel;
|
||||||
fModel = NULL;
|
fModel = NULL;
|
||||||
|
|
||||||
message.what = fAborted
|
|
||||||
? MSG_MODEL_LOADED_ABORTED : MSG_MODEL_LOADED_FAILED;
|
|
||||||
}
|
}
|
||||||
|
|
||||||
message.AddPointer("loader", this);
|
|
||||||
message.AddPointer("targetCookie", fTargetCookie);
|
|
||||||
fTarget.SendMessage(&message);
|
|
||||||
|
|
||||||
fLoading = false;
|
|
||||||
|
|
||||||
return B_OK;
|
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
||||||
|
|||||||
@@ -5,11 +5,9 @@
|
|||||||
#ifndef MAIN_MODEL_LOADER_H
|
#ifndef MAIN_MODEL_LOADER_H
|
||||||
#define MAIN_MODEL_LOADER_H
|
#define MAIN_MODEL_LOADER_H
|
||||||
|
|
||||||
#include <Locker.h>
|
|
||||||
#include <Messenger.h>
|
|
||||||
|
|
||||||
#include <util/OpenHashTable.h>
|
#include <util/OpenHashTable.h>
|
||||||
|
|
||||||
|
#include "AbstractModelLoader.h"
|
||||||
#include "Model.h"
|
#include "Model.h"
|
||||||
|
|
||||||
|
|
||||||
@@ -19,18 +17,23 @@ class DataSource;
|
|||||||
struct system_profiler_thread_added;
|
struct system_profiler_thread_added;
|
||||||
|
|
||||||
|
|
||||||
class ModelLoader {
|
class ModelLoader : public AbstractModelLoader {
|
||||||
public:
|
public:
|
||||||
ModelLoader(DataSource* dataSource,
|
ModelLoader(DataSource* dataSource,
|
||||||
const BMessenger& target,
|
const BMessenger& target,
|
||||||
void* targetCookie);
|
void* targetCookie);
|
||||||
|
|
||||||
|
protected:
|
||||||
~ModelLoader();
|
~ModelLoader();
|
||||||
|
|
||||||
status_t StartLoading();
|
public:
|
||||||
void Abort(bool wait);
|
|
||||||
|
|
||||||
Model* DetachModel();
|
Model* DetachModel();
|
||||||
|
|
||||||
|
protected:
|
||||||
|
virtual status_t PrepareForLoading();
|
||||||
|
virtual status_t Load();
|
||||||
|
virtual void FinishLoading(bool success);
|
||||||
|
|
||||||
private:
|
private:
|
||||||
enum ScheduleState {
|
enum ScheduleState {
|
||||||
RUNNING,
|
RUNNING,
|
||||||
@@ -78,8 +81,6 @@ private:
|
|||||||
thread_removed_from_run_queue;
|
thread_removed_from_run_queue;
|
||||||
|
|
||||||
private:
|
private:
|
||||||
static status_t _LoaderEntry(void* data);
|
|
||||||
status_t _Loader();
|
|
||||||
status_t _Load();
|
status_t _Load();
|
||||||
status_t _ReadDebugEvents(void** _eventData,
|
status_t _ReadDebugEvents(void** _eventData,
|
||||||
size_t* _size);
|
size_t* _size);
|
||||||
@@ -112,14 +113,8 @@ private:
|
|||||||
uint32 type, addr_t object);
|
uint32 type, addr_t object);
|
||||||
|
|
||||||
private:
|
private:
|
||||||
BLocker fLock;
|
|
||||||
Model* fModel;
|
Model* fModel;
|
||||||
DataSource* fDataSource;
|
DataSource* fDataSource;
|
||||||
BMessenger fTarget;
|
|
||||||
void* fTargetCookie;
|
|
||||||
thread_id fLoaderThread;
|
|
||||||
bool fLoading;
|
|
||||||
bool fAborted;
|
|
||||||
bigtime_t fBaseTime;
|
bigtime_t fBaseTime;
|
||||||
bigtime_t fLastEventTime;
|
bigtime_t fLastEventTime;
|
||||||
ThreadTable fThreads;
|
ThreadTable fThreads;
|
||||||
|
|||||||
Reference in New Issue
Block a user