Imgtool: C++-ized the imgtool_library object (now class imgtool::library)

This commit is contained in:
Nathan Woods 2016-09-04 10:47:54 -04:00
parent 3e0d522bce
commit 3534b0090a
6 changed files with 175 additions and 158 deletions

View File

@ -81,7 +81,7 @@ struct imgtool_directory
GLOBALS GLOBALS
***************************************************************************/ ***************************************************************************/
static imgtool_library *global_imgtool_library; static std::unique_ptr<imgtool::library> global_imgtool_library;
static int global_omit_untested; static int global_omit_untested;
static void (*global_warn)(const char *message); static void (*global_warn)(const char *message);
@ -216,14 +216,14 @@ static char *normalize_filename(imgtool_partition *partition, const char *src)
imgtool_init - initializes the imgtool core imgtool_init - initializes the imgtool core
-------------------------------------------------*/ -------------------------------------------------*/
void imgtool_init(int omit_untested, void (*warn)(const char *message)) void imgtool_init(bool omit_untested, void (*warn)(const char *message))
{ {
imgtoolerr_t err; imgtoolerr_t err;
err = imgtool_create_cannonical_library(omit_untested, &global_imgtool_library); err = imgtool_create_cannonical_library(omit_untested, global_imgtool_library);
assert(err == IMGTOOLERR_SUCCESS); assert(err == IMGTOOLERR_SUCCESS);
if (err == IMGTOOLERR_SUCCESS) if (err == IMGTOOLERR_SUCCESS)
{ {
imgtool_library_sort(global_imgtool_library, ITLS_DESCRIPTION); global_imgtool_library->sort(imgtool::library::sort_type::DESCRIPTION);
} }
global_omit_untested = omit_untested; global_omit_untested = omit_untested;
global_warn = warn; global_warn = warn;
@ -238,10 +238,8 @@ void imgtool_init(int omit_untested, void (*warn)(const char *message))
void imgtool_exit(void) void imgtool_exit(void)
{ {
if (global_imgtool_library) if (global_imgtool_library)
{ global_imgtool_library.reset();
imgtool_library_close(global_imgtool_library);
global_imgtool_library = nullptr;
}
global_warn = nullptr; global_warn = nullptr;
} }
@ -253,7 +251,7 @@ void imgtool_exit(void)
const imgtool_module *imgtool_find_module(const char *modulename) const imgtool_module *imgtool_find_module(const char *modulename)
{ {
return imgtool_library_findmodule(global_imgtool_library, modulename); return global_imgtool_library->findmodule(modulename);
} }
@ -386,7 +384,7 @@ imgtool_image *imgtool_partition_image(imgtool_partition *partition)
imgtoolerr_t imgtool_identify_file(const char *fname, imgtool_module **modules, size_t count) imgtoolerr_t imgtool_identify_file(const char *fname, imgtool_module **modules, size_t count)
{ {
imgtoolerr_t err = IMGTOOLERR_SUCCESS; imgtoolerr_t err = IMGTOOLERR_SUCCESS;
imgtool_library *library = global_imgtool_library; imgtool::library *library = global_imgtool_library.get();
imgtool_module *module = nullptr; imgtool_module *module = nullptr;
imgtool_module *insert_module; imgtool_module *insert_module;
imgtool_module *temp_module; imgtool_module *temp_module;
@ -420,7 +418,7 @@ imgtoolerr_t imgtool_identify_file(const char *fname, imgtool_module **modules,
extension++; extension++;
/* iterate through all modules */ /* iterate through all modules */
while((module = imgtool_library_iterate(library, module)) != nullptr) while((module = library->iterate(module)) != nullptr)
{ {
if (!extension || image_find_extension(module->extensions, extension)) if (!extension || image_find_extension(module->extensions, extension))
{ {
@ -939,7 +937,7 @@ int imgtool_validitychecks(void)
created_library = TRUE; created_library = TRUE;
} }
while((module = imgtool_library_iterate(global_imgtool_library, module)) != nullptr) while((module = global_imgtool_library->iterate(module)) != nullptr)
{ {
features = imgtool_get_module_features(module); features = imgtool_get_module_features(module);

View File

@ -78,7 +78,7 @@ struct imgtool_partition_features
}; };
/* ----- initialization and basics ----- */ /* ----- initialization and basics ----- */
void imgtool_init(int omit_untested, void (*warning)(const char *message)); void imgtool_init(bool omit_untested, void (*warning)(const char *message));
void imgtool_exit(void); void imgtool_exit(void);
const imgtool_module *imgtool_find_module(const char *modulename); const imgtool_module *imgtool_find_module(const char *modulename);
imgtool_module_features imgtool_get_module_features(const imgtool_module *module); imgtool_module_features imgtool_get_module_features(const imgtool_module *module);

View File

@ -2,7 +2,7 @@
// copyright-holders:Nathan Woods // copyright-holders:Nathan Woods
/**************************************************************************** /****************************************************************************
library.c library.cpp
Code relevant to the Imgtool library; analgous to the MESS/MAME driver Code relevant to the Imgtool library; analgous to the MESS/MAME driver
list. list.
@ -15,76 +15,62 @@
#include "library.h" #include "library.h"
#include "pool.h" #include "pool.h"
struct imgtool_library namespace imgtool {
//-------------------------------------------------
// ctor
//-------------------------------------------------
library::library()
{ {
object_pool *pool; m_pool = pool_alloc_lib(nullptr);
imgtool_module *first; if (!m_pool)
imgtool_module *last; throw std::bad_alloc();
}; m_first = nullptr;
m_last = nullptr;
imgtool_library *imgtool_library_create(void)
{
imgtool_library *library;
object_pool *pool;
/* create a memory pool */
pool = pool_alloc_lib(nullptr);
if (!pool)
goto error;
/* allocate the main structure */
library = (imgtool_library *)pool_malloc_lib(pool, sizeof(imgtool_library));
if (!library)
goto error;
/* initialize the structure */
memset(library, 0, sizeof(*library));
library->pool = pool;
return library;
error:
if (pool)
pool_free_lib(pool);
return nullptr;
} }
//-------------------------------------------------
// dtor
//-------------------------------------------------
void imgtool_library_close(imgtool_library *library) library::~library()
{ {
pool_free_lib(library->pool); pool_free_lib(m_pool);
} }
//-------------------------------------------------
// add_class
//-------------------------------------------------
static void imgtool_library_add_class(imgtool_library *library, const imgtool_class *imgclass) void library::add_class(const imgtool_class *imgclass)
{ {
imgtool_module *module; imgtool_module *module;
char *s1, *s2; char *s1, *s2;
/* allocate the module and place it in the chain */ // allocate the module and place it in the chain
module = (imgtool_module *)imgtool_library_malloc(library, sizeof(*module)); module = (imgtool_module *)imgtool_library_malloc(sizeof(*module));
memset(module, 0, sizeof(*module)); memset(module, 0, sizeof(*module));
module->previous = library->last; module->previous = m_last;
if (library->last) if (m_last)
library->last->next = module; m_last->next = module;
else else
library->first = module; m_first = module;
library->last = module; m_last = module;
/* extensions have a weird format */ // extensions have a weird format
s1 = imgtool_get_info_string(imgclass, IMGTOOLINFO_STR_FILE_EXTENSIONS); s1 = imgtool_get_info_string(imgclass, IMGTOOLINFO_STR_FILE_EXTENSIONS);
s2 = (char*)imgtool_library_malloc(library, strlen(s1) + 1); s2 = (char*)imgtool_library_malloc(strlen(s1) + 1);
strcpy(s2, s1); strcpy(s2, s1);
module->extensions = s2; module->extensions = s2;
module->imgclass = *imgclass; module->imgclass = *imgclass;
module->name = imgtool_library_strdup(library, imgtool_get_info_string(imgclass, IMGTOOLINFO_STR_NAME)); module->name = imgtool_library_strdup(imgtool_get_info_string(imgclass, IMGTOOLINFO_STR_NAME));
module->description = imgtool_library_strdup(library, imgtool_get_info_string(imgclass, IMGTOOLINFO_STR_DESCRIPTION)); module->description = imgtool_library_strdup(imgtool_get_info_string(imgclass, IMGTOOLINFO_STR_DESCRIPTION));
module->eoln = imgtool_library_strdup_allow_null(library, imgtool_get_info_string(imgclass, IMGTOOLINFO_STR_EOLN)); module->eoln = imgtool_library_strdup_allow_null(imgtool_get_info_string(imgclass, IMGTOOLINFO_STR_EOLN));
module->initial_path_separator = imgtool_get_info_int(imgclass, IMGTOOLINFO_INT_INITIAL_PATH_SEPARATOR) ? 1 : 0; module->initial_path_separator = imgtool_get_info_int(imgclass, IMGTOOLINFO_INT_INITIAL_PATH_SEPARATOR) ? 1 : 0;
module->open_is_strict = imgtool_get_info_int(imgclass, IMGTOOLINFO_INT_OPEN_IS_STRICT) ? 1 : 0; module->open_is_strict = imgtool_get_info_int(imgclass, IMGTOOLINFO_INT_OPEN_IS_STRICT) ? 1 : 0;
module->tracks_are_called_cylinders = imgtool_get_info_int(imgclass, IMGTOOLINFO_INT_TRACKS_ARE_CALLED_CYLINDERS) ? 1 : 0; module->tracks_are_called_cylinders = imgtool_get_info_int(imgclass, IMGTOOLINFO_INT_TRACKS_ARE_CALLED_CYLINDERS) ? 1 : 0;
@ -103,23 +89,26 @@ static void imgtool_library_add_class(imgtool_library *library, const imgtool_cl
module->list_partitions = (imgtoolerr_t (*)(imgtool_image *, imgtool_partition_info *, size_t)) imgtool_get_info_fct(imgclass, IMGTOOLINFO_PTR_LIST_PARTITIONS); module->list_partitions = (imgtoolerr_t (*)(imgtool_image *, imgtool_partition_info *, size_t)) imgtool_get_info_fct(imgclass, IMGTOOLINFO_PTR_LIST_PARTITIONS);
module->block_size = imgtool_get_info_int(imgclass, IMGTOOLINFO_INT_BLOCK_SIZE); module->block_size = imgtool_get_info_int(imgclass, IMGTOOLINFO_INT_BLOCK_SIZE);
module->createimage_optguide = (const util::option_guide *) imgtool_get_info_ptr(imgclass, IMGTOOLINFO_PTR_CREATEIMAGE_OPTGUIDE); module->createimage_optguide = (const util::option_guide *) imgtool_get_info_ptr(imgclass, IMGTOOLINFO_PTR_CREATEIMAGE_OPTGUIDE);
module->createimage_optspec = imgtool_library_strdup_allow_null(library, (const char*)imgtool_get_info_ptr(imgclass, IMGTOOLINFO_STR_CREATEIMAGE_OPTSPEC)); module->createimage_optspec = imgtool_library_strdup_allow_null((const char*)imgtool_get_info_ptr(imgclass, IMGTOOLINFO_STR_CREATEIMAGE_OPTSPEC));
module->image_extra_bytes += imgtool_get_info_int(imgclass, IMGTOOLINFO_INT_IMAGE_EXTRA_BYTES); module->image_extra_bytes += imgtool_get_info_int(imgclass, IMGTOOLINFO_INT_IMAGE_EXTRA_BYTES);
} }
//-------------------------------------------------
// add
//-------------------------------------------------
void imgtool_library_add(imgtool_library *library, imgtool_get_info get_info) void library::add(imgtool_get_info get_info)
{ {
int (*make_class)(int index, imgtool_class *imgclass); int (*make_class)(int index, imgtool_class *imgclass);
imgtool_class imgclass; imgtool_class imgclass;
int i, result; int i, result;
/* try this class */ // try this class
memset(&imgclass, 0, sizeof(imgclass)); memset(&imgclass, 0, sizeof(imgclass));
imgclass.get_info = get_info; imgclass.get_info = get_info;
/* do we have derived getinfo functions? */ // do we have derived getinfo functions?
make_class = (int (*)(int index, imgtool_class *imgclass)) make_class = (int (*)(int index, imgtool_class *imgclass))
imgtool_get_info_fct(&imgclass, IMGTOOLINFO_PTR_MAKE_CLASS); imgtool_get_info_fct(&imgclass, IMGTOOLINFO_PTR_MAKE_CLASS);
@ -128,38 +117,40 @@ void imgtool_library_add(imgtool_library *library, imgtool_get_info get_info)
i = 0; i = 0;
do do
{ {
/* clear out the class */ // clear out the class
memset(&imgclass, 0, sizeof(imgclass)); memset(&imgclass, 0, sizeof(imgclass));
imgclass.get_info = get_info; imgclass.get_info = get_info;
/* make the class */ // make the class
result = make_class(i++, &imgclass); result = make_class(i++, &imgclass);
if (result) if (result)
imgtool_library_add_class(library, &imgclass); add_class(&imgclass);
} }
while(result); while(result);
} }
else else
{ {
imgtool_library_add_class(library, &imgclass); add_class(&imgclass);
} }
} }
//-------------------------------------------------
// unlink
//-------------------------------------------------
const imgtool_module *imgtool_library_unlink(imgtool_library *library, const imgtool_module *library::unlink(const char *module)
const char *module)
{ {
imgtool_module *m; imgtool_module *m;
imgtool_module **previous; imgtool_module **previous;
imgtool_module **next; imgtool_module **next;
for (m = library->first; m; m = m->next) for (m = m_first; m; m = m->next)
{ {
if (!core_stricmp(m->name, module)) if (!core_stricmp(m->name, module))
{ {
previous = m->previous ? &m->previous->next : &library->first; previous = m->previous ? &m->previous->next : &m_first;
next = m->next ? &m->next->previous : &library->last; next = m->next ? &m->next->previous : &m_last;
*previous = m->next; *previous = m->next;
*next = m->previous; *next = m->previous;
m->previous = nullptr; m->previous = nullptr;
@ -171,26 +162,31 @@ const imgtool_module *imgtool_library_unlink(imgtool_library *library,
} }
//-------------------------------------------------
// module_compare
//-------------------------------------------------
static int module_compare(const imgtool_module *m1, int library::module_compare(const imgtool_module *m1, const imgtool_module *m2, sort_type sort)
const imgtool_module *m2, imgtool_libsort_t sort)
{ {
int rc = 0; int rc = 0;
switch(sort) switch(sort)
{ {
case ITLS_NAME: case sort_type::NAME:
rc = strcmp(m1->name, m2->name); rc = strcmp(m1->name, m2->name);
break; break;
case ITLS_DESCRIPTION: case sort_type::DESCRIPTION:
rc = core_stricmp(m1->name, m2->name); rc = core_stricmp(m1->description, m2->description);
break; break;
} }
return rc; return rc;
} }
//-------------------------------------------------
// sort
//-------------------------------------------------
void imgtool_library_sort(imgtool_library *library, imgtool_libsort_t sort) void library::sort(sort_type sort)
{ {
imgtool_module *m1; imgtool_module *m1;
imgtool_module *m2; imgtool_module *m2;
@ -198,7 +194,7 @@ void imgtool_library_sort(imgtool_library *library, imgtool_libsort_t sort)
imgtool_module **before; imgtool_module **before;
imgtool_module **after; imgtool_module **after;
for (m1 = library->first; m1; m1 = m1->next) for (m1 = m_first; m1; m1 = m1->next)
{ {
target = m1; target = m1;
for (m2 = m1->next; m2; m2 = m2->next) for (m2 = m1->next; m2; m2 = m2->next)
@ -209,74 +205,93 @@ void imgtool_library_sort(imgtool_library *library, imgtool_libsort_t sort)
if (target != m1) if (target != m1)
{ {
/* unlink the target */ // unlink the target
before = target->previous ? &target->previous->next : &library->first; before = target->previous ? &target->previous->next : &m_first;
after = target->next ? &target->next->previous : &library->last; after = target->next ? &target->next->previous : &m_last;
*before = target->next; *before = target->next;
*after = target->previous; *after = target->previous;
/* now place the target before m1 */ // now place the target before m1
target->previous = m1->previous; target->previous = m1->previous;
target->next = m1; target->next = m1;
before = m1->previous ? &m1->previous->next : &library->first; before = m1->previous ? &m1->previous->next : &m_first;
*before = target; *before = target;
m1->previous = target; m1->previous = target;
/* since we changed the order, we have to replace ourselves */ // since we changed the order, we have to replace ourselves
m1 = target; m1 = target;
} }
} }
} }
//-------------------------------------------------
// findmodule
//-------------------------------------------------
const imgtool_module *imgtool_library_findmodule( const imgtool_module *library::findmodule(const char *module_name)
imgtool_library *library, const char *module_name)
{ {
const imgtool_module *module; const imgtool_module *module;
assert(library); module = m_first;
module = library->first;
while(module && module_name && strcmp(module->name, module_name)) while(module && module_name && strcmp(module->name, module_name))
module = module->next; module = module->next;
return module; return module;
} }
//-------------------------------------------------
// iterate
//-------------------------------------------------
imgtool_module *imgtool_library_iterate(imgtool_library *library, const imgtool_module *module) imgtool_module *library::iterate(const imgtool_module *module)
{ {
return module ? module->next : library->first; return module ? module->next : m_first;
} }
//-------------------------------------------------
// index
//-------------------------------------------------
imgtool_module *imgtool_library_index(imgtool_library *library, int i) imgtool_module *library::index(int i)
{ {
imgtool_module *module; imgtool_module *module;
module = library->first; module = m_first;
while(module && i--) while(module && i--)
module = module->next; module = module->next;
return module; return module;
} }
//-------------------------------------------------
// imgtool_library_malloc
//-------------------------------------------------
void *imgtool_library_malloc(imgtool_library *library, size_t mem) void *library::imgtool_library_malloc(size_t mem)
{ {
return pool_malloc_lib(library->pool, mem); return pool_malloc_lib(m_pool, mem);
} }
//-------------------------------------------------
// imgtool_library_malloc
//-------------------------------------------------
char *imgtool_library_strdup(imgtool_library *library, const char *s) char *library::imgtool_library_strdup(const char *s)
{ {
return pool_strdup_lib(library->pool, s); return pool_strdup_lib(m_pool, s);
} }
//-------------------------------------------------
// imgtool_library_strdup_allow_null
//-------------------------------------------------
char *imgtool_library_strdup_allow_null(imgtool_library *library, const char *s) char *library::imgtool_library_strdup_allow_null(const char *s)
{ {
return s ? imgtool_library_strdup(library, s) : nullptr; return s ? imgtool_library_strdup(s) : nullptr;
} }
} // namespace imgtool

View File

@ -24,12 +24,12 @@
#include "stream.h" #include "stream.h"
#include "unicode.h" #include "unicode.h"
#include "charconv.h" #include "charconv.h"
#include "pool.h"
struct imgtool_image; struct imgtool_image;
struct imgtool_partition; struct imgtool_partition;
struct imgtool_directory; struct imgtool_directory;
struct imgtool_library;
enum imgtool_suggestion_viability_t enum imgtool_suggestion_viability_t
{ {
@ -52,12 +52,6 @@ union filterinfo
typedef void (*filter_getinfoproc)(UINT32 state, union filterinfo *info); typedef void (*filter_getinfoproc)(UINT32 state, union filterinfo *info);
enum imgtool_libsort_t
{
ITLS_NAME,
ITLS_DESCRIPTION
};
struct imgtool_dirent struct imgtool_dirent
{ {
char filename[1024]; char filename[1024];
@ -375,34 +369,56 @@ struct imgtool_module
const void *extra; const void *extra;
}; };
/* creates an imgtool library */ namespace imgtool {
imgtool_library *imgtool_library_create(void);
/* closes an imgtool library */ //**************************************************************************
void imgtool_library_close(imgtool_library *library); // TYPE DEFINITIONS
//**************************************************************************
/* adds a module to an imgtool library */ // imgtool "library" - equivalent to the MAME driver list
void imgtool_library_add(imgtool_library *library, imgtool_get_info get_info); class library
{
public:
enum class sort_type
{
NAME,
DESCRIPTION
};
/* seeks out and removes a module from an imgtool library */ library();
const imgtool_module *imgtool_library_unlink(imgtool_library *library, ~library();
const char *module);
/* sorts an imgtool library */ // adds a module to an imgtool library
void imgtool_library_sort(imgtool_library *library, imgtool_libsort_t sort); void add(imgtool_get_info get_info);
/* finds a module */ // seeks out and removes a module from an imgtool library
const imgtool_module *imgtool_library_findmodule( const imgtool_module *unlink(const char *module);
imgtool_library *library, const char *module_name);
/* memory allocators for pooled library memory */ // sorts an imgtool library
void *imgtool_library_malloc(imgtool_library *library, size_t mem); void sort(sort_type sort);
char *imgtool_library_strdup(imgtool_library *library, const char *s);
char *imgtool_library_strdup_allow_null(imgtool_library *library, const char *s);
imgtool_module *imgtool_library_iterate( // finds a module
imgtool_library *library, const imgtool_module *module); const imgtool_module *findmodule(const char *module_name);
imgtool_module *imgtool_library_index(
imgtool_library *library, int i);
#endif /* LIBRARY_H */ // module iteration
imgtool_module *iterate(const imgtool_module *module);
imgtool_module *index(int i);
private:
object_pool * m_pool;
imgtool_module * m_first;
imgtool_module * m_last;
// helpers
void add_class(const imgtool_class *imgclass);
int module_compare(const imgtool_module *m1, const imgtool_module *m2, sort_type sort);
// memory allocators for pooled library memory (these should go away in further C++-ification)
void *imgtool_library_malloc(size_t mem);
char *imgtool_library_strdup(const char *s);
char *imgtool_library_strdup_allow_null(const char *s);
};
} // namespace imgtool
#endif // LIBRARY_H

View File

@ -27,11 +27,9 @@ static void (*const modules[])(const imgtool_class *imgclass, UINT32 state, unio
}; };
/* step 3: declare imgtool_create_cannonical_library() */ /* step 3: declare imgtool_create_cannonical_library() */
imgtoolerr_t imgtool_create_cannonical_library(int omit_untested, imgtool_library **library) imgtoolerr_t imgtool_create_cannonical_library(bool omit_untested, std::unique_ptr<imgtool::library> &library)
{ {
imgtoolerr_t err;
size_t i; size_t i;
imgtool_library *lib;
imgtool_module *module; imgtool_module *module;
/* list of modules that we drop */ /* list of modules that we drop */
@ -40,28 +38,25 @@ imgtoolerr_t imgtool_create_cannonical_library(int omit_untested, imgtool_librar
"coco_os9_rsdos" "coco_os9_rsdos"
}; };
lib = imgtool_library_create(); library.reset(new imgtool::library());
if (!lib) if (!library)
{ return IMGTOOLERR_OUTOFMEMORY;
err = IMGTOOLERR_OUTOFMEMORY;
goto error;
}
/* create all modules */ // create all modules
for (i = 0; i < ARRAY_LENGTH(modules); i++) for (i = 0; i < ARRAY_LENGTH(modules); i++)
imgtool_library_add(lib, modules[i]); library->add( modules[i]);
/* remove irrelevant modules */ // remove irrelevant modules
for (i = 0; i < ARRAY_LENGTH(irrelevant_modules); i++) for (i = 0; i < ARRAY_LENGTH(irrelevant_modules); i++)
{ {
imgtool_library_unlink(lib, irrelevant_modules[i]); library->unlink(irrelevant_modules[i]);
} }
/* if we are omitting untested, go through and block out the functionality in question */ // if we are omitting untested, go through and block out the functionality in question
if (omit_untested) if (omit_untested)
{ {
module = nullptr; module = nullptr;
while((module = imgtool_library_iterate(lib, module)) != nullptr) while((module = library->iterate(module)) != nullptr)
{ {
if (module->writing_untested) if (module->writing_untested)
{ {
@ -76,14 +71,7 @@ imgtoolerr_t imgtool_create_cannonical_library(int omit_untested, imgtool_librar
} }
} }
*library = lib;
return IMGTOOLERR_SUCCESS; return IMGTOOLERR_SUCCESS;
error:
if (lib)
imgtool_library_close(lib);
return err;
} }

View File

@ -13,6 +13,6 @@
#include "library.h" #include "library.h"
imgtoolerr_t imgtool_create_cannonical_library(int omit_untested, imgtool_library **library); imgtoolerr_t imgtool_create_cannonical_library(bool omit_untested, std::unique_ptr<imgtool::library> &library);
#endif /* MODULES_H */ #endif /* MODULES_H */