Bug 766347 - Adjust Handle<T> constructors to only accept Rooted<S> or Handle<S> where S is convertible to T. r=luke

--HG--
extra : rebase_source : 5cd1b32a977b4172fbad256a9bbd4a28e8314cdd
This commit is contained in:
Jeff Walden 2012-06-19 15:01:58 -07:00
parent 1128bafac5
commit bda7170ce4

View File

@ -8,12 +8,14 @@
#ifndef jsgc_root_h__ #ifndef jsgc_root_h__
#define jsgc_root_h__ #define jsgc_root_h__
#ifdef __cplusplus
#include "mozilla/TypeTraits.h"
#include "jspubtd.h" #include "jspubtd.h"
#include "js/Utility.h" #include "js/Utility.h"
#ifdef __cplusplus
namespace JS { namespace JS {
/* /*
@ -73,9 +75,11 @@ template <typename T>
class Handle class Handle
{ {
public: public:
/* Copy handles of different types, with implicit coercion. */ /* Creates a handle from a handle of a type convertible to T. */
template <typename S> Handle(Handle<S> handle) { template <typename S>
testAssign<S>(); Handle(Handle<S> handle,
typename mozilla::EnableIf<mozilla::IsConvertible<S, T>::value, int>::Type dummy = 0)
{
ptr = reinterpret_cast<const T *>(handle.address()); ptr = reinterpret_cast<const T *>(handle.address());
} }
@ -96,7 +100,10 @@ class Handle
* Construct a handle from an explicitly rooted location. This is the * Construct a handle from an explicitly rooted location. This is the
* normal way to create a handle, and normally happens implicitly. * normal way to create a handle, and normally happens implicitly.
*/ */
template <typename S> inline Handle(Rooted<S> &root); template <typename S>
inline
Handle(Rooted<S> &root,
typename mozilla::EnableIf<mozilla::IsConvertible<S, T>::value, int>::Type dummy = 0);
const T *address() const { return ptr; } const T *address() const { return ptr; }
T value() const { return *ptr; } T value() const { return *ptr; }
@ -108,16 +115,6 @@ class Handle
Handle() {} Handle() {}
const T *ptr; const T *ptr;
template <typename S>
void testAssign() {
#ifdef DEBUG
T a = RootMethods<T>::initial();
S b = RootMethods<S>::initial();
a = b;
(void)a;
#endif
}
}; };
typedef Handle<JSObject*> HandleObject; typedef Handle<JSObject*> HandleObject;
@ -208,9 +205,9 @@ class Rooted
template<typename T> template <typename S> template<typename T> template <typename S>
inline inline
Handle<T>::Handle(Rooted<S> &root) Handle<T>::Handle(Rooted<S> &root,
typename mozilla::EnableIf<mozilla::IsConvertible<S, T>::value, int>::Type dummy)
{ {
testAssign<S>();
ptr = reinterpret_cast<const T *>(root.address()); ptr = reinterpret_cast<const T *>(root.address());
} }