зеркало из https://github.com/mozilla/pjs.git
NOT YET PART OF SEAMONKEY - more conversion stuff implemented
This commit is contained in:
Родитель
50b4c17f6d
Коммит
b65de451d8
|
@ -1 +1,4 @@
|
|||
Makefile
|
||||
convert
|
||||
mk.bat
|
||||
set_env.bat
|
||||
|
|
|
@ -33,7 +33,7 @@ class nsXPTConstant;
|
|||
class nsIInterfaceInfo : public nsISupports
|
||||
{
|
||||
public:
|
||||
|
||||
|
||||
NS_IMETHOD GetName(char** name) = 0; // returns IAllocatator alloc'd copy
|
||||
NS_IMETHOD GetIID(nsIID** iid) = 0; // returns IAllocatator alloc'd copy
|
||||
|
||||
|
|
|
@ -51,8 +51,8 @@ nsXPConnect::GetXPConnect()
|
|||
return mSelf;
|
||||
}
|
||||
|
||||
// static
|
||||
nsIAllocator*
|
||||
// static
|
||||
nsIAllocator*
|
||||
nsXPConnect::GetAllocator(nsXPConnect* xpc /*= NULL*/)
|
||||
{
|
||||
nsIAllocator* al;
|
||||
|
@ -67,8 +67,8 @@ nsXPConnect::GetAllocator(nsXPConnect* xpc /*= NULL*/)
|
|||
return al;
|
||||
}
|
||||
|
||||
// static
|
||||
nsIInterfaceInfoManager*
|
||||
// static
|
||||
nsIInterfaceInfoManager*
|
||||
nsXPConnect::GetInterfaceInfoManager(nsXPConnect* xpc /*= NULL*/)
|
||||
{
|
||||
nsIInterfaceInfoManager* iim;
|
||||
|
@ -83,6 +83,25 @@ nsXPConnect::GetInterfaceInfoManager(nsXPConnect* xpc /*= NULL*/)
|
|||
return iim;
|
||||
}
|
||||
|
||||
// static
|
||||
XPCContext*
|
||||
nsXPConnect::GetContext(JSContext* cx, nsXPConnect* xpc /*= NULL*/)
|
||||
{
|
||||
NS_PRECONDITION(cx,"bad param");
|
||||
|
||||
XPCContext* xpcc;
|
||||
nsXPConnect* xpcl = xpc;
|
||||
|
||||
if(!xpcl && !(xpcl = GetXPConnect()))
|
||||
return NULL;
|
||||
xpcc = xpcl->mContextMap->Find(cx);
|
||||
if(!xpcc)
|
||||
xpcc = xpcl->NewContext(cx, JS_GetGlobalObject(cx));
|
||||
if(!xpc)
|
||||
NS_RELEASE(xpcl);
|
||||
return xpcc;
|
||||
}
|
||||
|
||||
nsXPConnect::nsXPConnect()
|
||||
: mContextMap(NULL),
|
||||
mAllocator(NULL),
|
||||
|
@ -130,17 +149,6 @@ nsXPConnect::InitJSContext(JSContext* aJSContext,
|
|||
return NS_OK;
|
||||
}
|
||||
|
||||
XPCContext*
|
||||
nsXPConnect::GetContext(JSContext* cx)
|
||||
{
|
||||
XPCContext* xpcc;
|
||||
NS_PRECONDITION(cx,"bad param");
|
||||
xpcc = mContextMap->Find(cx);
|
||||
if(!xpcc)
|
||||
xpcc = NewContext(cx, JS_GetGlobalObject(cx));
|
||||
return xpcc;
|
||||
}
|
||||
|
||||
XPCContext*
|
||||
nsXPConnect::NewContext(JSContext* cx, JSObject* global)
|
||||
{
|
||||
|
@ -171,7 +179,7 @@ nsXPConnect::WrapNative(JSContext* aJSContext,
|
|||
|
||||
*aWrapper = NULL;
|
||||
|
||||
XPCContext* xpcc = GetContext(aJSContext);
|
||||
XPCContext* xpcc = nsXPConnect::GetContext(aJSContext, this);
|
||||
if(!xpcc)
|
||||
return NS_ERROR_FAILURE;
|
||||
|
||||
|
@ -197,7 +205,7 @@ nsXPConnect::WrapJS(JSContext* aJSContext,
|
|||
|
||||
*aWrapper = NULL;
|
||||
|
||||
XPCContext* xpcc = GetContext(aJSContext);
|
||||
XPCContext* xpcc = nsXPConnect::GetContext(aJSContext, this);
|
||||
if(!xpcc)
|
||||
return NS_ERROR_FAILURE;
|
||||
|
||||
|
|
|
@ -20,8 +20,10 @@
|
|||
|
||||
#include "xpcprivate.h"
|
||||
|
||||
// static
|
||||
JSBool
|
||||
static NS_DEFINE_IID(kWrappedJSMethodsIID, NS_IXPCONNECT_WRAPPED_JS_METHODS_IID);
|
||||
|
||||
// static
|
||||
JSBool
|
||||
XPCConvert::IsMethodReflectable(const nsXPTMethodInfo& info)
|
||||
{
|
||||
if(info.IsHidden())
|
||||
|
@ -166,7 +168,7 @@ XPCConvert::IsMethodReflectable(const nsXPTMethodInfo& info)
|
|||
}
|
||||
}
|
||||
return JS_TRUE;
|
||||
}
|
||||
}
|
||||
|
||||
// XXX these conversion functions need to be finished.
|
||||
// XXX conversion functions may still need paramInfo to handle the additional
|
||||
|
@ -178,10 +180,10 @@ XPCConvert::IsMethodReflectable(const nsXPTMethodInfo& info)
|
|||
// Win32 can't handle uint64 to double conversion
|
||||
#define JAM_DOUBLE_U64(v,d) JAM_DOUBLE(((int64)v),d)
|
||||
|
||||
// static
|
||||
// static
|
||||
JSBool
|
||||
XPCConvert::NativeData2JS(jsval* d, const void* s,
|
||||
const nsXPTType& type)
|
||||
XPCConvert::NativeData2JS(JSContext* cx, jsval* d, const void* s,
|
||||
const nsXPTType& type, const nsID* iid)
|
||||
{
|
||||
NS_PRECONDITION(s, "bad param");
|
||||
NS_PRECONDITION(d, "bad param");
|
||||
|
@ -209,40 +211,96 @@ XPCConvert::NativeData2JS(jsval* d, const void* s,
|
|||
NS_ASSERTION(0,"unsupported type");
|
||||
return JS_FALSE;
|
||||
}
|
||||
|
||||
// set the default result
|
||||
*d = JSVAL_NULL;
|
||||
|
||||
switch(type.TagPart())
|
||||
{
|
||||
case nsXPTType::T_VOID:
|
||||
// XXX implement void*
|
||||
// XXX implement void* ?
|
||||
NS_ASSERTION(0,"void* params not supported");
|
||||
return JS_FALSE;
|
||||
|
||||
case nsXPTType::T_IID:
|
||||
// XXX implement IID
|
||||
NS_ASSERTION(0,"iid params not supported");
|
||||
return JS_FALSE;
|
||||
{
|
||||
nsID* iid = *((nsID**)s);
|
||||
if(!iid)
|
||||
break;
|
||||
JSObject* obj;
|
||||
if(!(obj = xpc_NewIDObject(cx, *iid)))
|
||||
break;
|
||||
*d = OBJECT_TO_JSVAL(obj);
|
||||
break;
|
||||
}
|
||||
|
||||
case nsXPTType::T_BSTR:
|
||||
// XXX implement BSTR
|
||||
NS_ASSERTION(0,"string params not supported");
|
||||
// XXX implement BSTR ?
|
||||
NS_ASSERTION(0,"'BSTR' string params not supported");
|
||||
return JS_FALSE;
|
||||
|
||||
case nsXPTType::T_CHAR_STR:
|
||||
// XXX implement CHAR_STR
|
||||
NS_ASSERTION(0,"string params not supported");
|
||||
return JS_FALSE;
|
||||
{
|
||||
char* p = *((char**)s);
|
||||
if(!p)
|
||||
break;
|
||||
JSString* str;
|
||||
if(!(str = JS_NewStringCopyZ(cx, p)))
|
||||
break;
|
||||
*d = STRING_TO_JSVAL(str);
|
||||
break;
|
||||
}
|
||||
|
||||
case nsXPTType::T_WCHAR_STR:
|
||||
// XXX implement WCHAR_STR
|
||||
NS_ASSERTION(0,"string params not supported");
|
||||
return JS_FALSE;
|
||||
{
|
||||
jschar* p = *((jschar**)s);
|
||||
if(!p)
|
||||
break;
|
||||
JSString* str;
|
||||
if(!(str = JS_NewUCStringCopyZ(cx, p)))
|
||||
break;
|
||||
*d = STRING_TO_JSVAL(str);
|
||||
break;
|
||||
}
|
||||
|
||||
case nsXPTType::T_INTERFACE:
|
||||
// XXX implement INTERFACE
|
||||
// make sure 'src' is an object
|
||||
// get the nsIInterfaceInfo* from the param and
|
||||
// build a wrapper and then hand over the wrapper.
|
||||
// XXX remember to release the wrapper in cleanup below
|
||||
NS_ASSERTION(0,"interface params not supported");
|
||||
return JS_FALSE;
|
||||
case nsXPTType::T_INTERFACE_IS:
|
||||
// XXX implement INTERFACE_IS
|
||||
NS_ASSERTION(0,"interface_is params not supported");
|
||||
return JS_FALSE;
|
||||
{
|
||||
nsISupports* iface = *((nsISupports**)s);
|
||||
if(!iface)
|
||||
break;
|
||||
JSObject* aJSObj;
|
||||
// is this a wrapped JS object?
|
||||
if(nsXPCWrappedJSClass::IsWrappedJS(iface))
|
||||
{
|
||||
nsIXPConnectWrappedJSMethods* methods;
|
||||
if(NS_SUCCEEDED(iface->QueryInterface(kWrappedJSMethodsIID,
|
||||
(void**)&methods)) &&
|
||||
NS_SUCCEEDED(methods->GetJSObject(&aJSObj)))
|
||||
{
|
||||
NS_RELEASE(methods);
|
||||
*d = OBJECT_TO_JSVAL(aJSObj);
|
||||
}
|
||||
}
|
||||
else
|
||||
{
|
||||
// we need to build a wrapper
|
||||
nsXPCWrappedNative* wrapper;
|
||||
XPCContext* xpcc;
|
||||
if(!iid || !(xpcc = nsXPConnect::GetContext(cx)) ||
|
||||
!(wrapper = nsXPCWrappedNative::GetNewOrUsedWrapper(xpcc,
|
||||
iface, *iid)))
|
||||
{
|
||||
break;
|
||||
}
|
||||
aJSObj = wrapper->GetJSObject();
|
||||
NS_RELEASE(wrapper);
|
||||
if(aJSObj)
|
||||
*d = OBJECT_TO_JSVAL(aJSObj);
|
||||
}
|
||||
|
||||
break;
|
||||
}
|
||||
default:
|
||||
NS_ASSERTION(0, "bad type");
|
||||
return JS_FALSE;
|
||||
|
@ -251,10 +309,10 @@ XPCConvert::NativeData2JS(jsval* d, const void* s,
|
|||
return JS_TRUE;
|
||||
}
|
||||
|
||||
// static
|
||||
// static
|
||||
JSBool
|
||||
XPCConvert::JSData2Native(JSContext* cx, void* d, jsval s,
|
||||
const nsXPTType& type,
|
||||
const nsXPTType& type,
|
||||
nsIAllocator* al, const nsID* iid)
|
||||
{
|
||||
NS_PRECONDITION(d, "bad param");
|
||||
|
@ -430,17 +488,47 @@ XPCConvert::JSData2Native(JSContext* cx, void* d, jsval s,
|
|||
}
|
||||
|
||||
case nsXPTType::T_INTERFACE:
|
||||
// XXX implement INTERFACE
|
||||
// make sure 'src' is an object
|
||||
// get the nsIInterfaceInfo* from the param and
|
||||
// build a wrapper and then hand over the wrapper.
|
||||
// XXX remember to release the wrapper in cleanup below
|
||||
NS_ASSERTION(0,"interface params not supported");
|
||||
return JS_FALSE;
|
||||
case nsXPTType::T_INTERFACE_IS:
|
||||
// XXX implement INTERFACE_IS
|
||||
NS_ASSERTION(0,"interface_is params not supported");
|
||||
{
|
||||
NS_ASSERTION(iid,"can't do interface conversions without iid");
|
||||
JSObject* obj;
|
||||
nsISupports* iface = NULL;
|
||||
|
||||
// only wrpa JSObjects
|
||||
if(!JSVAL_IS_OBJECT(s) ||
|
||||
(!(obj = JSVAL_TO_OBJECT(s))))
|
||||
{
|
||||
// XXX should report error
|
||||
return JS_FALSE;
|
||||
}
|
||||
|
||||
// is this really a native xpcom object with a wrapper?
|
||||
nsXPCWrappedNative* wrapper;
|
||||
if(NULL != (wrapper =
|
||||
nsXPCWrappedNativeClass::GetWrappedNativeOfJSObject(cx,obj)))
|
||||
{
|
||||
iface = wrapper->GetNative();
|
||||
// is the underlying object the right interface?
|
||||
if(wrapper->GetIID().Equals(*iid))
|
||||
NS_ADDREF(iface);
|
||||
else
|
||||
iface->QueryInterface(*iid, (void**)&iface);
|
||||
}
|
||||
else
|
||||
{
|
||||
// lets try to build a wrapper around the JSObject
|
||||
XPCContext* xpcc;
|
||||
if(NULL != (xpcc = nsXPConnect::GetContext(cx)))
|
||||
iface = nsXPCWrappedJS::GetNewOrUsedWrapper(xpcc, obj, *iid);
|
||||
}
|
||||
if(iface)
|
||||
{
|
||||
// one AddRef has already been done
|
||||
*((nsISupports**)d) = iface;
|
||||
return JS_TRUE;
|
||||
}
|
||||
return JS_FALSE;
|
||||
}
|
||||
default:
|
||||
NS_ASSERTION(0, "bad type");
|
||||
return JS_FALSE;
|
||||
|
|
|
@ -215,4 +215,4 @@ xpc_JSObjectToID(JSContext *cx, JSObject* obj)
|
|||
return NULL;
|
||||
|
||||
return &data->GetID();
|
||||
}
|
||||
}
|
||||
|
|
|
@ -68,8 +68,8 @@ public:
|
|||
static nsXPConnect* GetXPConnect();
|
||||
static nsIAllocator* GetAllocator(nsXPConnect* xpc = NULL);
|
||||
static nsIInterfaceInfoManager* GetInterfaceInfoManager(nsXPConnect* xpc = NULL);
|
||||
static XPCContext* GetContext(JSContext* cx, nsXPConnect* xpc = NULL);
|
||||
|
||||
XPCContext* GetContext(JSContext* cx);
|
||||
JSContext2XPCContextMap* GetContextMap() {return mContextMap;}
|
||||
nsIXPCScriptable* GetArbitraryScriptable() {return mArbitraryScriptable;}
|
||||
|
||||
|
@ -144,26 +144,6 @@ class nsIXPCWrappedJSClass : public nsISupports
|
|||
|
||||
/*************************/
|
||||
|
||||
// nsXPCWrappedJSClass maintains an array of these things
|
||||
class XPCJSMemberDescriptor
|
||||
{
|
||||
private:
|
||||
enum {
|
||||
// these are all bitwise flags!
|
||||
JSMD_REFLECTABLE = 0x1
|
||||
};
|
||||
|
||||
public:
|
||||
JSBool IsReflectable() const {return flags & JSMD_REFLECTABLE;}
|
||||
void SetReflectable(JSBool b) {if(b) flags |= JSMD_REFLECTABLE;
|
||||
else flags &= ~JSMD_REFLECTABLE;}
|
||||
XPCJSMemberDescriptor(){}
|
||||
private:
|
||||
uint16 flags;
|
||||
};
|
||||
|
||||
/*************************/
|
||||
|
||||
class nsXPCWrappedJSClass : public nsIXPCWrappedJSClass
|
||||
{
|
||||
// all the interface method declarations...
|
||||
|
@ -177,7 +157,7 @@ public:
|
|||
nsIInterfaceInfo* GetInterfaceInfo() const {return mInfo;}
|
||||
|
||||
static JSBool InitForContext(XPCContext* xpcc);
|
||||
JSBool IsWrappedJS(nsISupports* aPtr);
|
||||
static JSBool IsWrappedJS(nsISupports* aPtr);
|
||||
|
||||
NS_IMETHOD DelegatedQueryInterface(nsXPCWrappedJS* self, REFNSIID aIID,
|
||||
void** aInstancePtr);
|
||||
|
@ -200,9 +180,9 @@ private:
|
|||
|
||||
JSObject* CallQueryInterfaceOnJSObject(JSObject* jsobj, REFNSIID aIID);
|
||||
|
||||
JSBool IsReflectable(uint16 i) const
|
||||
JSBool IsReflectable(uint16 i) const
|
||||
{return mDescriptors[i/32] & (1 << (i%32));}
|
||||
void SetReflectable(uint16 i, JSBool b)
|
||||
void SetReflectable(uint16 i, JSBool b)
|
||||
{if(b) mDescriptors[i/32] |= (1 << (i%32));
|
||||
else mDescriptors[i/32] &= ~(1 << (i%32));}
|
||||
|
||||
|
@ -276,7 +256,7 @@ private:
|
|||
// these are all bitwise flags!
|
||||
NMD_CONSTANT = 0x0, // categories...
|
||||
NMD_METHOD = 0x1,
|
||||
NMD_ATTRIB_RO = 0x2,
|
||||
NMD_ATTRIB_RO = 0x2,
|
||||
NMD_ATTRIB_RW = 0x3,
|
||||
NMD_CAT_MASK = 0x3, // & mask for the categories above
|
||||
// any new bits start at 0x04
|
||||
|
@ -351,7 +331,8 @@ public:
|
|||
|
||||
const XPCNativeMemberDescriptor* LookupMemberByID(jsid id) const;
|
||||
|
||||
JSBool GetConstantAsJSVal(nsXPCWrappedNative* wrapper,
|
||||
JSBool GetConstantAsJSVal(JSContext* cx,
|
||||
nsXPCWrappedNative* wrapper,
|
||||
const XPCNativeMemberDescriptor* desc,
|
||||
jsval* vp);
|
||||
|
||||
|
@ -409,15 +390,6 @@ private:
|
|||
|
||||
/*************************/
|
||||
|
||||
class nsXPCArbitraryScriptable : public nsIXPCScriptable
|
||||
{
|
||||
public:
|
||||
// all the interface method declarations...
|
||||
NS_DECL_ISUPPORTS;
|
||||
XPC_DECLARE_IXPCSCRIPTABLE;
|
||||
nsXPCArbitraryScriptable() {NS_INIT_REFCNT();NS_ADDREF_THIS();}
|
||||
};
|
||||
|
||||
class nsXPCWrappedNative : public nsIXPConnectWrappedNative
|
||||
{
|
||||
// all the interface method declarations...
|
||||
|
@ -465,6 +437,17 @@ private:
|
|||
nsXPCWrappedNative* mNext;
|
||||
};
|
||||
|
||||
/***************************************************************************/
|
||||
|
||||
class nsXPCArbitraryScriptable : public nsIXPCScriptable
|
||||
{
|
||||
public:
|
||||
// all the interface method declarations...
|
||||
NS_DECL_ISUPPORTS;
|
||||
XPC_DECLARE_IXPCSCRIPTABLE;
|
||||
nsXPCArbitraryScriptable() {NS_INIT_REFCNT();NS_ADDREF_THIS();}
|
||||
};
|
||||
|
||||
/***************************************************************************/
|
||||
// nsID JavaScript class functions
|
||||
|
||||
|
@ -486,11 +469,11 @@ class XPCConvert
|
|||
public:
|
||||
static JSBool IsMethodReflectable(const nsXPTMethodInfo& info);
|
||||
|
||||
static JSBool NativeData2JS(jsval* d, const void* s,
|
||||
const nsXPTType& type);
|
||||
static JSBool NativeData2JS(JSContext* cx, jsval* d, const void* s,
|
||||
const nsXPTType& type, const nsID* iid);
|
||||
|
||||
static JSBool JSData2Native(JSContext* cx, void* d, jsval s,
|
||||
const nsXPTType& type,
|
||||
const nsXPTType& type,
|
||||
nsIAllocator* al, const nsID* iid);
|
||||
private:
|
||||
XPCConvert(); // not implemented
|
||||
|
|
|
@ -57,13 +57,15 @@ struct nsXPCVariant : public nsXPCMiniVariant
|
|||
|
||||
enum
|
||||
{
|
||||
PTR_IS_DATA = 0x1, // used for OUT params of Arithmetic types,
|
||||
// ptr points to data in val
|
||||
VAL_IS_OWNED = 0x2 // val.p holds an alloced ptr that must be freed
|
||||
// these are bitflags!
|
||||
PTR_IS_DATA = 0x1, // ptr points to 'real' data in val
|
||||
VAL_IS_OWNED = 0x2, // val.p holds alloced ptr that must be freed
|
||||
VAL_IS_IFACE = 0x4 // val.p holds interface ptr that must be released
|
||||
};
|
||||
|
||||
JSBool IsPtrData() const {return (JSBool) (flags & PTR_IS_DATA);}
|
||||
JSBool IsValOwned() const {return (JSBool) (flags & VAL_IS_OWNED);}
|
||||
JSBool IsPtrData() const {return (JSBool) (flags & PTR_IS_DATA);}
|
||||
JSBool IsValOwned() const {return (JSBool) (flags & VAL_IS_OWNED);}
|
||||
JSBool IsValInterface() const {return (JSBool) (flags & VAL_IS_IFACE);}
|
||||
};
|
||||
|
||||
#endif /* xpcvariant_h___ */
|
||||
|
|
|
@ -97,7 +97,7 @@ nsXPCWrappedJSClass::nsXPCWrappedJSClass(XPCContext* xpcc, REFNSIID aIID,
|
|||
mDescriptors = NULL;
|
||||
break;
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
else
|
||||
|
@ -110,7 +110,7 @@ nsXPCWrappedJSClass::nsXPCWrappedJSClass(XPCContext* xpcc, REFNSIID aIID,
|
|||
nsXPCWrappedJSClass::~nsXPCWrappedJSClass()
|
||||
{
|
||||
if(mDescriptors && mDescriptors != &zero_methods_descriptor)
|
||||
delete [] mDescriptors;
|
||||
delete [] mDescriptors;
|
||||
mXPCContext->GetWrappedJSClassMap()->Remove(this);
|
||||
NS_RELEASE(mInfo);
|
||||
}
|
||||
|
@ -195,6 +195,7 @@ public:
|
|||
|
||||
/***************************************************************************/
|
||||
|
||||
// static
|
||||
JSBool
|
||||
nsXPCWrappedJSClass::IsWrappedJS(nsISupports* aPtr)
|
||||
{
|
||||
|
@ -317,7 +318,7 @@ nsXPCWrappedJSClass::CallMethod(nsXPCWrappedJS* wrapper, uint16 methodIndex,
|
|||
if(type.IsPointer())
|
||||
pv = (nsXPCMiniVariant*) pv->val.p;
|
||||
|
||||
if(!XPCConvert::NativeData2JS(&val, &pv->val, type))
|
||||
if(!XPCConvert::NativeData2JS(cx, &val, &pv->val, type, NULL))
|
||||
{
|
||||
retval = NS_ERROR_FAILURE;
|
||||
goto done;
|
||||
|
|
|
@ -307,7 +307,8 @@ nsXPCWrappedNativeClass::GetInterfaceName()
|
|||
}
|
||||
|
||||
JSBool
|
||||
nsXPCWrappedNativeClass::GetConstantAsJSVal(nsXPCWrappedNative* wrapper,
|
||||
nsXPCWrappedNativeClass::GetConstantAsJSVal(JSContext *cx,
|
||||
nsXPCWrappedNative* wrapper,
|
||||
const XPCNativeMemberDescriptor* desc,
|
||||
jsval* vp)
|
||||
{
|
||||
|
@ -328,7 +329,8 @@ nsXPCWrappedNativeClass::GetConstantAsJSVal(nsXPCWrappedNative* wrapper,
|
|||
v.type = constant->GetType();
|
||||
memcpy(&v.val, &mv.val, sizeof(mv.val));
|
||||
|
||||
return XPCConvert::NativeData2JS(vp, &v.val, v.type);
|
||||
// XXX if iid consts are supported, then coditionally fill it in here
|
||||
return XPCConvert::NativeData2JS(cx, vp, &v.val, v.type, NULL);
|
||||
}
|
||||
|
||||
void
|
||||
|
@ -362,7 +364,7 @@ nsXPCWrappedNativeClass::CallWrappedMethod(nsXPCWrappedNative* wrapper,
|
|||
uint8 vtblIndex;
|
||||
nsresult invokeResult;
|
||||
nsIAllocator* al = NULL;
|
||||
|
||||
|
||||
*vp = JSVAL_NULL;
|
||||
|
||||
if(!(al = nsXPConnect::GetAllocator()))
|
||||
|
@ -443,8 +445,12 @@ nsXPCWrappedNativeClass::CallWrappedMethod(nsXPCWrappedNative* wrapper,
|
|||
if(!param.IsIn())
|
||||
continue;
|
||||
|
||||
// in the future there may be a param flag indicating 'stingy'
|
||||
if(type.IsPointer())
|
||||
{
|
||||
conditional_al = al;
|
||||
dp->flags |= nsXPCVariant::VAL_IS_OWNED;
|
||||
}
|
||||
}
|
||||
else
|
||||
{
|
||||
|
@ -458,14 +464,33 @@ nsXPCWrappedNativeClass::CallWrappedMethod(nsXPCWrappedNative* wrapper,
|
|||
|
||||
if(type.TagPart() == nsXPTType::T_INTERFACE)
|
||||
{
|
||||
// XXX get the iid
|
||||
dp->flags |= nsXPCVariant::VAL_IS_IFACE;
|
||||
|
||||
if(!(conditional_iid = param.GetInterfaceIID()))
|
||||
{
|
||||
// XXX this (and others!) should throw rather than report error
|
||||
ReportError(desc, "could not get interface type");
|
||||
goto done;
|
||||
}
|
||||
}
|
||||
else if(type.TagPart() == nsXPTType::T_INTERFACE_IS)
|
||||
{
|
||||
// XXX get the iid
|
||||
dp->flags |= nsXPCVariant::VAL_IS_IFACE;
|
||||
|
||||
uint8 arg_num = param.GetInterfaceIsArgNumber();
|
||||
const nsXPTParamInfo& param = info->GetParam(arg_num);
|
||||
const nsXPTType& type = param.GetType();
|
||||
if(!type.IsPointer() || type.TagPart() != nsXPTType::T_IID ||
|
||||
!XPCConvert::JSData2Native(cx, &conditional_iid, argv[arg_num],
|
||||
type, NULL, NULL))
|
||||
{
|
||||
// XXX this (and others!) should throw rather than report error
|
||||
ReportError(desc, "could not get interface type");
|
||||
goto done;
|
||||
}
|
||||
}
|
||||
|
||||
if(!XPCConvert::JSData2Native(cx, &dp->val, src, type,
|
||||
if(!XPCConvert::JSData2Native(cx, &dp->val, src, type,
|
||||
conditional_al, conditional_iid))
|
||||
{
|
||||
NS_ASSERTION(0, "bad type");
|
||||
|
@ -489,13 +514,38 @@ nsXPCWrappedNativeClass::CallWrappedMethod(nsXPCWrappedNative* wrapper,
|
|||
{
|
||||
const nsXPTParamInfo& param = info->GetParam(i);
|
||||
const nsXPTType& type = param.GetType();
|
||||
nsID* conditional_iid = NULL;
|
||||
|
||||
nsXPCVariant* dp = &dispatchParams[i];
|
||||
if(param.IsOut())
|
||||
{
|
||||
jsval v;
|
||||
|
||||
if(!XPCConvert::NativeData2JS(&v, &dp->val, type))
|
||||
if(type.TagPart() == nsXPTType::T_INTERFACE)
|
||||
{
|
||||
if(!(conditional_iid = param.GetInterfaceIID()))
|
||||
{
|
||||
// XXX this (and others!) should throw rather than report error
|
||||
ReportError(desc, "could not get interface type");
|
||||
goto done;
|
||||
}
|
||||
}
|
||||
else if(type.TagPart() == nsXPTType::T_INTERFACE_IS)
|
||||
{
|
||||
uint8 arg_num = param.GetInterfaceIsArgNumber();
|
||||
const nsXPTParamInfo& param = info->GetParam(arg_num);
|
||||
const nsXPTType& type = param.GetType();
|
||||
if(!type.IsPointer() || type.TagPart() != nsXPTType::T_IID ||
|
||||
!(conditional_iid = (nsID*)dispatchParams[arg_num].val.p))
|
||||
{
|
||||
// XXX this (and others!) should throw rather than report error
|
||||
ReportError(desc, "could not get interface type");
|
||||
goto done;
|
||||
}
|
||||
}
|
||||
|
||||
if(!XPCConvert::NativeData2JS(cx, &v, &dp->val, type,
|
||||
conditional_iid))
|
||||
{
|
||||
retval = NS_ERROR_FAILURE;
|
||||
goto done;
|
||||
|
@ -524,12 +574,11 @@ done:
|
|||
{
|
||||
nsXPCVariant* dp = &dispatchParams[i];
|
||||
void* p = dp->val.p;
|
||||
// XXX verify that ALL this this stuff is right
|
||||
if(!p)
|
||||
continue;
|
||||
if(dp->flags & nsXPCVariant::VAL_IS_OWNED)
|
||||
delete [] p;
|
||||
else if(info->GetParam(i).GetType() == nsXPTType::T_INTERFACE)
|
||||
if(dp->IsValOwned() && al)
|
||||
al->Free(p);
|
||||
if(dp->IsValInterface())
|
||||
((nsISupports*)p)->Release();
|
||||
}
|
||||
|
||||
|
@ -619,7 +668,7 @@ WrappedNative_GetProperty(JSContext *cx, JSObject *obj, jsid id, jsval *vp)
|
|||
if(desc)
|
||||
{
|
||||
if(desc->IsConstant())
|
||||
return clazz->GetConstantAsJSVal(wrapper, desc, vp);
|
||||
return clazz->GetConstantAsJSVal(cx, wrapper, desc, vp);
|
||||
else if(desc->IsMethod())
|
||||
{
|
||||
// allow for lazy creation of 'prototypical' function invoke object
|
||||
|
|
|
@ -168,6 +168,13 @@ nsXPTParamInfo::GetInterface() const
|
|||
return info;
|
||||
}
|
||||
|
||||
nsIID*
|
||||
nsXPTParamInfo::GetInterfaceIID() const
|
||||
{
|
||||
NS_PRECONDITION(GetType() == nsXPTType::T_INTERFACE,"not an interface");
|
||||
return &InterfaceDirectoryEntryTable[type.type.interface].iid;
|
||||
}
|
||||
|
||||
/***************************************************************************/
|
||||
// VERY simple implementations...
|
||||
|
||||
|
@ -179,8 +186,8 @@ XPT_GetInterfaceInfoManager()
|
|||
return InterfaceInfoManagerImpl::GetInterfaceInfoManager();
|
||||
}
|
||||
|
||||
// static
|
||||
InterfaceInfoManagerImpl*
|
||||
// static
|
||||
InterfaceInfoManagerImpl*
|
||||
InterfaceInfoManagerImpl::GetInterfaceInfoManager()
|
||||
{
|
||||
static InterfaceInfoManagerImpl* impl = NULL;
|
||||
|
@ -192,10 +199,10 @@ InterfaceInfoManagerImpl::GetInterfaceInfoManager()
|
|||
if(impl)
|
||||
NS_ADDREF(impl);
|
||||
return impl;
|
||||
}
|
||||
}
|
||||
|
||||
// static
|
||||
nsIAllocator*
|
||||
// static
|
||||
nsIAllocator*
|
||||
InterfaceInfoManagerImpl::GetAllocator(InterfaceInfoManagerImpl* iim /*= NULL*/)
|
||||
{
|
||||
nsIAllocator* al;
|
||||
|
@ -208,7 +215,7 @@ InterfaceInfoManagerImpl::GetAllocator(InterfaceInfoManagerImpl* iim /*= NULL*/)
|
|||
if(!iim)
|
||||
NS_RELEASE(iiml);
|
||||
return al;
|
||||
}
|
||||
}
|
||||
|
||||
|
||||
static NS_DEFINE_IID(kAllocatorCID, NS_ALLOCATOR_CID);
|
||||
|
@ -228,17 +235,17 @@ InterfaceInfoManagerImpl::InterfaceInfoManagerImpl()
|
|||
nsServiceManager::GetService(kAllocatorCID,
|
||||
kIAllocatorIID,
|
||||
(nsISupports **)&mAllocator);
|
||||
}
|
||||
}
|
||||
|
||||
InterfaceInfoManagerImpl::~InterfaceInfoManagerImpl()
|
||||
{
|
||||
// let the singleton leak
|
||||
}
|
||||
}
|
||||
|
||||
PRBool
|
||||
PRBool
|
||||
InterfaceInfoManagerImpl::BuildInterfaceForEntry(uint16 i)
|
||||
{
|
||||
XPTInterfaceDirectoryEntry *parent_interface =
|
||||
XPTInterfaceDirectoryEntry *parent_interface =
|
||||
InterfaceDirectoryEntryTable[i].interface_descriptor->parent_interface;
|
||||
uint16 parent_index = 0;
|
||||
|
||||
|
@ -252,7 +259,7 @@ InterfaceInfoManagerImpl::BuildInterfaceForEntry(uint16 i)
|
|||
parent_interface ?
|
||||
mInfoArray[parent_index] : NULL);
|
||||
return (PRBool) mInfoArray[i];
|
||||
}
|
||||
}
|
||||
|
||||
NS_IMETHODIMP
|
||||
InterfaceInfoManagerImpl::GetInfoForIID(const nsIID* iid, nsIInterfaceInfo** info)
|
||||
|
@ -263,7 +270,7 @@ InterfaceInfoManagerImpl::GetInfoForIID(const nsIID* iid, nsIInterfaceInfo** inf
|
|||
if(iid->Equals(entry->iid))
|
||||
{
|
||||
if(!mInfoArray[i] && !BuildInterfaceForEntry(i))
|
||||
break;
|
||||
break;
|
||||
*info = mInfoArray[i];
|
||||
NS_ADDREF(*info);
|
||||
return NS_OK;
|
||||
|
@ -282,7 +289,7 @@ InterfaceInfoManagerImpl::GetInfoForName(const char* name, nsIInterfaceInfo** in
|
|||
if(!strcmp(name, entry->name))
|
||||
{
|
||||
if(!mInfoArray[i] && !BuildInterfaceForEntry(i))
|
||||
break;
|
||||
break;
|
||||
*info = mInfoArray[i];
|
||||
NS_ADDREF(*info);
|
||||
return NS_OK;
|
||||
|
@ -338,7 +345,7 @@ NS_IMPL_ISUPPORTS(InterfaceInfoImpl, NS_IINTERFACEINFO_IID)
|
|||
|
||||
InterfaceInfoImpl::InterfaceInfoImpl(XPTInterfaceDirectoryEntry* entry,
|
||||
InterfaceInfoImpl* parent)
|
||||
: mEntry(entry),
|
||||
: mEntry(entry),
|
||||
mParent(parent)
|
||||
{
|
||||
NS_INIT_REFCNT();
|
||||
|
@ -349,7 +356,7 @@ InterfaceInfoImpl::InterfaceInfoImpl(XPTInterfaceDirectoryEntry* entry,
|
|||
{
|
||||
mMethodBaseIndex = mParent->mMethodBaseIndex + mParent->mMethodCount;
|
||||
mConstantBaseIndex = mParent->mConstantBaseIndex + mParent->mConstantCount;
|
||||
}
|
||||
}
|
||||
else
|
||||
mMethodBaseIndex = mConstantBaseIndex = 0;
|
||||
|
||||
|
@ -361,7 +368,7 @@ InterfaceInfoImpl::~InterfaceInfoImpl()
|
|||
{
|
||||
if(mParent)
|
||||
NS_RELEASE(mParent);
|
||||
}
|
||||
}
|
||||
|
||||
NS_IMETHODIMP
|
||||
InterfaceInfoImpl::GetName(char** name)
|
||||
|
@ -381,10 +388,10 @@ InterfaceInfoImpl::GetName(char** name)
|
|||
return NS_OK;
|
||||
}
|
||||
}
|
||||
|
||||
|
||||
*name = NULL;
|
||||
return NS_ERROR_FAILURE;
|
||||
}
|
||||
}
|
||||
|
||||
NS_IMETHODIMP
|
||||
InterfaceInfoImpl::GetIID(nsIID** iid)
|
||||
|
@ -403,7 +410,7 @@ InterfaceInfoImpl::GetIID(nsIID** iid)
|
|||
return NS_OK;
|
||||
}
|
||||
}
|
||||
|
||||
|
||||
*iid = NULL;
|
||||
return NS_ERROR_FAILURE;
|
||||
}
|
||||
|
@ -436,7 +443,7 @@ InterfaceInfoImpl::GetConstantCount(uint16* count)
|
|||
NS_PRECONDITION(count, "bad param");
|
||||
*count = mConstantBaseIndex + mConstantCount;
|
||||
return NS_OK;
|
||||
|
||||
|
||||
}
|
||||
|
||||
NS_IMETHODIMP
|
||||
|
@ -456,7 +463,7 @@ InterfaceInfoImpl::GetMethodInfo(uint16 index, const nsXPTMethodInfo** info)
|
|||
// else...
|
||||
*info = NS_STATIC_CAST(nsXPTMethodInfo*, &mEntry->interface_descriptor->method_descriptors[index-mMethodBaseIndex]);
|
||||
return NS_OK;
|
||||
|
||||
|
||||
}
|
||||
|
||||
NS_IMETHODIMP
|
||||
|
|
|
@ -30,7 +30,7 @@ class nsXPTType : public XPTTypeDescriptorPrefix
|
|||
{
|
||||
// NO DATA - this a flyweight wrapper
|
||||
public:
|
||||
nsXPTType()
|
||||
nsXPTType()
|
||||
{} // random contents
|
||||
nsXPTType(const XPTTypeDescriptorPrefix& prefix)
|
||||
{*(XPTTypeDescriptorPrefix*)this = prefix;}
|
||||
|
@ -38,10 +38,10 @@ public:
|
|||
nsXPTType(const uint8& prefix)
|
||||
{*(uint8*)this = prefix;}
|
||||
|
||||
nsXPTType& operator=(uint8 val)
|
||||
nsXPTType& operator=(uint8 val)
|
||||
{flags = val; return *this;}
|
||||
|
||||
operator uint8() const
|
||||
operator uint8() const
|
||||
{return flags;}
|
||||
|
||||
JSBool IsPointer() const
|
||||
|
@ -57,7 +57,7 @@ public:
|
|||
{return flags <= T_WCHAR;}
|
||||
|
||||
JSBool IsInterfacePointer() const
|
||||
{return (JSBool) (TagPart() == T_INTERFACE ||
|
||||
{return (JSBool) (TagPart() == T_INTERFACE ||
|
||||
TagPart() == T_INTERFACE_IS);}
|
||||
|
||||
uint8 TagPart() const
|
||||
|
@ -117,6 +117,9 @@ public:
|
|||
// find (or build) the appropriate nsIInterfaceInfo. Simple :)
|
||||
nsIInterfaceInfo* GetInterface() const ;
|
||||
|
||||
// a *little* simpler than the above
|
||||
nsIID* GetInterfaceIID() const ;
|
||||
|
||||
private:
|
||||
nsXPTParamInfo(); // no implementation
|
||||
// NO DATA - this a flyweight wrapper
|
||||
|
@ -141,7 +144,7 @@ public:
|
|||
NS_PRECONDITION(index < GetParamCount(),"bad arg");
|
||||
return params[index];
|
||||
}
|
||||
const nsXPTParamInfo GetResult() const
|
||||
const nsXPTParamInfo GetResult() const
|
||||
{return *result;}
|
||||
private:
|
||||
nsXPTMethodInfo(); // no implementation
|
||||
|
@ -159,14 +162,14 @@ public:
|
|||
nsXPTConstant(const XPTConstDescriptor& desc)
|
||||
{*(XPTConstDescriptor*)this = desc;}
|
||||
|
||||
const char* GetName() const
|
||||
const char* GetName() const
|
||||
{return name;}
|
||||
|
||||
const nsXPTType GetType() const
|
||||
{return type.prefix;}
|
||||
|
||||
// XXX this is ugly
|
||||
const nsXPCMiniVariant* GetValue() const
|
||||
const nsXPCMiniVariant* GetValue() const
|
||||
{return (nsXPCMiniVariant*) &value;}
|
||||
private:
|
||||
nsXPTConstant(); // no implementation
|
||||
|
|
Загрузка…
Ссылка в новой задаче