зеркало из https://github.com/mozilla/pjs.git
Bug 592352 - 'Assertbotch on shutdown after IDB solo mochitest -- leaked contexts?'. r=bent.
This commit is contained in:
Родитель
1f39e2f2b2
Коммит
a31f48ade7
|
@ -255,7 +255,7 @@ IDBCursor::IDBCursor()
|
|||
: mDirection(nsIIDBCursor::NEXT),
|
||||
mCachedValue(JSVAL_VOID),
|
||||
mHaveCachedValue(false),
|
||||
mJSRuntime(nsnull),
|
||||
mValueRooted(false),
|
||||
mContinueCalled(false),
|
||||
mDataIndex(0),
|
||||
mType(OBJECTSTORE)
|
||||
|
@ -267,8 +267,8 @@ IDBCursor::~IDBCursor()
|
|||
{
|
||||
NS_ASSERTION(NS_IsMainThread(), "Wrong thread!");
|
||||
|
||||
if (mJSRuntime) {
|
||||
js_RemoveRoot(mJSRuntime, &mCachedValue);
|
||||
if (mValueRooted) {
|
||||
NS_DROP_JS_OBJECTS(this, IDBCursor);
|
||||
}
|
||||
|
||||
if (mListenerManager) {
|
||||
|
@ -280,18 +280,38 @@ NS_IMPL_CYCLE_COLLECTION_CLASS(IDBCursor)
|
|||
|
||||
NS_IMPL_CYCLE_COLLECTION_TRAVERSE_BEGIN_INHERITED(IDBCursor,
|
||||
nsDOMEventTargetHelper)
|
||||
NS_IMPL_CYCLE_COLLECTION_TRAVERSE_SCRIPT_OBJECTS
|
||||
NS_IMPL_CYCLE_COLLECTION_TRAVERSE_NSCOMPTR_AMBIGUOUS(mRequest,
|
||||
nsPIDOMEventTarget)
|
||||
NS_IMPL_CYCLE_COLLECTION_TRAVERSE_NSCOMPTR_AMBIGUOUS(mTransaction,
|
||||
nsPIDOMEventTarget)
|
||||
NS_IMPL_CYCLE_COLLECTION_TRAVERSE_NSCOMPTR_AMBIGUOUS(mObjectStore,
|
||||
nsPIDOMEventTarget)
|
||||
NS_IMPL_CYCLE_COLLECTION_TRAVERSE_NSCOMPTR_AMBIGUOUS(mIndex,
|
||||
nsPIDOMEventTarget)
|
||||
NS_IMPL_CYCLE_COLLECTION_TRAVERSE_NSCOMPTR_AMBIGUOUS(mTransaction,
|
||||
nsPIDOMEventTarget)
|
||||
NS_IMPL_CYCLE_COLLECTION_TRAVERSE_NSCOMPTR(mOnErrorListener)
|
||||
NS_IMPL_CYCLE_COLLECTION_TRAVERSE_END
|
||||
|
||||
NS_IMPL_CYCLE_COLLECTION_ROOT_BEGIN(IDBCursor)
|
||||
if (tmp->mValueRooted) {
|
||||
NS_DROP_JS_OBJECTS(tmp, IDBCursor);
|
||||
tmp->mCachedValue = JSVAL_VOID;
|
||||
tmp->mHaveCachedValue = false;
|
||||
tmp->mValueRooted = false;
|
||||
}
|
||||
NS_IMPL_CYCLE_COLLECTION_ROOT_END
|
||||
|
||||
NS_IMPL_CYCLE_COLLECTION_TRACE_BEGIN(IDBCursor)
|
||||
if (JSVAL_IS_GCTHING(tmp->mCachedValue)) {
|
||||
void *gcThing = JSVAL_TO_GCTHING(tmp->mCachedValue);
|
||||
NS_IMPL_CYCLE_COLLECTION_TRACE_JS_CALLBACK(gcThing)
|
||||
}
|
||||
NS_IMPL_CYCLE_COLLECTION_TRACE_END
|
||||
|
||||
NS_IMPL_CYCLE_COLLECTION_UNLINK_BEGIN_INHERITED(IDBCursor,
|
||||
nsDOMEventTargetHelper)
|
||||
// Don't unlink mObjectStore, mIndex, or mTransaction!
|
||||
NS_IMPL_CYCLE_COLLECTION_UNLINK_NSCOMPTR(mRequest)
|
||||
NS_IMPL_CYCLE_COLLECTION_UNLINK_NSCOMPTR(mOnErrorListener)
|
||||
NS_IMPL_CYCLE_COLLECTION_UNLINK_END
|
||||
|
||||
|
@ -377,19 +397,15 @@ IDBCursor::GetValue(JSContext* aCx,
|
|||
if (!mHaveCachedValue) {
|
||||
JSAutoRequest ar(aCx);
|
||||
|
||||
if (!mJSRuntime) {
|
||||
JSRuntime* rt = JS_GetRuntime(aCx);
|
||||
JSBool ok = js_AddRootRT(rt, &mCachedValue,
|
||||
"IDBCursor::mCachedValue");
|
||||
NS_ENSURE_TRUE(ok, NS_ERROR_FAILURE);
|
||||
|
||||
mJSRuntime = rt;
|
||||
}
|
||||
|
||||
nsCOMPtr<nsIJSON> json(new nsJSON());
|
||||
rv = json->DecodeToJSVal(mData[mDataIndex].value, aCx, &mCachedValue);
|
||||
NS_ENSURE_SUCCESS(rv, rv);
|
||||
|
||||
if (!mValueRooted) {
|
||||
NS_HOLD_JS_OBJECTS(this, IDBCursor);
|
||||
mValueRooted = true;
|
||||
}
|
||||
|
||||
mHaveCachedValue = true;
|
||||
}
|
||||
|
||||
|
|
|
@ -78,8 +78,8 @@ public:
|
|||
NS_DECL_ISUPPORTS_INHERITED
|
||||
NS_DECL_NSIIDBCURSOR
|
||||
|
||||
NS_DECL_CYCLE_COLLECTION_CLASS_INHERITED(IDBCursor,
|
||||
nsDOMEventTargetHelper)
|
||||
NS_DECL_CYCLE_COLLECTION_SCRIPT_HOLDER_CLASS_INHERITED(IDBCursor,
|
||||
nsDOMEventTargetHelper)
|
||||
|
||||
static
|
||||
already_AddRefed<IDBCursor>
|
||||
|
@ -137,7 +137,7 @@ protected:
|
|||
nsCOMPtr<nsIVariant> mCachedKey;
|
||||
jsval mCachedValue;
|
||||
bool mHaveCachedValue;
|
||||
JSRuntime* mJSRuntime;
|
||||
bool mValueRooted;
|
||||
|
||||
bool mContinueCalled;
|
||||
PRUint32 mDataIndex;
|
||||
|
|
|
@ -205,7 +205,17 @@ IDBEvent::CreateGenericEventRunnable(const nsAString& aType,
|
|||
NS_IMPL_ADDREF_INHERITED(IDBEvent, nsDOMEvent)
|
||||
NS_IMPL_RELEASE_INHERITED(IDBEvent, nsDOMEvent)
|
||||
|
||||
NS_INTERFACE_MAP_BEGIN(IDBEvent)
|
||||
NS_IMPL_CYCLE_COLLECTION_CLASS(IDBEvent)
|
||||
|
||||
NS_IMPL_CYCLE_COLLECTION_TRAVERSE_BEGIN_INHERITED(IDBEvent, nsDOMEvent)
|
||||
NS_IMPL_CYCLE_COLLECTION_TRAVERSE_NSCOMPTR(mSource)
|
||||
NS_IMPL_CYCLE_COLLECTION_TRAVERSE_END
|
||||
|
||||
NS_IMPL_CYCLE_COLLECTION_UNLINK_BEGIN_INHERITED(IDBEvent, nsDOMEvent)
|
||||
NS_IMPL_CYCLE_COLLECTION_UNLINK_NSCOMPTR(mSource)
|
||||
NS_IMPL_CYCLE_COLLECTION_UNLINK_END
|
||||
|
||||
NS_INTERFACE_MAP_BEGIN_CYCLE_COLLECTION_INHERITED(IDBEvent)
|
||||
NS_INTERFACE_MAP_ENTRY(nsIIDBEvent)
|
||||
NS_INTERFACE_MAP_END_INHERITING(nsDOMEvent)
|
||||
|
||||
|
@ -331,7 +341,19 @@ IDBSuccessEvent::CreateRunnable(IDBRequest* aRequest,
|
|||
NS_IMPL_ADDREF_INHERITED(IDBSuccessEvent, IDBEvent)
|
||||
NS_IMPL_RELEASE_INHERITED(IDBSuccessEvent, IDBEvent)
|
||||
|
||||
NS_INTERFACE_MAP_BEGIN(IDBSuccessEvent)
|
||||
NS_IMPL_CYCLE_COLLECTION_CLASS(IDBSuccessEvent)
|
||||
|
||||
NS_IMPL_CYCLE_COLLECTION_TRAVERSE_BEGIN_INHERITED(IDBSuccessEvent, IDBEvent)
|
||||
NS_IMPL_CYCLE_COLLECTION_TRAVERSE_NSCOMPTR(mResult)
|
||||
NS_IMPL_CYCLE_COLLECTION_TRAVERSE_NSCOMPTR(mTransaction)
|
||||
NS_IMPL_CYCLE_COLLECTION_TRAVERSE_END
|
||||
|
||||
NS_IMPL_CYCLE_COLLECTION_UNLINK_BEGIN_INHERITED(IDBSuccessEvent, IDBEvent)
|
||||
NS_IMPL_CYCLE_COLLECTION_UNLINK_NSCOMPTR(mResult)
|
||||
NS_IMPL_CYCLE_COLLECTION_UNLINK_NSCOMPTR(mTransaction)
|
||||
NS_IMPL_CYCLE_COLLECTION_UNLINK_END
|
||||
|
||||
NS_INTERFACE_MAP_BEGIN_CYCLE_COLLECTION_INHERITED(IDBSuccessEvent)
|
||||
NS_INTERFACE_MAP_ENTRY_CONDITIONAL(nsIIDBTransactionEvent, mTransaction)
|
||||
NS_DOM_INTERFACE_MAP_ENTRY_CLASSINFO_CONDITIONAL(IDBTransactionEvent,
|
||||
mTransaction)
|
||||
|
@ -372,6 +394,13 @@ IDBSuccessEvent::GetTransaction(nsIIDBTransaction** aTransaction)
|
|||
return NS_OK;
|
||||
}
|
||||
|
||||
GetSuccessEvent::~GetSuccessEvent()
|
||||
{
|
||||
if (mValueRooted) {
|
||||
NS_DROP_JS_OBJECTS(this, GetSuccessEvent);
|
||||
}
|
||||
}
|
||||
|
||||
nsresult
|
||||
GetSuccessEvent::Init(IDBRequest* aRequest,
|
||||
IDBTransaction* aTransaction)
|
||||
|
@ -398,20 +427,14 @@ GetSuccessEvent::GetResult(JSContext* aCx,
|
|||
return NS_OK;
|
||||
}
|
||||
|
||||
if (!mJSRuntime) {
|
||||
if (!mValueRooted) {
|
||||
RootCachedValue();
|
||||
|
||||
nsString jsonValue = mValue;
|
||||
mValue.Truncate();
|
||||
|
||||
JSAutoRequest ar(aCx);
|
||||
|
||||
JSRuntime* rt = JS_GetRuntime(aCx);
|
||||
|
||||
JSBool ok = js_AddRootRT(rt, &mCachedValue,
|
||||
"GetSuccessEvent::mCachedValue");
|
||||
NS_ENSURE_TRUE(ok, NS_ERROR_FAILURE);
|
||||
|
||||
mJSRuntime = rt;
|
||||
|
||||
nsCOMPtr<nsIJSON> json(new nsJSON());
|
||||
nsresult rv = json->DecodeToJSVal(jsonValue, aCx, &mCachedValue);
|
||||
if (NS_FAILED(rv)) {
|
||||
|
@ -426,21 +449,56 @@ GetSuccessEvent::GetResult(JSContext* aCx,
|
|||
return NS_OK;
|
||||
}
|
||||
|
||||
void
|
||||
GetSuccessEvent::RootCachedValue()
|
||||
{
|
||||
mValueRooted = PR_TRUE;
|
||||
NS_HOLD_JS_OBJECTS(this, GetSuccessEvent);
|
||||
}
|
||||
|
||||
NS_IMPL_ADDREF_INHERITED(GetSuccessEvent, IDBSuccessEvent)
|
||||
NS_IMPL_RELEASE_INHERITED(GetSuccessEvent, IDBSuccessEvent)
|
||||
|
||||
NS_IMPL_CYCLE_COLLECTION_CLASS(GetSuccessEvent)
|
||||
|
||||
NS_IMPL_CYCLE_COLLECTION_TRAVERSE_BEGIN_INHERITED(GetSuccessEvent,
|
||||
IDBSuccessEvent)
|
||||
NS_IMPL_CYCLE_COLLECTION_TRAVERSE_SCRIPT_OBJECTS
|
||||
NS_IMPL_CYCLE_COLLECTION_TRAVERSE_END
|
||||
|
||||
NS_IMPL_CYCLE_COLLECTION_ROOT_BEGIN(GetSuccessEvent)
|
||||
if (tmp->mValueRooted) {
|
||||
NS_DROP_JS_OBJECTS(tmp, GetSuccessEvent);
|
||||
tmp->mCachedValue = JSVAL_VOID;
|
||||
tmp->mValueRooted = PR_FALSE;
|
||||
}
|
||||
NS_IMPL_CYCLE_COLLECTION_ROOT_END
|
||||
|
||||
NS_IMPL_CYCLE_COLLECTION_UNLINK_BEGIN_INHERITED(GetSuccessEvent,
|
||||
IDBSuccessEvent)
|
||||
NS_IMPL_CYCLE_COLLECTION_UNLINK_NSCOMPTR(mResult)
|
||||
NS_IMPL_CYCLE_COLLECTION_UNLINK_NSCOMPTR(mTransaction)
|
||||
NS_IMPL_CYCLE_COLLECTION_UNLINK_END
|
||||
|
||||
NS_IMPL_CYCLE_COLLECTION_TRACE_BEGIN(GetSuccessEvent)
|
||||
if (JSVAL_IS_GCTHING(tmp->mCachedValue)) {
|
||||
void *gcThing = JSVAL_TO_GCTHING(tmp->mCachedValue);
|
||||
NS_IMPL_CYCLE_COLLECTION_TRACE_JS_CALLBACK(gcThing)
|
||||
}
|
||||
NS_IMPL_CYCLE_COLLECTION_TRACE_END
|
||||
|
||||
NS_INTERFACE_MAP_BEGIN_CYCLE_COLLECTION_INHERITED(GetSuccessEvent)
|
||||
NS_INTERFACE_MAP_END_INHERITING(IDBSuccessEvent)
|
||||
|
||||
NS_IMETHODIMP
|
||||
GetAllSuccessEvent::GetResult(JSContext* aCx,
|
||||
jsval* aResult)
|
||||
{
|
||||
if (!mJSRuntime) {
|
||||
if (!mValueRooted) {
|
||||
RootCachedValue();
|
||||
|
||||
JSAutoRequest ar(aCx);
|
||||
|
||||
JSRuntime* rt = JS_GetRuntime(aCx);
|
||||
|
||||
JSBool ok = js_AddRootRT(rt, &mCachedValue,
|
||||
"GetSuccessEvent::mCachedValue");
|
||||
NS_ENSURE_TRUE(ok, NS_ERROR_FAILURE);
|
||||
|
||||
mJSRuntime = rt;
|
||||
|
||||
// Swap into a stack array so that we don't hang on to the strings if
|
||||
// something fails.
|
||||
nsTArray<nsString> values;
|
||||
|
@ -497,17 +555,11 @@ NS_IMETHODIMP
|
|||
GetAllKeySuccessEvent::GetResult(JSContext* aCx,
|
||||
jsval* aResult)
|
||||
{
|
||||
if (!mJSRuntime) {
|
||||
if (!mValueRooted) {
|
||||
RootCachedValue();
|
||||
|
||||
JSAutoRequest ar(aCx);
|
||||
|
||||
JSRuntime* rt = JS_GetRuntime(aCx);
|
||||
|
||||
JSBool ok = js_AddRootRT(rt, &mCachedValue,
|
||||
"GetSuccessEvent::mCachedValue");
|
||||
NS_ENSURE_TRUE(ok, NS_ERROR_FAILURE);
|
||||
|
||||
mJSRuntime = rt;
|
||||
|
||||
// Swap into a stack array so that we don't hang on to the strings if
|
||||
// something fails.
|
||||
nsTArray<Key> keys;
|
||||
|
|
|
@ -73,6 +73,8 @@ public:
|
|||
NS_DECL_NSIIDBEVENT
|
||||
NS_FORWARD_TO_NSDOMEVENT
|
||||
|
||||
NS_DECL_CYCLE_COLLECTION_CLASS_INHERITED(IDBEvent, nsDOMEvent)
|
||||
|
||||
static already_AddRefed<nsIDOMEvent>
|
||||
CreateGenericEvent(const nsAString& aType);
|
||||
|
||||
|
@ -121,6 +123,8 @@ public:
|
|||
NS_FORWARD_NSIDOMEVENT(IDBEvent::)
|
||||
NS_FORWARD_NSIIDBEVENT(IDBEvent::)
|
||||
|
||||
NS_DECL_CYCLE_COLLECTION_CLASS_INHERITED(IDBSuccessEvent, IDBEvent)
|
||||
|
||||
static already_AddRefed<nsIDOMEvent>
|
||||
Create(IDBRequest* aRequest,
|
||||
nsIVariant* aResult,
|
||||
|
@ -144,15 +148,14 @@ public:
|
|||
GetSuccessEvent(const nsAString& aValue)
|
||||
: mValue(aValue),
|
||||
mCachedValue(JSVAL_VOID),
|
||||
mJSRuntime(nsnull)
|
||||
mValueRooted(PR_FALSE)
|
||||
{ }
|
||||
|
||||
~GetSuccessEvent()
|
||||
{
|
||||
if (mJSRuntime) {
|
||||
js_RemoveRoot(mJSRuntime, &mCachedValue);
|
||||
}
|
||||
}
|
||||
~GetSuccessEvent();
|
||||
|
||||
NS_DECL_ISUPPORTS_INHERITED
|
||||
NS_DECL_CYCLE_COLLECTION_SCRIPT_HOLDER_CLASS_INHERITED(GetSuccessEvent,
|
||||
IDBSuccessEvent)
|
||||
|
||||
NS_IMETHOD GetResult(JSContext* aCx,
|
||||
jsval* aResult);
|
||||
|
@ -164,8 +167,11 @@ private:
|
|||
nsString mValue;
|
||||
|
||||
protected:
|
||||
void RootCachedValue();
|
||||
|
||||
jsval mCachedValue;
|
||||
JSRuntime* mJSRuntime;
|
||||
PRBool mValueRooted;
|
||||
};
|
||||
|
||||
class GetAllSuccessEvent : public GetSuccessEvent
|
||||
|
|
|
@ -113,12 +113,14 @@ NS_IMPL_CYCLE_COLLECTION_TRAVERSE_BEGIN_INHERITED(IDBRequest,
|
|||
nsDOMEventTargetHelper)
|
||||
NS_IMPL_CYCLE_COLLECTION_TRAVERSE_NSCOMPTR(mOnSuccessListener)
|
||||
NS_IMPL_CYCLE_COLLECTION_TRAVERSE_NSCOMPTR(mOnErrorListener)
|
||||
NS_IMPL_CYCLE_COLLECTION_TRAVERSE_NSCOMPTR(mSource)
|
||||
NS_IMPL_CYCLE_COLLECTION_TRAVERSE_END
|
||||
|
||||
NS_IMPL_CYCLE_COLLECTION_UNLINK_BEGIN_INHERITED(IDBRequest,
|
||||
nsDOMEventTargetHelper)
|
||||
NS_IMPL_CYCLE_COLLECTION_UNLINK_NSCOMPTR(mOnSuccessListener)
|
||||
NS_IMPL_CYCLE_COLLECTION_UNLINK_NSCOMPTR(mOnErrorListener)
|
||||
NS_IMPL_CYCLE_COLLECTION_UNLINK_NSCOMPTR(mSource)
|
||||
NS_IMPL_CYCLE_COLLECTION_UNLINK_END
|
||||
|
||||
NS_INTERFACE_MAP_BEGIN_CYCLE_COLLECTION_INHERITED(IDBRequest)
|
||||
|
|
Загрузка…
Ссылка в новой задаче