Add logic to ensure that shared pointers are checked to be of the

right width. The primary upshot is that if you declare AM_SHARE("paletteram")
in an 8-bit memory map, then only m_generic_paletteram_8 will be populated,
and m_generic_paletteram_16 will be NULL. But it applies to all
required_/optional_shared_ptrs declared, so make sure they are of the
right type.

The required_/optional_shared_ptr mechanism should be used to replace
AM_BASE_MEMBER and AM_SIZE_MEMBER, which are technically dangerous and
illegal in C++ but work today through some trickery.
This commit is contained in:
Aaron Giles 2012-04-05 19:19:38 +00:00
parent f87e01ed81
commit e48e63d684
2 changed files with 16 additions and 8 deletions

View File

@ -859,12 +859,18 @@ device_t::finder_base::~finder_base()
// find_memory - find memory // find_memory - find memory
//------------------------------------------------- //-------------------------------------------------
void *device_t::finder_base::find_memory(size_t &size) void *device_t::finder_base::find_memory(UINT8 width, size_t &bytes, bool required)
{ {
memory_share *share = m_base.machine().memory().shared(m_base, m_tag); memory_share *share = m_base.machine().memory().shared(m_base, m_tag);
if (share == NULL) if (share == NULL)
return NULL; return NULL;
size = share->bytes(); if (share->width() != width)
{
if (required)
mame_printf_warning("Shared ptr '%s' found but is width %d, not %d as requested\n", m_tag, share->width(), width);
return NULL;
}
bytes = share->bytes();
return share->ptr(); return share->ptr();
} }

View File

@ -303,7 +303,7 @@ protected:
protected: protected:
// static helpers // static helpers
void *find_memory(size_t &size); void *find_memory(UINT8 width, size_t &bytes, bool required);
// internal state // internal state
finder_base *m_next; finder_base *m_next;
@ -367,11 +367,12 @@ protected:
{ {
public: public:
// construction/destruction // construction/destruction
shared_ptr_finder(device_t &base, const char *tag) shared_ptr_finder(device_t &base, const char *tag, UINT8 width = 0)
: finder_base(base, tag), : finder_base(base, tag),
m_target(0), m_target(0),
m_bytes(0), m_bytes(0),
m_allocated(false) { } m_allocated(false),
m_width((width != 0) ? width : sizeof(_PointerType) * 8) { }
virtual ~shared_ptr_finder() { if (m_allocated) global_free(m_target); } virtual ~shared_ptr_finder() { if (m_allocated) global_free(m_target); }
@ -404,13 +405,14 @@ protected:
} }
// finder // finder
virtual void findit() { m_target = reinterpret_cast<_PointerType *>(find_memory(m_bytes)); } virtual void findit() { m_target = reinterpret_cast<_PointerType *>(find_memory(m_width, m_bytes, _Required)); }
protected: protected:
// internal state // internal state
_PointerType *m_target; _PointerType *m_target;
size_t m_bytes; size_t m_bytes;
bool m_allocated; bool m_allocated;
UINT8 m_width;
}; };
// optional device finder // optional device finder
@ -418,7 +420,7 @@ protected:
class optional_shared_ptr : public shared_ptr_finder<_PointerType, false> class optional_shared_ptr : public shared_ptr_finder<_PointerType, false>
{ {
public: public:
optional_shared_ptr(device_t &base, const char *tag) : shared_ptr_finder<_PointerType, false>(base, tag) { } optional_shared_ptr(device_t &base, const char *tag, UINT8 width = 0) : shared_ptr_finder<_PointerType, false>(base, tag, width) { }
}; };
// required devices are similar but throw an error if they are not found // required devices are similar but throw an error if they are not found
@ -426,7 +428,7 @@ protected:
class required_shared_ptr : public shared_ptr_finder<_PointerType, true> class required_shared_ptr : public shared_ptr_finder<_PointerType, true>
{ {
public: public:
required_shared_ptr(device_t &base, const char *tag) : shared_ptr_finder<_PointerType, true>(base, tag) { } required_shared_ptr(device_t &base, const char *tag, UINT8 width = 0) : shared_ptr_finder<_PointerType, true>(base, tag, width) { }
}; };
// internal helpers // internal helpers