mirror of
https://gitlab.winehq.org/wine/wine-gecko.git
synced 2024-09-13 09:24:08 -07:00
merge fx-team to m-c
This commit is contained in:
commit
44be5ce2e3
@ -1587,6 +1587,13 @@ nsAccessibleWrap::FirePlatformEvent(AccEvent* aEvent)
|
|||||||
|
|
||||||
// Fire MSAA event for client area window.
|
// Fire MSAA event for client area window.
|
||||||
NotifyWinEvent(winEvent, hWnd, OBJID_CLIENT, childID);
|
NotifyWinEvent(winEvent, hWnd, OBJID_CLIENT, childID);
|
||||||
|
|
||||||
|
// JAWS announces collapsed combobox navigation based on focus events.
|
||||||
|
if (eventType == nsIAccessibleEvent::EVENT_SELECTION &&
|
||||||
|
accessible->Role() == nsIAccessibleRole::ROLE_COMBOBOX_OPTION &&
|
||||||
|
nsWinUtils::IsWindowEmulationFor(kJAWSModuleHandle)) {
|
||||||
|
NotifyWinEvent(EVENT_OBJECT_FOCUS, hWnd, OBJID_CLIENT, childID);
|
||||||
|
}
|
||||||
return NS_OK;
|
return NS_OK;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
@ -61,30 +61,6 @@ DEFINES += -DAB_CD=$(AB_CD)
|
|||||||
APP_VERSION = $(shell cat $(srcdir)/../config/version.txt)
|
APP_VERSION = $(shell cat $(srcdir)/../config/version.txt)
|
||||||
DEFINES += -DAPP_VERSION="$(APP_VERSION)"
|
DEFINES += -DAPP_VERSION="$(APP_VERSION)"
|
||||||
|
|
||||||
DIST_FILES = application.ini
|
|
||||||
|
|
||||||
GRE_MILESTONE = $(shell $(PYTHON) $(topsrcdir)/config/printconfigsetting.py $(LIBXUL_DIST)/bin/platform.ini Build Milestone)
|
|
||||||
GRE_BUILDID = $(shell $(PYTHON) $(topsrcdir)/config/printconfigsetting.py $(LIBXUL_DIST)/bin/platform.ini Build BuildID)
|
|
||||||
|
|
||||||
DEFINES += -DGRE_MILESTONE=$(GRE_MILESTONE) -DGRE_BUILDID=$(GRE_BUILDID)
|
|
||||||
|
|
||||||
MOZ_SOURCE_STAMP ?= $(shell hg -R $(topsrcdir) parent --template="{node|short}\n" 2>/dev/null)
|
|
||||||
ifdef MOZ_SOURCE_STAMP
|
|
||||||
DEFINES += -DMOZ_SOURCE_STAMP="$(MOZ_SOURCE_STAMP)"
|
|
||||||
endif
|
|
||||||
|
|
||||||
SOURCE_REPO := $(shell hg -R $(topsrcdir) showconfig paths.default 2>/dev/null | sed -e "s/^ssh:/http:/")
|
|
||||||
ifdef SOURCE_REPO
|
|
||||||
DEFINES += -DMOZ_SOURCE_REPO="$(SOURCE_REPO)"
|
|
||||||
endif
|
|
||||||
|
|
||||||
DEFINES += -DMOZ_APP_BASENAME="$(MOZ_APP_BASENAME)" \
|
|
||||||
-DMOZ_APP_VENDOR="$(MOZ_APP_VENDOR)"
|
|
||||||
|
|
||||||
ifdef MOZ_APP_PROFILE
|
|
||||||
DEFINES += -DMOZ_APP_PROFILE="$(MOZ_APP_PROFILE)"
|
|
||||||
endif
|
|
||||||
|
|
||||||
ifdef LIBXUL_SDK
|
ifdef LIBXUL_SDK
|
||||||
include $(topsrcdir)/config/rules.mk
|
include $(topsrcdir)/config/rules.mk
|
||||||
else
|
else
|
||||||
@ -97,6 +73,7 @@ CPPSRCS = nsBrowserApp.cpp
|
|||||||
LOCAL_INCLUDES += -I$(topsrcdir)/toolkit/xre
|
LOCAL_INCLUDES += -I$(topsrcdir)/toolkit/xre
|
||||||
LOCAL_INCLUDES += -I$(topsrcdir)/xpcom/base
|
LOCAL_INCLUDES += -I$(topsrcdir)/xpcom/base
|
||||||
LOCAL_INCLUDES += -I$(topsrcdir)/xpcom/build
|
LOCAL_INCLUDES += -I$(topsrcdir)/xpcom/build
|
||||||
|
LOCAL_INCLUDES += -I$(DEPTH)/build
|
||||||
|
|
||||||
DEFINES += -DXPCOM_GLUE
|
DEFINES += -DXPCOM_GLUE
|
||||||
STL_FLAGS=
|
STL_FLAGS=
|
||||||
@ -187,10 +164,6 @@ endif # LIBXUL_SDK
|
|||||||
|
|
||||||
DEFINES += -DFIREFOX_ICO=\"$(DIST)/branding/firefox.ico\" -DDOCUMENT_ICO=\"$(DIST)/branding/document.ico\"
|
DEFINES += -DFIREFOX_ICO=\"$(DIST)/branding/firefox.ico\" -DDOCUMENT_ICO=\"$(DIST)/branding/document.ico\"
|
||||||
|
|
||||||
ifdef MOZILLA_OFFICIAL
|
|
||||||
DEFINES += -DMOZILLA_OFFICIAL
|
|
||||||
endif
|
|
||||||
|
|
||||||
ifeq ($(MOZ_WIDGET_TOOLKIT),gtk2)
|
ifeq ($(MOZ_WIDGET_TOOLKIT),gtk2)
|
||||||
libs::
|
libs::
|
||||||
$(INSTALL) $(IFLAGS1) $(DIST)/branding/mozicon128.png $(DIST)/bin/icons
|
$(INSTALL) $(IFLAGS1) $(DIST)/branding/mozicon128.png $(DIST)/bin/icons
|
||||||
@ -228,7 +201,7 @@ else
|
|||||||
APPFILES = MacOS
|
APPFILES = MacOS
|
||||||
endif
|
endif
|
||||||
|
|
||||||
libs repackage:: $(PROGRAM) application.ini
|
libs repackage:: $(PROGRAM)
|
||||||
$(MKDIR) -p $(DIST)/$(APP_NAME).app/Contents/MacOS
|
$(MKDIR) -p $(DIST)/$(APP_NAME).app/Contents/MacOS
|
||||||
rsync -a --exclude CVS --exclude "*.in" $(srcdir)/macbuild/Contents $(DIST)/$(APP_NAME).app --exclude English.lproj
|
rsync -a --exclude CVS --exclude "*.in" $(srcdir)/macbuild/Contents $(DIST)/$(APP_NAME).app --exclude English.lproj
|
||||||
$(MKDIR) -p $(DIST)/$(APP_NAME).app/Contents/Resources/$(AB).lproj
|
$(MKDIR) -p $(DIST)/$(APP_NAME).app/Contents/Resources/$(AB).lproj
|
||||||
|
@ -36,8 +36,8 @@
|
|||||||
*
|
*
|
||||||
* ***** END LICENSE BLOCK ***** */
|
* ***** END LICENSE BLOCK ***** */
|
||||||
|
|
||||||
|
#include "application.ini.h"
|
||||||
#include "nsXPCOMGlue.h"
|
#include "nsXPCOMGlue.h"
|
||||||
#include "nsXULAppAPI.h"
|
|
||||||
#if defined(XP_WIN)
|
#if defined(XP_WIN)
|
||||||
#include <windows.h>
|
#include <windows.h>
|
||||||
#include <stdlib.h>
|
#include <stdlib.h>
|
||||||
@ -140,20 +140,7 @@ static const nsDynamicFunctionLoad kXULFuncs[] = {
|
|||||||
static int do_main(const char *exePath, int argc, char* argv[])
|
static int do_main(const char *exePath, int argc, char* argv[])
|
||||||
{
|
{
|
||||||
nsCOMPtr<nsILocalFile> appini;
|
nsCOMPtr<nsILocalFile> appini;
|
||||||
#ifdef XP_WIN
|
nsresult rv;
|
||||||
// exePath comes from mozilla::BinaryPath::Get, which returns a UTF-8
|
|
||||||
// encoded path, so it is safe to convert it
|
|
||||||
nsresult rv = NS_NewLocalFile(NS_ConvertUTF8toUTF16(exePath), false,
|
|
||||||
getter_AddRefs(appini));
|
|
||||||
#else
|
|
||||||
nsresult rv = NS_NewNativeLocalFile(nsDependentCString(exePath), false,
|
|
||||||
getter_AddRefs(appini));
|
|
||||||
#endif
|
|
||||||
if (NS_FAILED(rv)) {
|
|
||||||
return 255;
|
|
||||||
}
|
|
||||||
|
|
||||||
appini->SetNativeLeafName(NS_LITERAL_CSTRING("application.ini"));
|
|
||||||
|
|
||||||
// Allow firefox.exe to launch XULRunner apps via -app <application.ini>
|
// Allow firefox.exe to launch XULRunner apps via -app <application.ini>
|
||||||
// Note that -app must be the *first* argument.
|
// Note that -app must be the *first* argument.
|
||||||
@ -188,15 +175,32 @@ static int do_main(const char *exePath, int argc, char* argv[])
|
|||||||
argc -= 2;
|
argc -= 2;
|
||||||
}
|
}
|
||||||
|
|
||||||
nsXREAppData *appData;
|
int result;
|
||||||
rv = XRE_CreateAppData(appini, &appData);
|
if (appini) {
|
||||||
if (NS_FAILED(rv)) {
|
nsXREAppData *appData;
|
||||||
Output("Couldn't read application.ini");
|
rv = XRE_CreateAppData(appini, &appData);
|
||||||
return 255;
|
if (NS_FAILED(rv)) {
|
||||||
|
Output("Couldn't read application.ini");
|
||||||
|
return 255;
|
||||||
|
}
|
||||||
|
result = XRE_main(argc, argv, appData);
|
||||||
|
XRE_FreeAppData(appData);
|
||||||
|
} else {
|
||||||
|
#ifdef XP_WIN
|
||||||
|
// exePath comes from mozilla::BinaryPath::Get, which returns a UTF-8
|
||||||
|
// encoded path, so it is safe to convert it
|
||||||
|
rv = NS_NewLocalFile(NS_ConvertUTF8toUTF16(exePath), PR_FALSE,
|
||||||
|
getter_AddRefs(appini));
|
||||||
|
#else
|
||||||
|
rv = NS_NewNativeLocalFile(nsDependentCString(exePath), PR_FALSE,
|
||||||
|
getter_AddRefs(appini));
|
||||||
|
#endif
|
||||||
|
if (NS_FAILED(rv)) {
|
||||||
|
return 255;
|
||||||
|
}
|
||||||
|
result = XRE_main(argc, argv, &sAppData);
|
||||||
}
|
}
|
||||||
|
|
||||||
int result = XRE_main(argc, argv, appData);
|
|
||||||
XRE_FreeAppData(appData);
|
|
||||||
return result;
|
return result;
|
||||||
}
|
}
|
||||||
|
|
||||||
@ -240,6 +244,8 @@ int main(int argc, char* argv[])
|
|||||||
Output("Couldn't load XPCOM.\n");
|
Output("Couldn't load XPCOM.\n");
|
||||||
return 255;
|
return 255;
|
||||||
}
|
}
|
||||||
|
// Reset exePath so that it is the directory name and not the xpcom dll name
|
||||||
|
*lastSlash = 0;
|
||||||
|
|
||||||
rv = XPCOMGlueLoadXULFunctions(kXULFuncs);
|
rv = XPCOMGlueLoadXULFunctions(kXULFuncs);
|
||||||
if (NS_FAILED(rv)) {
|
if (NS_FAILED(rv)) {
|
||||||
|
@ -1,8 +1,8 @@
|
|||||||
ac_add_options --enable-debug
|
ac_add_options --enable-debug
|
||||||
ac_add_options --enable-trace-malloc
|
ac_add_options --enable-trace-malloc
|
||||||
|
|
||||||
CC=/tools/gcc-4.5/bin/gcc
|
CC=/tools/gcc-4.5-0moz2/bin/gcc
|
||||||
CXX=/tools/gcc-4.5/bin/g++
|
CXX=/tools/gcc-4.5-0moz2/bin/g++
|
||||||
# Avoid dependency on libstdc++ 4.5
|
# Avoid dependency on libstdc++ 4.5
|
||||||
ac_add_options --enable-stdcxx-compat
|
ac_add_options --enable-stdcxx-compat
|
||||||
|
|
||||||
|
@ -3,5 +3,5 @@ ac_add_options --enable-official-branding
|
|||||||
ac_add_options --enable-update-channel=${MOZ_UPDATE_CHANNEL}
|
ac_add_options --enable-update-channel=${MOZ_UPDATE_CHANNEL}
|
||||||
ac_add_options --enable-update-packaging
|
ac_add_options --enable-update-packaging
|
||||||
|
|
||||||
CC=/tools/gcc-4.3.3/installed/bin/gcc
|
CC=/tools/gcc-4.5-0moz2/bin/gcc
|
||||||
CXX=/tools/gcc-4.3.3/installed/bin/g++
|
CXX=/tools/gcc-4.5-0moz2/bin/g++
|
||||||
|
@ -5,8 +5,8 @@ ac_add_options --enable-codesighs
|
|||||||
# Nightlies only since this has a cost in performance
|
# Nightlies only since this has a cost in performance
|
||||||
ac_add_options --enable-js-diagnostics
|
ac_add_options --enable-js-diagnostics
|
||||||
|
|
||||||
CC=/tools/gcc-4.5/bin/gcc
|
CC=/tools/gcc-4.5-0moz2/bin/gcc
|
||||||
CXX=/tools/gcc-4.5/bin/g++
|
CXX=/tools/gcc-4.5-0moz2/bin/g++
|
||||||
# Avoid dependency on libstdc++ 4.5
|
# Avoid dependency on libstdc++ 4.5
|
||||||
ac_add_options --enable-stdcxx-compat
|
ac_add_options --enable-stdcxx-compat
|
||||||
|
|
||||||
|
@ -1,8 +1,8 @@
|
|||||||
ac_add_options --enable-update-packaging
|
ac_add_options --enable-update-packaging
|
||||||
ac_add_options --enable-codesighs
|
ac_add_options --enable-codesighs
|
||||||
|
|
||||||
CC=/tools/gcc-4.5/bin/gcc
|
CC=/tools/gcc-4.5-0moz2/bin/gcc
|
||||||
CXX=/tools/gcc-4.5/bin/g++
|
CXX=/tools/gcc-4.5-0moz2/bin/g++
|
||||||
# Avoid dependency on libstdc++ 4.5
|
# Avoid dependency on libstdc++ 4.5
|
||||||
ac_add_options --enable-stdcxx-compat
|
ac_add_options --enable-stdcxx-compat
|
||||||
|
|
||||||
|
@ -2,8 +2,8 @@ ac_add_options --enable-update-channel=${MOZ_UPDATE_CHANNEL}
|
|||||||
ac_add_options --enable-update-packaging
|
ac_add_options --enable-update-packaging
|
||||||
ac_add_options --enable-official-branding
|
ac_add_options --enable-official-branding
|
||||||
|
|
||||||
CC=/tools/gcc-4.5/bin/gcc
|
CC=/tools/gcc-4.5-0moz2/bin/gcc
|
||||||
CXX=/tools/gcc-4.5/bin/g++
|
CXX=/tools/gcc-4.5-0moz2/bin/g++
|
||||||
# Avoid dependency on libstdc++ 4.5
|
# Avoid dependency on libstdc++ 4.5
|
||||||
ac_add_options --enable-stdcxx-compat
|
ac_add_options --enable-stdcxx-compat
|
||||||
|
|
||||||
|
@ -9,8 +9,8 @@ ac_add_options --disable-updater
|
|||||||
ac_add_options --prefix=$PREFIX
|
ac_add_options --prefix=$PREFIX
|
||||||
ac_add_options --libdir=$LIBDIR
|
ac_add_options --libdir=$LIBDIR
|
||||||
|
|
||||||
CC=/tools/gcc-4.5/bin/gcc
|
CC=/tools/gcc-4.5-0moz2/bin/gcc
|
||||||
CXX=/tools/gcc-4.5/bin/g++
|
CXX=/tools/gcc-4.5-0moz2/bin/g++
|
||||||
# Avoid dependency on libstdc++ 4.5
|
# Avoid dependency on libstdc++ 4.5
|
||||||
ac_add_options --enable-stdcxx-compat
|
ac_add_options --enable-stdcxx-compat
|
||||||
|
|
||||||
|
@ -1,8 +1,8 @@
|
|||||||
ac_add_options --enable-debug
|
ac_add_options --enable-debug
|
||||||
ac_add_options --enable-trace-malloc
|
ac_add_options --enable-trace-malloc
|
||||||
|
|
||||||
CC=/tools/gcc-4.5/bin/gcc
|
CC=/tools/gcc-4.5-0moz2/bin/gcc
|
||||||
CXX=/tools/gcc-4.5/bin/g++
|
CXX=/tools/gcc-4.5-0moz2/bin/g++
|
||||||
# Avoid dependency on libstdc++ 4.5
|
# Avoid dependency on libstdc++ 4.5
|
||||||
ac_add_options --enable-stdcxx-compat
|
ac_add_options --enable-stdcxx-compat
|
||||||
|
|
||||||
|
@ -3,5 +3,5 @@ ac_add_options --enable-official-branding
|
|||||||
ac_add_options --enable-update-channel=${MOZ_UPDATE_CHANNEL}
|
ac_add_options --enable-update-channel=${MOZ_UPDATE_CHANNEL}
|
||||||
ac_add_options --enable-update-packaging
|
ac_add_options --enable-update-packaging
|
||||||
|
|
||||||
CC=/tools/gcc/bin/gcc
|
CC=/tools/gcc-4.5-0moz2/bin/gcc
|
||||||
CXX=/tools/gcc/bin/g++
|
CXX=/tools/gcc-4.5-0moz2/bin/g++
|
||||||
|
@ -5,8 +5,8 @@ ac_add_options --enable-codesighs
|
|||||||
# Nightlies only since this has a cost in performance
|
# Nightlies only since this has a cost in performance
|
||||||
ac_add_options --enable-js-diagnostics
|
ac_add_options --enable-js-diagnostics
|
||||||
|
|
||||||
CC=/tools/gcc-4.5/bin/gcc
|
CC=/tools/gcc-4.5-0moz2/bin/gcc
|
||||||
CXX=/tools/gcc-4.5/bin/g++
|
CXX=/tools/gcc-4.5-0moz2/bin/g++
|
||||||
# Avoid dependency on libstdc++ 4.5
|
# Avoid dependency on libstdc++ 4.5
|
||||||
ac_add_options --enable-stdcxx-compat
|
ac_add_options --enable-stdcxx-compat
|
||||||
|
|
||||||
|
@ -2,8 +2,8 @@ ac_add_options --enable-update-channel=${MOZ_UPDATE_CHANNEL}
|
|||||||
ac_add_options --enable-update-packaging
|
ac_add_options --enable-update-packaging
|
||||||
ac_add_options --enable-official-branding
|
ac_add_options --enable-official-branding
|
||||||
|
|
||||||
CC=/tools/gcc-4.5/bin/gcc
|
CC=/tools/gcc-4.5-0moz2/bin/gcc
|
||||||
CXX=/tools/gcc-4.5/bin/g++
|
CXX=/tools/gcc-4.5-0moz2/bin/g++
|
||||||
# Avoid dependency on libstdc++ 4.5
|
# Avoid dependency on libstdc++ 4.5
|
||||||
ac_add_options --enable-stdcxx-compat
|
ac_add_options --enable-stdcxx-compat
|
||||||
|
|
||||||
|
@ -9,8 +9,8 @@ ac_add_options --disable-updater
|
|||||||
ac_add_options --prefix=$PREFIX
|
ac_add_options --prefix=$PREFIX
|
||||||
ac_add_options --libdir=$LIBDIR
|
ac_add_options --libdir=$LIBDIR
|
||||||
|
|
||||||
CC=/tools/gcc-4.5/bin/gcc
|
CC=/tools/gcc-4.5-0moz2/bin/gcc
|
||||||
CXX=/tools/gcc-4.5/bin/g++
|
CXX=/tools/gcc-4.5-0moz2/bin/g++
|
||||||
# Avoid dependency on libstdc++ 4.5
|
# Avoid dependency on libstdc++ 4.5
|
||||||
ac_add_options --enable-stdcxx-compat
|
ac_add_options --enable-stdcxx-compat
|
||||||
|
|
||||||
|
@ -51,3 +51,7 @@ MOZ_EXTENSIONS_DEFAULT=" gnomevfs"
|
|||||||
# because branding dependencies are broken.
|
# because branding dependencies are broken.
|
||||||
MOZ_BRANDING_DIRECTORY=browser/branding/nightly
|
MOZ_BRANDING_DIRECTORY=browser/branding/nightly
|
||||||
MOZ_OFFICIAL_BRANDING_DIRECTORY=browser/branding/official
|
MOZ_OFFICIAL_BRANDING_DIRECTORY=browser/branding/official
|
||||||
|
MOZ_APP_ID={ec8030f7-c20a-464f-9b0e-13a3a9e97384}
|
||||||
|
MOZ_PROFILE_MIGRATOR=1
|
||||||
|
MOZ_EXTENSION_MANAGER=1
|
||||||
|
MOZ_APP_STATIC_INI=1
|
||||||
|
@ -14,6 +14,7 @@
|
|||||||
@DLL_PREFIX@mozjs@DLL_SUFFIX@
|
@DLL_PREFIX@mozjs@DLL_SUFFIX@
|
||||||
#endif
|
#endif
|
||||||
LICENSE
|
LICENSE
|
||||||
|
update.locale
|
||||||
browserconfig.properties
|
browserconfig.properties
|
||||||
chrome/US.jar
|
chrome/US.jar
|
||||||
chrome/app-chrome.manifest
|
chrome/app-chrome.manifest
|
||||||
|
@ -66,6 +66,60 @@ ifeq (android,$(MOZ_WIDGET_TOOLKIT))
|
|||||||
endif
|
endif
|
||||||
endif
|
endif
|
||||||
|
|
||||||
|
ifdef MOZ_APP_BASENAME
|
||||||
|
DIST_FILES = application.ini
|
||||||
|
|
||||||
|
ifdef LIBXUL_SDK
|
||||||
|
GRE_MILESTONE = $(shell $(PYTHON) $(topsrcdir)/config/printconfigsetting.py $(LIBXUL_DIST)/bin/platform.ini Build Milestone)
|
||||||
|
APP_INI_DEPS = $(LIBXUL_DIST)/bin/platform.ini
|
||||||
|
else
|
||||||
|
GRE_MILESTONE = $(shell tail -n 1 $(topsrcdir)/config/milestone.txt 2>/dev/null || tail -1 $(topsrcdir)/config/milestone.txt)
|
||||||
|
APP_INI_DEPS = $(topsrcdir)/config/milestone.txt
|
||||||
|
endif
|
||||||
|
|
||||||
|
APP_BUILDID := $(shell cat $(DEPTH)/config/buildid)
|
||||||
|
APP_INI_DEPS += $(DEPTH)/config/buildid
|
||||||
|
|
||||||
|
DEFINES += -DGRE_MILESTONE=$(GRE_MILESTONE) -DAPP_BUILDID=$(APP_BUILDID)
|
||||||
|
|
||||||
|
DEFINES += -DMOZ_APP_VERSION="$(MOZ_APP_VERSION)"
|
||||||
|
APP_INI_DEPS += $(DEPTH)/config/autoconf.mk
|
||||||
|
|
||||||
|
MOZ_SOURCE_STAMP ?= $(firstword $(shell hg -R $(topsrcdir) parent --template="{node|short}\n" 2>/dev/null))
|
||||||
|
ifdef MOZ_SOURCE_STAMP
|
||||||
|
DEFINES += -DMOZ_SOURCE_STAMP="$(MOZ_SOURCE_STAMP)"
|
||||||
|
endif
|
||||||
|
|
||||||
|
_dollar=$$
|
||||||
|
SOURCE_REPO := $(shell cd $(topsrcdir) && hg showconfig paths.default 2>/dev/null | head -n1 | sed -e "s/^ssh:/http:/" -e "s/\/$(_dollar)//" )
|
||||||
|
ifdef SOURCE_REPO
|
||||||
|
DEFINES += -DMOZ_SOURCE_REPO="$(SOURCE_REPO)"
|
||||||
|
endif
|
||||||
|
|
||||||
|
DEFINES += \
|
||||||
|
-DMOZ_APP_BASENAME="$(MOZ_APP_BASENAME)" \
|
||||||
|
-DMOZ_APP_VENDOR="$(MOZ_APP_VENDOR)" \
|
||||||
|
-DMOZ_APP_ID="$(MOZ_APP_ID)" \
|
||||||
|
$(NULL)
|
||||||
|
|
||||||
|
ifdef MOZ_APP_PROFILE
|
||||||
|
DEFINES += -DMOZ_APP_PROFILE="$(MOZ_APP_PROFILE)"
|
||||||
|
endif
|
||||||
|
|
||||||
|
ifdef MOZILLA_OFFICIAL
|
||||||
|
DEFINES += -DMOZILLA_OFFICIAL
|
||||||
|
endif
|
||||||
|
|
||||||
|
ifdef MOZ_PROFILE_MIGRATOR
|
||||||
|
DEFINES += -DMOZ_PROFILE_MIGRATOR
|
||||||
|
endif
|
||||||
|
|
||||||
|
ifdef MOZ_EXTENSION_MANAGER
|
||||||
|
DEFINES += -DMOZ_EXTENSION_MANAGER
|
||||||
|
endif
|
||||||
|
|
||||||
|
endif
|
||||||
|
|
||||||
include $(topsrcdir)/config/rules.mk
|
include $(topsrcdir)/config/rules.mk
|
||||||
|
|
||||||
# we install to _leaktest/
|
# we install to _leaktest/
|
||||||
@ -100,6 +154,19 @@ leaktest.py: leaktest.py.in
|
|||||||
chmod +x $@
|
chmod +x $@
|
||||||
GARBAGE += leaktest.py
|
GARBAGE += leaktest.py
|
||||||
|
|
||||||
|
ifdef MOZ_APP_BASENAME
|
||||||
|
application.ini: application.ini.in $(APP_INI_DEPS)
|
||||||
|
$(PYTHON) $(topsrcdir)/config/Preprocessor.py $(DEFINES) $< > $@
|
||||||
|
GARBAGE += application.ini
|
||||||
|
|
||||||
|
ifdef MOZ_APP_STATIC_INI
|
||||||
|
application.ini.h: appini_header.py application.ini
|
||||||
|
$(PYTHON) $^ > $@
|
||||||
|
export:: application.ini.h
|
||||||
|
GARBAGE += application.ini.h
|
||||||
|
endif
|
||||||
|
endif
|
||||||
|
|
||||||
libs:: $(_LEAKTEST_FILES)
|
libs:: $(_LEAKTEST_FILES)
|
||||||
$(INSTALL) $^ $(_LEAKTEST_DIR)
|
$(INSTALL) $^ $(_LEAKTEST_DIR)
|
||||||
|
|
||||||
|
86
build/appini_header.py
Normal file
86
build/appini_header.py
Normal file
@ -0,0 +1,86 @@
|
|||||||
|
# ***** BEGIN LICENSE BLOCK *****
|
||||||
|
# Version: MPL 1.1/GPL 2.0/LGPL 2.1
|
||||||
|
#
|
||||||
|
# The contents of this file are subject to the Mozilla Public License Version
|
||||||
|
# 1.1 (the "License"); you may not use this file except in compliance with
|
||||||
|
# the License. You may obtain a copy of the License at
|
||||||
|
# http://www.mozilla.org/MPL/
|
||||||
|
#
|
||||||
|
# Software distributed under the License is distributed on an "AS IS" basis,
|
||||||
|
# WITHOUT WARRANTY OF ANY KIND, either express or implied. See the License
|
||||||
|
# for the specific language governing rights and limitations under the
|
||||||
|
# License.
|
||||||
|
#
|
||||||
|
# The Original Code is a build helper for libraries
|
||||||
|
#
|
||||||
|
# The Initial Developer of the Original Code is
|
||||||
|
# the Mozilla Foundation
|
||||||
|
# Portions created by the Initial Developer are Copyright (C) 2011
|
||||||
|
# the Initial Developer. All Rights Reserved.
|
||||||
|
#
|
||||||
|
# Contributor(s):
|
||||||
|
# Mike Hommey <mh@glandium.org>
|
||||||
|
#
|
||||||
|
# Alternatively, the contents of this file may be used under the terms of
|
||||||
|
# either the GNU General Public License Version 2 or later (the "GPL"), or
|
||||||
|
# the GNU Lesser General Public License Version 2.1 or later (the "LGPL"),
|
||||||
|
# in which case the provisions of the GPL or the LGPL are applicable instead
|
||||||
|
# of those above. If you wish to allow use of your version of this file only
|
||||||
|
# under the terms of either the GPL or the LGPL, and not to allow others to
|
||||||
|
# use your version of this file under the terms of the MPL, indicate your
|
||||||
|
# decision by deleting the provisions above and replace them with the notice
|
||||||
|
# and other provisions required by the GPL or the LGPL. If you do not delete
|
||||||
|
# the provisions above, a recipient may use your version of this file under
|
||||||
|
# the terms of any one of the MPL, the GPL or the LGPL.
|
||||||
|
#
|
||||||
|
# ***** END LICENSE BLOCK *****
|
||||||
|
|
||||||
|
'''Parses a given application.ini file and outputs the corresponding
|
||||||
|
XULAppData structure as a C++ header file'''
|
||||||
|
|
||||||
|
import ConfigParser
|
||||||
|
import sys
|
||||||
|
|
||||||
|
def main(file):
|
||||||
|
config = ConfigParser.RawConfigParser()
|
||||||
|
config.read(file)
|
||||||
|
flags = set()
|
||||||
|
try:
|
||||||
|
if config.getint('XRE', 'EnableExtensionManager') == 1:
|
||||||
|
flags.add('NS_XRE_ENABLE_EXTENSION_MANAGER')
|
||||||
|
except: pass
|
||||||
|
try:
|
||||||
|
if config.getint('XRE', 'EnableProfileMigrator') == 1:
|
||||||
|
flags.add('NS_XRE_ENABLE_PROFILE_MIGRATOR')
|
||||||
|
except: pass
|
||||||
|
try:
|
||||||
|
if config.getint('Crash Reporter', 'Enabled') == 1:
|
||||||
|
flags.add('NS_XRE_ENABLE_CRASH_REPORTER')
|
||||||
|
except: pass
|
||||||
|
appdata = dict(("%s:%s" % (s, o), config.get(s, o)) for s in config.sections() for o in config.options(s))
|
||||||
|
appdata['flags'] = ' | '.join(flags) if flags else '0'
|
||||||
|
appdata['App:profile'] = '"%s"' % appdata['App:profile'] if 'App:profile' in appdata else 'NULL'
|
||||||
|
|
||||||
|
print '''#include "nsXULAppAPI.h"
|
||||||
|
static const nsXREAppData sAppData = {
|
||||||
|
sizeof(nsXREAppData),
|
||||||
|
NULL, // directory
|
||||||
|
"%(App:vendor)s",
|
||||||
|
"%(App:name)s",
|
||||||
|
"%(App:version)s",
|
||||||
|
"%(App:buildid)s",
|
||||||
|
"%(App:id)s",
|
||||||
|
NULL, // copyright
|
||||||
|
%(flags)s,
|
||||||
|
NULL, // xreDirectory
|
||||||
|
"%(Gecko:minversion)s",
|
||||||
|
"%(Gecko:maxversion)s",
|
||||||
|
"%(Crash Reporter:serverurl)s",
|
||||||
|
%(App:profile)s
|
||||||
|
};''' % appdata
|
||||||
|
|
||||||
|
if __name__ == '__main__':
|
||||||
|
if len(sys.argv) != 1:
|
||||||
|
main(sys.argv[1])
|
||||||
|
else:
|
||||||
|
print >>sys.stderr, "Usage: %s /path/to/application.ini" % sys.argv[0]
|
@ -1,3 +1,9 @@
|
|||||||
|
#if MOZ_APP_STATIC_INI
|
||||||
|
; This file is not used. If you modify it and want the application to use
|
||||||
|
; your modifications, start with the "-app /path/to/application.ini"
|
||||||
|
; argument.
|
||||||
|
#endif
|
||||||
|
#if 0
|
||||||
; ***** BEGIN LICENSE BLOCK *****
|
; ***** BEGIN LICENSE BLOCK *****
|
||||||
; Version: MPL 1.1/GPL 2.0/LGPL 2.1
|
; Version: MPL 1.1/GPL 2.0/LGPL 2.1
|
||||||
;
|
;
|
||||||
@ -34,34 +40,38 @@
|
|||||||
; the terms of any one of the MPL, the GPL or the LGPL.
|
; the terms of any one of the MPL, the GPL or the LGPL.
|
||||||
;
|
;
|
||||||
; ***** END LICENSE BLOCK *****
|
; ***** END LICENSE BLOCK *****
|
||||||
|
#endif
|
||||||
#filter substitution
|
#filter substitution
|
||||||
[App]
|
[App]
|
||||||
Vendor=@MOZ_APP_VENDOR@
|
Vendor=@MOZ_APP_VENDOR@
|
||||||
Name=@MOZ_APP_BASENAME@
|
Name=@MOZ_APP_BASENAME@
|
||||||
Version=@APP_VERSION@
|
Version=@MOZ_APP_VERSION@
|
||||||
#ifdef MOZ_APP_PROFILE
|
#ifdef MOZ_APP_PROFILE
|
||||||
Profile=@MOZ_APP_PROFILE@
|
Profile=@MOZ_APP_PROFILE@
|
||||||
#endif
|
#endif
|
||||||
BuildID=@GRE_BUILDID@
|
BuildID=@APP_BUILDID@
|
||||||
#ifdef MOZ_SOURCE_REPO
|
#ifdef MOZ_SOURCE_REPO
|
||||||
SourceRepository=@MOZ_SOURCE_REPO@
|
SourceRepository=@MOZ_SOURCE_REPO@
|
||||||
#endif
|
#endif
|
||||||
#ifdef MOZ_SOURCE_STAMP
|
#ifdef MOZ_SOURCE_STAMP
|
||||||
SourceStamp=@MOZ_SOURCE_STAMP@
|
SourceStamp=@MOZ_SOURCE_STAMP@
|
||||||
#endif
|
#endif
|
||||||
ID={ec8030f7-c20a-464f-9b0e-13a3a9e97384}
|
ID=@MOZ_APP_ID@
|
||||||
|
|
||||||
[Gecko]
|
[Gecko]
|
||||||
MinVersion=@GRE_MILESTONE@
|
MinVersion=@GRE_MILESTONE@
|
||||||
MaxVersion=@GRE_MILESTONE@
|
MaxVersion=@GRE_MILESTONE@
|
||||||
|
|
||||||
[XRE]
|
[XRE]
|
||||||
|
#ifdef MOZ_PROFILE_MIGRATOR
|
||||||
EnableProfileMigrator=1
|
EnableProfileMigrator=1
|
||||||
|
#endif
|
||||||
|
#ifdef MOZ_EXTENSION_MANAGER
|
||||||
EnableExtensionManager=1
|
EnableExtensionManager=1
|
||||||
|
#endif
|
||||||
|
|
||||||
[Crash Reporter]
|
[Crash Reporter]
|
||||||
#if MOZILLA_OFFICIAL
|
#if MOZILLA_OFFICIAL
|
||||||
Enabled=1
|
Enabled=1
|
||||||
#endif
|
#endif
|
||||||
ServerURL=https://crash-reports.mozilla.com/submit?id=ec8030f7-c20a-464f-9b0e-13a3a9e97384&version=@APP_VERSION@&buildid=@GRE_BUILDID@
|
ServerURL=https://crash-reports.mozilla.com/submit?id=@MOZ_APP_ID@&version=@MOZ_APP_VERSION@&buildid=@APP_BUILDID@
|
@ -340,6 +340,7 @@ user_pref("browser.ui.layout.tablet", 0); // force tablet UI off
|
|||||||
user_pref("dom.allow_scripts_to_close_windows", true);
|
user_pref("dom.allow_scripts_to_close_windows", true);
|
||||||
user_pref("dom.disable_open_during_load", false);
|
user_pref("dom.disable_open_during_load", false);
|
||||||
user_pref("dom.max_script_run_time", 0); // no slow script dialogs
|
user_pref("dom.max_script_run_time", 0); // no slow script dialogs
|
||||||
|
user_pref("hangmonitor.timeout", 0); // no hang monitor
|
||||||
user_pref("dom.max_chrome_script_run_time", 0);
|
user_pref("dom.max_chrome_script_run_time", 0);
|
||||||
user_pref("dom.popup_maximum", -1);
|
user_pref("dom.popup_maximum", -1);
|
||||||
user_pref("dom.send_after_paint_to_content", true);
|
user_pref("dom.send_after_paint_to_content", true);
|
||||||
@ -366,6 +367,9 @@ user_pref("app.update.enabled", false);
|
|||||||
user_pref("browser.panorama.experienced_first_run", true); // Assume experienced
|
user_pref("browser.panorama.experienced_first_run", true); // Assume experienced
|
||||||
user_pref("dom.w3c_touch_events.enabled", true);
|
user_pref("dom.w3c_touch_events.enabled", true);
|
||||||
user_pref("toolkit.telemetry.prompted", 2);
|
user_pref("toolkit.telemetry.prompted", 2);
|
||||||
|
// Existing tests assume there is no font size inflation.
|
||||||
|
user_pref("font.size.inflation.emPerLine", 0);
|
||||||
|
user_pref("font.size.inflation.minTwips", 0);
|
||||||
|
|
||||||
// Only load extensions from the application and user profile
|
// Only load extensions from the application and user profile
|
||||||
// AddonManager.SCOPE_PROFILE + AddonManager.SCOPE_APPLICATION
|
// AddonManager.SCOPE_PROFILE + AddonManager.SCOPE_APPLICATION
|
||||||
|
@ -52,9 +52,13 @@ MOZ_APP_DISPLAYNAME = @MOZ_APP_DISPLAYNAME@
|
|||||||
MOZ_APP_BASENAME = @MOZ_APP_BASENAME@
|
MOZ_APP_BASENAME = @MOZ_APP_BASENAME@
|
||||||
MOZ_APP_VENDOR = @MOZ_APP_VENDOR@
|
MOZ_APP_VENDOR = @MOZ_APP_VENDOR@
|
||||||
MOZ_APP_PROFILE = @MOZ_APP_PROFILE@
|
MOZ_APP_PROFILE = @MOZ_APP_PROFILE@
|
||||||
|
MOZ_APP_ID = @MOZ_APP_ID@
|
||||||
|
MOZ_PROFILE_MIGRATOR = @MOZ_PROFILE_MIGRATOR@
|
||||||
|
MOZ_EXTENSION_MANAGER = @MOZ_EXTENSION_MANAGER@
|
||||||
MOZ_APP_UA_NAME = @MOZ_APP_UA_NAME@
|
MOZ_APP_UA_NAME = @MOZ_APP_UA_NAME@
|
||||||
MOZ_APP_VERSION = @MOZ_APP_VERSION@
|
MOZ_APP_VERSION = @MOZ_APP_VERSION@
|
||||||
MOZ_UA_BUILDID = @MOZ_UA_BUILDID@
|
MOZ_UA_BUILDID = @MOZ_UA_BUILDID@
|
||||||
|
MOZ_APP_STATIC_INI = @MOZ_APP_STATIC_INI@
|
||||||
|
|
||||||
MOZ_PKG_SPECIAL = @MOZ_PKG_SPECIAL@
|
MOZ_PKG_SPECIAL = @MOZ_PKG_SPECIAL@
|
||||||
|
|
||||||
|
@ -64,8 +64,6 @@ ifdef SDK_HEADERS
|
|||||||
EXPORTS += $(SDK_HEADERS)
|
EXPORTS += $(SDK_HEADERS)
|
||||||
endif
|
endif
|
||||||
|
|
||||||
REPORT_BUILD = @echo $(notdir $<)
|
|
||||||
|
|
||||||
ifeq ($(OS_ARCH),OS2)
|
ifeq ($(OS_ARCH),OS2)
|
||||||
EXEC =
|
EXEC =
|
||||||
else
|
else
|
||||||
@ -1150,32 +1148,25 @@ endif # MOZ_AUTO_DEPS
|
|||||||
|
|
||||||
# Rules for building native targets must come first because of the host_ prefix
|
# Rules for building native targets must come first because of the host_ prefix
|
||||||
host_%.$(OBJ_SUFFIX): %.c $(GLOBAL_DEPS)
|
host_%.$(OBJ_SUFFIX): %.c $(GLOBAL_DEPS)
|
||||||
$(REPORT_BUILD)
|
|
||||||
$(ELOG) $(HOST_CC) $(HOST_OUTOPTION)$@ -c $(HOST_CFLAGS) $(INCLUDES) $(NSPR_CFLAGS) $(_VPATH_SRCS)
|
$(ELOG) $(HOST_CC) $(HOST_OUTOPTION)$@ -c $(HOST_CFLAGS) $(INCLUDES) $(NSPR_CFLAGS) $(_VPATH_SRCS)
|
||||||
|
|
||||||
host_%.$(OBJ_SUFFIX): %.cpp $(GLOBAL_DEPS)
|
host_%.$(OBJ_SUFFIX): %.cpp $(GLOBAL_DEPS)
|
||||||
$(REPORT_BUILD)
|
|
||||||
$(ELOG) $(HOST_CXX) $(HOST_OUTOPTION)$@ -c $(HOST_CXXFLAGS) $(INCLUDES) $(NSPR_CFLAGS) $(_VPATH_SRCS)
|
$(ELOG) $(HOST_CXX) $(HOST_OUTOPTION)$@ -c $(HOST_CXXFLAGS) $(INCLUDES) $(NSPR_CFLAGS) $(_VPATH_SRCS)
|
||||||
|
|
||||||
host_%.$(OBJ_SUFFIX): %.cc $(GLOBAL_DEPS)
|
host_%.$(OBJ_SUFFIX): %.cc $(GLOBAL_DEPS)
|
||||||
$(REPORT_BUILD)
|
|
||||||
$(ELOG) $(HOST_CXX) $(HOST_OUTOPTION)$@ -c $(HOST_CXXFLAGS) $(INCLUDES) $(NSPR_CFLAGS) $(_VPATH_SRCS)
|
$(ELOG) $(HOST_CXX) $(HOST_OUTOPTION)$@ -c $(HOST_CXXFLAGS) $(INCLUDES) $(NSPR_CFLAGS) $(_VPATH_SRCS)
|
||||||
|
|
||||||
host_%.$(OBJ_SUFFIX): %.m $(GLOBAL_DEPS)
|
host_%.$(OBJ_SUFFIX): %.m $(GLOBAL_DEPS)
|
||||||
$(REPORT_BUILD)
|
|
||||||
$(ELOG) $(HOST_CC) $(HOST_OUTOPTION)$@ -c $(HOST_CFLAGS) $(HOST_CMFLAGS) $(INCLUDES) $(NSPR_CFLAGS) $(_VPATH_SRCS)
|
$(ELOG) $(HOST_CC) $(HOST_OUTOPTION)$@ -c $(HOST_CFLAGS) $(HOST_CMFLAGS) $(INCLUDES) $(NSPR_CFLAGS) $(_VPATH_SRCS)
|
||||||
|
|
||||||
host_%.$(OBJ_SUFFIX): %.mm $(GLOBAL_DEPS)
|
host_%.$(OBJ_SUFFIX): %.mm $(GLOBAL_DEPS)
|
||||||
$(REPORT_BUILD)
|
|
||||||
$(ELOG) $(HOST_CXX) $(HOST_OUTOPTION)$@ -c $(HOST_CXXFLAGS) $(HOST_CMMFLAGS) $(INCLUDES) $(NSPR_CFLAGS) $(_VPATH_SRCS)
|
$(ELOG) $(HOST_CXX) $(HOST_OUTOPTION)$@ -c $(HOST_CXXFLAGS) $(HOST_CMMFLAGS) $(INCLUDES) $(NSPR_CFLAGS) $(_VPATH_SRCS)
|
||||||
|
|
||||||
%:: %.c $(GLOBAL_DEPS)
|
%:: %.c $(GLOBAL_DEPS)
|
||||||
$(REPORT_BUILD)
|
|
||||||
@$(MAKE_DEPS_AUTO_CC)
|
@$(MAKE_DEPS_AUTO_CC)
|
||||||
$(ELOG) $(CC) $(CFLAGS) $(LDFLAGS) $(OUTOPTION)$@ $(_VPATH_SRCS)
|
$(ELOG) $(CC) $(CFLAGS) $(LDFLAGS) $(OUTOPTION)$@ $(_VPATH_SRCS)
|
||||||
|
|
||||||
%.$(OBJ_SUFFIX): %.c $(GLOBAL_DEPS)
|
%.$(OBJ_SUFFIX): %.c $(GLOBAL_DEPS)
|
||||||
$(REPORT_BUILD)
|
|
||||||
@$(MAKE_DEPS_AUTO_CC)
|
@$(MAKE_DEPS_AUTO_CC)
|
||||||
$(ELOG) $(CC) $(OUTOPTION)$@ -c $(COMPILE_CFLAGS) $(_VPATH_SRCS)
|
$(ELOG) $(CC) $(OUTOPTION)$@ -c $(COMPILE_CFLAGS) $(_VPATH_SRCS)
|
||||||
|
|
||||||
@ -1186,7 +1177,6 @@ moc_%.cpp: %.h $(GLOBAL_DEPS)
|
|||||||
$(MOC) $(DEFINES) $(ACDEFINES) $< $(OUTOPTION)$@
|
$(MOC) $(DEFINES) $(ACDEFINES) $< $(OUTOPTION)$@
|
||||||
|
|
||||||
moc_%.cc: %.cc $(GLOBAL_DEPS)
|
moc_%.cc: %.cc $(GLOBAL_DEPS)
|
||||||
$(REPORT_BUILD)
|
|
||||||
$(ELOG) $(MOC) $(DEFINES) $(ACDEFINES) $(_VPATH_SRCS:.cc=.h) $(OUTOPTION)$@
|
$(ELOG) $(MOC) $(DEFINES) $(ACDEFINES) $(_VPATH_SRCS:.cc=.h) $(OUTOPTION)$@
|
||||||
|
|
||||||
ifdef ASFILES
|
ifdef ASFILES
|
||||||
@ -1207,12 +1197,10 @@ endif
|
|||||||
# Please keep the next two rules in sync.
|
# Please keep the next two rules in sync.
|
||||||
#
|
#
|
||||||
%.$(OBJ_SUFFIX): %.cc $(GLOBAL_DEPS)
|
%.$(OBJ_SUFFIX): %.cc $(GLOBAL_DEPS)
|
||||||
$(REPORT_BUILD)
|
|
||||||
@$(MAKE_DEPS_AUTO_CXX)
|
@$(MAKE_DEPS_AUTO_CXX)
|
||||||
$(ELOG) $(CCC) $(OUTOPTION)$@ -c $(COMPILE_CXXFLAGS) $(_VPATH_SRCS)
|
$(ELOG) $(CCC) $(OUTOPTION)$@ -c $(COMPILE_CXXFLAGS) $(_VPATH_SRCS)
|
||||||
|
|
||||||
%.$(OBJ_SUFFIX): %.cpp $(GLOBAL_DEPS)
|
%.$(OBJ_SUFFIX): %.cpp $(GLOBAL_DEPS)
|
||||||
$(REPORT_BUILD)
|
|
||||||
@$(MAKE_DEPS_AUTO_CXX)
|
@$(MAKE_DEPS_AUTO_CXX)
|
||||||
ifdef STRICT_CPLUSPLUS_SUFFIX
|
ifdef STRICT_CPLUSPLUS_SUFFIX
|
||||||
echo "#line 1 \"$*.cpp\"" | cat - $*.cpp > t_$*.cc
|
echo "#line 1 \"$*.cpp\"" | cat - $*.cpp > t_$*.cc
|
||||||
@ -1223,12 +1211,10 @@ else
|
|||||||
endif #STRICT_CPLUSPLUS_SUFFIX
|
endif #STRICT_CPLUSPLUS_SUFFIX
|
||||||
|
|
||||||
$(OBJ_PREFIX)%.$(OBJ_SUFFIX): %.mm $(GLOBAL_DEPS)
|
$(OBJ_PREFIX)%.$(OBJ_SUFFIX): %.mm $(GLOBAL_DEPS)
|
||||||
$(REPORT_BUILD)
|
|
||||||
@$(MAKE_DEPS_AUTO_CXX)
|
@$(MAKE_DEPS_AUTO_CXX)
|
||||||
$(ELOG) $(CCC) -o $@ -c $(COMPILE_CXXFLAGS) $(COMPILE_CMMFLAGS) $(_VPATH_SRCS)
|
$(ELOG) $(CCC) -o $@ -c $(COMPILE_CXXFLAGS) $(COMPILE_CMMFLAGS) $(_VPATH_SRCS)
|
||||||
|
|
||||||
$(OBJ_PREFIX)%.$(OBJ_SUFFIX): %.m $(GLOBAL_DEPS)
|
$(OBJ_PREFIX)%.$(OBJ_SUFFIX): %.m $(GLOBAL_DEPS)
|
||||||
$(REPORT_BUILD)
|
|
||||||
@$(MAKE_DEPS_AUTO_CC)
|
@$(MAKE_DEPS_AUTO_CC)
|
||||||
$(ELOG) $(CC) -o $@ -c $(COMPILE_CFLAGS) $(COMPILE_CMFLAGS) $(_VPATH_SRCS)
|
$(ELOG) $(CC) -o $@ -c $(COMPILE_CFLAGS) $(COMPILE_CMFLAGS) $(_VPATH_SRCS)
|
||||||
|
|
||||||
@ -1478,7 +1464,6 @@ XPIDL_DEPS = \
|
|||||||
$(NULL)
|
$(NULL)
|
||||||
|
|
||||||
$(XPIDL_GEN_DIR)/%.h: %.idl $(XPIDL_DEPS) $(XPIDL_GEN_DIR)/.done
|
$(XPIDL_GEN_DIR)/%.h: %.idl $(XPIDL_DEPS) $(XPIDL_GEN_DIR)/.done
|
||||||
$(REPORT_BUILD)
|
|
||||||
$(PYTHON_PATH) \
|
$(PYTHON_PATH) \
|
||||||
-I$(topsrcdir)/other-licenses/ply \
|
-I$(topsrcdir)/other-licenses/ply \
|
||||||
-I$(topsrcdir)/xpcom/idl-parser \
|
-I$(topsrcdir)/xpcom/idl-parser \
|
||||||
@ -1490,7 +1475,6 @@ ifndef NO_GEN_XPT
|
|||||||
# generate intermediate .xpt files into $(XPIDL_GEN_DIR), then link
|
# generate intermediate .xpt files into $(XPIDL_GEN_DIR), then link
|
||||||
# into $(XPIDL_MODULE).xpt and export it to $(FINAL_TARGET)/components.
|
# into $(XPIDL_MODULE).xpt and export it to $(FINAL_TARGET)/components.
|
||||||
$(XPIDL_GEN_DIR)/%.xpt: %.idl $(XPIDL_DEPS) $(XPIDL_GEN_DIR)/.done
|
$(XPIDL_GEN_DIR)/%.xpt: %.idl $(XPIDL_DEPS) $(XPIDL_GEN_DIR)/.done
|
||||||
$(REPORT_BUILD)
|
|
||||||
$(PYTHON_PATH) \
|
$(PYTHON_PATH) \
|
||||||
-I$(topsrcdir)/other-licenses/ply \
|
-I$(topsrcdir)/other-licenses/ply \
|
||||||
-I$(topsrcdir)/xpcom/idl-parser \
|
-I$(topsrcdir)/xpcom/idl-parser \
|
||||||
@ -1779,15 +1763,12 @@ define MAKE_DEPS_NOAUTO
|
|||||||
endef
|
endef
|
||||||
|
|
||||||
$(MDDEPDIR)/%.pp: %.c
|
$(MDDEPDIR)/%.pp: %.c
|
||||||
$(REPORT_BUILD)
|
|
||||||
@$(MAKE_DEPS_NOAUTO)
|
@$(MAKE_DEPS_NOAUTO)
|
||||||
|
|
||||||
$(MDDEPDIR)/%.pp: %.cpp
|
$(MDDEPDIR)/%.pp: %.cpp
|
||||||
$(REPORT_BUILD)
|
|
||||||
@$(MAKE_DEPS_NOAUTO)
|
@$(MAKE_DEPS_NOAUTO)
|
||||||
|
|
||||||
$(MDDEPDIR)/%.pp: %.s
|
$(MDDEPDIR)/%.pp: %.s
|
||||||
$(REPORT_BUILD)
|
|
||||||
@$(MAKE_DEPS_NOAUTO)
|
@$(MAKE_DEPS_NOAUTO)
|
||||||
|
|
||||||
ifneq (,$(OBJS)$(XPIDLSRCS)$(SIMPLE_PROGRAMS))
|
ifneq (,$(OBJS)$(XPIDLSRCS)$(SIMPLE_PROGRAMS))
|
||||||
|
15
configure.in
15
configure.in
@ -8503,10 +8503,15 @@ AC_SUBST(MOZ_POST_PROGRAM_COMMAND)
|
|||||||
# - MOZ_APP_DISPLAYNAME: Used in user-visible fields (DLL properties,
|
# - MOZ_APP_DISPLAYNAME: Used in user-visible fields (DLL properties,
|
||||||
# Mac Bundle name, Updater, Installer), it is typically used for nightly
|
# Mac Bundle name, Updater, Installer), it is typically used for nightly
|
||||||
# builds (e.g. Aurora for Firefox).
|
# builds (e.g. Aurora for Firefox).
|
||||||
|
# - MOZ_APP_VERSION: Defines the application version number.
|
||||||
# - MOZ_APP_NAME: Used for e.g. the binary program file name. If not set,
|
# - MOZ_APP_NAME: Used for e.g. the binary program file name. If not set,
|
||||||
# defaults to a lowercase form of MOZ_APP_BASENAME.
|
# defaults to a lowercase form of MOZ_APP_BASENAME.
|
||||||
# - MOZ_APP_PROFILE: When set, used for application.ini's
|
# - MOZ_APP_PROFILE: When set, used for application.ini's
|
||||||
# "Profile" field, which controls profile location.
|
# "Profile" field, which controls profile location.
|
||||||
|
# - MOZ_APP_ID: When set, used for application.ini's "ID" field, and
|
||||||
|
# crash reporter server url.
|
||||||
|
# - MOZ_PROFILE_MIGRATOR: When set, enables profile migrator.
|
||||||
|
# - MOZ_EXTENSION_MANAGER: When set, enabled extension manager.
|
||||||
|
|
||||||
if test -z "$MOZ_APP_NAME"; then
|
if test -z "$MOZ_APP_NAME"; then
|
||||||
MOZ_APP_NAME=`echo $MOZ_APP_BASENAME | tr A-Z a-z`
|
MOZ_APP_NAME=`echo $MOZ_APP_BASENAME | tr A-Z a-z`
|
||||||
@ -8517,6 +8522,9 @@ AC_SUBST(MOZ_APP_DISPLAYNAME)
|
|||||||
AC_SUBST(MOZ_APP_BASENAME)
|
AC_SUBST(MOZ_APP_BASENAME)
|
||||||
AC_SUBST(MOZ_APP_VENDOR)
|
AC_SUBST(MOZ_APP_VENDOR)
|
||||||
AC_SUBST(MOZ_APP_PROFILE)
|
AC_SUBST(MOZ_APP_PROFILE)
|
||||||
|
AC_SUBST(MOZ_APP_ID)
|
||||||
|
AC_SUBST(MOZ_PROFILE_MIGRATOR)
|
||||||
|
AC_SUBST(MOZ_EXTENSION_MANAGER)
|
||||||
AC_DEFINE_UNQUOTED(MOZ_APP_UA_NAME, "$MOZ_APP_UA_NAME")
|
AC_DEFINE_UNQUOTED(MOZ_APP_UA_NAME, "$MOZ_APP_UA_NAME")
|
||||||
AC_SUBST(MOZ_APP_UA_NAME)
|
AC_SUBST(MOZ_APP_UA_NAME)
|
||||||
AC_DEFINE_UNQUOTED(MOZ_APP_UA_VERSION, "$MOZ_APP_VERSION")
|
AC_DEFINE_UNQUOTED(MOZ_APP_UA_VERSION, "$MOZ_APP_VERSION")
|
||||||
@ -8527,6 +8535,13 @@ AC_SUBST(FIREFOX_VERSION)
|
|||||||
AC_DEFINE_UNQUOTED(MOZ_UA_BUILDID, "$MOZ_UA_BUILDID")
|
AC_DEFINE_UNQUOTED(MOZ_UA_BUILDID, "$MOZ_UA_BUILDID")
|
||||||
AC_SUBST(MOZ_UA_BUILDID)
|
AC_SUBST(MOZ_UA_BUILDID)
|
||||||
|
|
||||||
|
# We can't use the static application.ini data when building against
|
||||||
|
# a libxul SDK.
|
||||||
|
if test -n "$LIBXUL_SDK"; then
|
||||||
|
MOZ_APP_STATIC_INI=
|
||||||
|
fi
|
||||||
|
AC_SUBST(MOZ_APP_STATIC_INI)
|
||||||
|
|
||||||
AC_SUBST(MOZ_PKG_SPECIAL)
|
AC_SUBST(MOZ_PKG_SPECIAL)
|
||||||
|
|
||||||
AC_SUBST(MOZILLA_OFFICIAL)
|
AC_SUBST(MOZILLA_OFFICIAL)
|
||||||
|
@ -100,3 +100,4 @@ load 693212.xhtml
|
|||||||
load 698974-1.html
|
load 698974-1.html
|
||||||
load 700090-1.html
|
load 700090-1.html
|
||||||
load 700090-2.html
|
load 700090-2.html
|
||||||
|
load xhr_html_nullresponse.html
|
||||||
|
5
content/base/crashtests/xhr_html_nullresponse.html
Normal file
5
content/base/crashtests/xhr_html_nullresponse.html
Normal file
@ -0,0 +1,5 @@
|
|||||||
|
<!DOCTYPE html>
|
||||||
|
<html class="reftest-wait">
|
||||||
|
<script>
|
||||||
|
var xhr=new XMLHttpRequest();xhr.open("GET",window.location);xhr.overrideMimeType("text/html");xhr.onprogress=function(){if(xhr.readyState!=3)return;xhr.abort();document.documentElement.removeAttribute('class');};xhr.onabort=function(){xhr.responseText;};xhr.send();
|
||||||
|
</script>
|
@ -124,8 +124,8 @@ class Element;
|
|||||||
} // namespace mozilla
|
} // namespace mozilla
|
||||||
|
|
||||||
#define NS_IDOCUMENT_IID \
|
#define NS_IDOCUMENT_IID \
|
||||||
{ 0xc3e40e8e, 0x8b91, 0x424c, \
|
{ 0x184e0a3c, 0x1899, 0x417d, \
|
||||||
{ 0xbe, 0x9c, 0x9c, 0xc1, 0x76, 0xa7, 0xf7, 0x24 } }
|
{ 0xbf, 0xf4, 0x5a, 0x15, 0xe6, 0xe8, 0xaa, 0x94 } }
|
||||||
|
|
||||||
// Flag for AddStyleSheet().
|
// Flag for AddStyleSheet().
|
||||||
#define NS_STYLESHEET_FROM_CATALOG (1 << 0)
|
#define NS_STYLESHEET_FROM_CATALOG (1 << 0)
|
||||||
@ -1562,7 +1562,15 @@ public:
|
|||||||
virtual nsresult SetNavigationTiming(nsDOMNavigationTiming* aTiming) = 0;
|
virtual nsresult SetNavigationTiming(nsDOMNavigationTiming* aTiming) = 0;
|
||||||
|
|
||||||
virtual Element* FindImageMap(const nsAString& aNormalizedMapName) = 0;
|
virtual Element* FindImageMap(const nsAString& aNormalizedMapName) = 0;
|
||||||
|
|
||||||
|
// Called to notify the document that a listener on the "mozaudioavailable"
|
||||||
|
// event has been added. Media elements in the document need to ensure they
|
||||||
|
// fire the event.
|
||||||
|
virtual void NotifyAudioAvailableListener() = 0;
|
||||||
|
|
||||||
|
// Returns true if the document has "mozaudioavailable" event listeners.
|
||||||
|
virtual bool HasAudioAvailableListeners() = 0;
|
||||||
|
|
||||||
// Add aLink to the set of links that need their status resolved.
|
// Add aLink to the set of links that need their status resolved.
|
||||||
void RegisterPendingLinkUpdate(mozilla::dom::Link* aLink);
|
void RegisterPendingLinkUpdate(mozilla::dom::Link* aLink);
|
||||||
|
|
||||||
|
@ -8237,6 +8237,25 @@ nsDocument::AddImage(imgIRequest* aImage)
|
|||||||
return rv;
|
return rv;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
static void
|
||||||
|
NotifyAudioAvailableListener(nsIContent *aContent, void *aUnused)
|
||||||
|
{
|
||||||
|
#ifdef MOZ_MEDIA
|
||||||
|
nsCOMPtr<nsIDOMHTMLMediaElement> domMediaElem(do_QueryInterface(aContent));
|
||||||
|
if (domMediaElem) {
|
||||||
|
nsHTMLMediaElement* mediaElem = static_cast<nsHTMLMediaElement*>(aContent);
|
||||||
|
mediaElem->NotifyAudioAvailableListener();
|
||||||
|
}
|
||||||
|
#endif
|
||||||
|
}
|
||||||
|
|
||||||
|
void
|
||||||
|
nsDocument::NotifyAudioAvailableListener()
|
||||||
|
{
|
||||||
|
mHasAudioAvailableListener = true;
|
||||||
|
EnumerateFreezableElements(::NotifyAudioAvailableListener, nsnull);
|
||||||
|
}
|
||||||
|
|
||||||
nsresult
|
nsresult
|
||||||
nsDocument::RemoveImage(imgIRequest* aImage)
|
nsDocument::RemoveImage(imgIRequest* aImage)
|
||||||
{
|
{
|
||||||
|
@ -949,6 +949,13 @@ public:
|
|||||||
|
|
||||||
virtual Element* FindImageMap(const nsAString& aNormalizedMapName);
|
virtual Element* FindImageMap(const nsAString& aNormalizedMapName);
|
||||||
|
|
||||||
|
virtual void NotifyAudioAvailableListener();
|
||||||
|
|
||||||
|
bool HasAudioAvailableListeners()
|
||||||
|
{
|
||||||
|
return mHasAudioAvailableListener;
|
||||||
|
}
|
||||||
|
|
||||||
virtual Element* GetFullScreenElement();
|
virtual Element* GetFullScreenElement();
|
||||||
virtual void AsyncRequestFullScreen(Element* aElement);
|
virtual void AsyncRequestFullScreen(Element* aElement);
|
||||||
virtual void CancelFullScreen();
|
virtual void CancelFullScreen();
|
||||||
@ -1157,6 +1164,10 @@ protected:
|
|||||||
// Whether we currently require our images to animate
|
// Whether we currently require our images to animate
|
||||||
bool mAnimatingImages:1;
|
bool mAnimatingImages:1;
|
||||||
|
|
||||||
|
// Whether some node in this document has a listener for the
|
||||||
|
// "mozaudioavailable" event.
|
||||||
|
bool mHasAudioAvailableListener:1;
|
||||||
|
|
||||||
// Whether we are currently in full-screen mode, as per the DOM API.
|
// Whether we are currently in full-screen mode, as per the DOM API.
|
||||||
bool mIsFullScreen:1;
|
bool mIsFullScreen:1;
|
||||||
|
|
||||||
|
@ -2167,9 +2167,9 @@ static nsresult GetPartialTextRect(nsLayoutUtils::RectCallback* aCallback,
|
|||||||
continue;
|
continue;
|
||||||
|
|
||||||
// overlapping with the offset we want
|
// overlapping with the offset we want
|
||||||
f->EnsureTextRun();
|
f->EnsureTextRun(nsTextFrame::eInflated);
|
||||||
NS_ENSURE_TRUE(f->GetTextRun(), NS_ERROR_OUT_OF_MEMORY);
|
NS_ENSURE_TRUE(f->GetTextRun(nsTextFrame::eInflated), NS_ERROR_OUT_OF_MEMORY);
|
||||||
bool rtl = f->GetTextRun()->IsRightToLeft();
|
bool rtl = f->GetTextRun(nsTextFrame::eInflated)->IsRightToLeft();
|
||||||
nsRect r(f->GetOffsetTo(relativeTo), f->GetSize());
|
nsRect r(f->GetOffsetTo(relativeTo), f->GetSize());
|
||||||
if (fstart < aStartOffset) {
|
if (fstart < aStartOffset) {
|
||||||
// aStartOffset is within this frame
|
// aStartOffset is within this frame
|
||||||
|
@ -43,6 +43,8 @@
|
|||||||
#ifndef nsTextFragment_h___
|
#ifndef nsTextFragment_h___
|
||||||
#define nsTextFragment_h___
|
#define nsTextFragment_h___
|
||||||
|
|
||||||
|
#include "mozilla/Attributes.h"
|
||||||
|
|
||||||
#include "nsString.h"
|
#include "nsString.h"
|
||||||
#include "nsReadableUtils.h"
|
#include "nsReadableUtils.h"
|
||||||
#include "nsTraceRefcnt.h"
|
#include "nsTraceRefcnt.h"
|
||||||
@ -80,7 +82,7 @@ class nsCString;
|
|||||||
* This class does not have a virtual destructor therefore it is not
|
* This class does not have a virtual destructor therefore it is not
|
||||||
* meant to be subclassed.
|
* meant to be subclassed.
|
||||||
*/
|
*/
|
||||||
class NS_FINAL_CLASS nsTextFragment {
|
class nsTextFragment MOZ_FINAL {
|
||||||
public:
|
public:
|
||||||
static nsresult Init();
|
static nsresult Init();
|
||||||
static void Shutdown();
|
static void Shutdown();
|
||||||
|
@ -164,7 +164,8 @@ nsWebSocket::CloseConnection()
|
|||||||
|
|
||||||
if (mReadyState == nsIMozWebSocket::CONNECTING) {
|
if (mReadyState == nsIMozWebSocket::CONNECTING) {
|
||||||
SetReadyState(nsIMozWebSocket::CLOSED);
|
SetReadyState(nsIMozWebSocket::CLOSED);
|
||||||
mWebSocketChannel->Close(mClientReasonCode, mClientReason);
|
if (mWebSocketChannel)
|
||||||
|
mWebSocketChannel->Close(mClientReasonCode, mClientReason);
|
||||||
Disconnect();
|
Disconnect();
|
||||||
return NS_OK;
|
return NS_OK;
|
||||||
}
|
}
|
||||||
|
@ -1476,7 +1476,7 @@ nsXMLHttpRequest::IsSystemXHR()
|
|||||||
bool
|
bool
|
||||||
nsXMLHttpRequest::IsWaitingForHTMLCharset()
|
nsXMLHttpRequest::IsWaitingForHTMLCharset()
|
||||||
{
|
{
|
||||||
if (!mIsHtml) {
|
if (!mIsHtml || !mResponseXML) {
|
||||||
return false;
|
return false;
|
||||||
}
|
}
|
||||||
nsCOMPtr<nsIDocument> doc = do_QueryInterface(mResponseXML);
|
nsCOMPtr<nsIDocument> doc = do_QueryInterface(mResponseXML);
|
||||||
|
@ -614,7 +614,8 @@ WebGLContext::SetDimensions(PRInt32 width, PRInt32 height)
|
|||||||
|
|
||||||
PRInt32 status;
|
PRInt32 status;
|
||||||
nsCOMPtr<nsIGfxInfo> gfxInfo = do_GetService("@mozilla.org/gfx/info;1");
|
nsCOMPtr<nsIGfxInfo> gfxInfo = do_GetService("@mozilla.org/gfx/info;1");
|
||||||
if (mOptions.antialias &&
|
if (mOptions.antialias &&
|
||||||
|
gfxInfo &&
|
||||||
NS_SUCCEEDED(gfxInfo->GetFeatureStatus(nsIGfxInfo::FEATURE_WEBGL_MSAA, &status))) {
|
NS_SUCCEEDED(gfxInfo->GetFeatureStatus(nsIGfxInfo::FEATURE_WEBGL_MSAA, &status))) {
|
||||||
if (status == nsIGfxInfo::FEATURE_NO_INFO || forceMSAA) {
|
if (status == nsIGfxInfo::FEATURE_NO_INFO || forceMSAA) {
|
||||||
PRUint32 msaaLevel = Preferences::GetUint("webgl.msaa-level", 2);
|
PRUint32 msaaLevel = Preferences::GetUint("webgl.msaa-level", 2);
|
||||||
|
@ -2544,7 +2544,8 @@ GetScrollableLineHeight(nsIFrame* aTargetFrame)
|
|||||||
|
|
||||||
// Fall back to the font height of the target frame.
|
// Fall back to the font height of the target frame.
|
||||||
nsRefPtr<nsFontMetrics> fm;
|
nsRefPtr<nsFontMetrics> fm;
|
||||||
nsLayoutUtils::GetFontMetricsForFrame(aTargetFrame, getter_AddRefs(fm));
|
nsLayoutUtils::GetFontMetricsForFrame(aTargetFrame, getter_AddRefs(fm),
|
||||||
|
nsLayoutUtils::FontSizeInflationFor(aTargetFrame));
|
||||||
NS_ASSERTION(fm, "FontMetrics is null!");
|
NS_ASSERTION(fm, "FontMetrics is null!");
|
||||||
if (fm)
|
if (fm)
|
||||||
return fm->MaxHeight();
|
return fm->MaxHeight();
|
||||||
|
@ -178,6 +178,13 @@ public:
|
|||||||
// (no data has arrived for a while).
|
// (no data has arrived for a while).
|
||||||
void DownloadStalled();
|
void DownloadStalled();
|
||||||
|
|
||||||
|
// Called when a "MozAudioAvailable" event listener is added. The media
|
||||||
|
// element will then notify its decoder that it needs to make a copy of
|
||||||
|
// the audio data sent to hardware and dispatch it in "mozaudioavailable"
|
||||||
|
// events. This allows us to not perform the copy and thus reduce overhead
|
||||||
|
// in the common case where we don't have a "MozAudioAvailable" listener.
|
||||||
|
void NotifyAudioAvailableListener();
|
||||||
|
|
||||||
// Called by the media decoder and the video frame to get the
|
// Called by the media decoder and the video frame to get the
|
||||||
// ImageContainer containing the video data.
|
// ImageContainer containing the video data.
|
||||||
ImageContainer* GetImageContainer();
|
ImageContainer* GetImageContainer();
|
||||||
@ -301,12 +308,6 @@ public:
|
|||||||
void NotifyAudioAvailable(float* aFrameBuffer, PRUint32 aFrameBufferLength,
|
void NotifyAudioAvailable(float* aFrameBuffer, PRUint32 aFrameBufferLength,
|
||||||
float aTime);
|
float aTime);
|
||||||
|
|
||||||
/**
|
|
||||||
* Called in order to check whether some node (this window, its document,
|
|
||||||
* or content in that document) has a MozAudioAvailable event listener.
|
|
||||||
*/
|
|
||||||
bool MayHaveAudioAvailableEventListener();
|
|
||||||
|
|
||||||
virtual bool IsNodeOfType(PRUint32 aFlags) const;
|
virtual bool IsNodeOfType(PRUint32 aFlags) const;
|
||||||
|
|
||||||
/**
|
/**
|
||||||
|
@ -2008,13 +2008,16 @@ nsHTMLInputElement::PostHandleEvent(nsEventChainPostVisitor& aVisitor)
|
|||||||
// if it was cancelled and a radio button, then set the old
|
// if it was cancelled and a radio button, then set the old
|
||||||
// selected btn to TRUE. if it is a checkbox then set it to its
|
// selected btn to TRUE. if it is a checkbox then set it to its
|
||||||
// original value
|
// original value
|
||||||
nsCOMPtr<nsIDOMHTMLInputElement> selectedRadioButton =
|
if (oldType == NS_FORM_INPUT_RADIO) {
|
||||||
do_QueryInterface(aVisitor.mItemData);
|
nsCOMPtr<nsIDOMHTMLInputElement> selectedRadioButton =
|
||||||
if (selectedRadioButton) {
|
do_QueryInterface(aVisitor.mItemData);
|
||||||
selectedRadioButton->SetChecked(true);
|
if (selectedRadioButton) {
|
||||||
// If this one is no longer a radio button we must reset it back to
|
selectedRadioButton->SetChecked(true);
|
||||||
// false to cancel the action. See how the web of hack grows?
|
}
|
||||||
if (mType != NS_FORM_INPUT_RADIO) {
|
// If there was no checked radio button or this one is no longer a
|
||||||
|
// radio button we must reset it back to false to cancel the action.
|
||||||
|
// See how the web of hack grows?
|
||||||
|
if (!selectedRadioButton || mType != NS_FORM_INPUT_RADIO) {
|
||||||
DoSetChecked(false, true, true);
|
DoSetChecked(false, true, true);
|
||||||
}
|
}
|
||||||
} else if (oldType == NS_FORM_INPUT_CHECKBOX) {
|
} else if (oldType == NS_FORM_INPUT_CHECKBOX) {
|
||||||
|
@ -702,24 +702,6 @@ void nsHTMLMediaElement::NotifyAudioAvailable(float* aFrameBuffer,
|
|||||||
DispatchAudioAvailableEvent(frameBuffer.forget(), aFrameBufferLength, aTime);
|
DispatchAudioAvailableEvent(frameBuffer.forget(), aFrameBufferLength, aTime);
|
||||||
}
|
}
|
||||||
|
|
||||||
bool nsHTMLMediaElement::MayHaveAudioAvailableEventListener()
|
|
||||||
{
|
|
||||||
// Determine if the current element is focused, if it is not focused
|
|
||||||
// then we should not try to blur. Note: we allow for the case of
|
|
||||||
// |var a = new Audio()| with no parent document.
|
|
||||||
nsIDocument *document = GetDocument();
|
|
||||||
if (!document) {
|
|
||||||
return true;
|
|
||||||
}
|
|
||||||
|
|
||||||
nsPIDOMWindow *window = document->GetInnerWindow();
|
|
||||||
if (!window) {
|
|
||||||
return true;
|
|
||||||
}
|
|
||||||
|
|
||||||
return window->HasAudioAvailableEventListeners();
|
|
||||||
}
|
|
||||||
|
|
||||||
void nsHTMLMediaElement::LoadFromSourceChildren()
|
void nsHTMLMediaElement::LoadFromSourceChildren()
|
||||||
{
|
{
|
||||||
NS_ASSERTION(mDelayingLoadEvent,
|
NS_ASSERTION(mDelayingLoadEvent,
|
||||||
@ -1498,6 +1480,13 @@ nsresult nsHTMLMediaElement::BindToTree(nsIDocument* aDocument, nsIContent* aPar
|
|||||||
// The preload action depends on the value of the autoplay attribute.
|
// The preload action depends on the value of the autoplay attribute.
|
||||||
// It's value may have changed, so update it.
|
// It's value may have changed, so update it.
|
||||||
UpdatePreloadAction();
|
UpdatePreloadAction();
|
||||||
|
|
||||||
|
if (aDocument->HasAudioAvailableListeners()) {
|
||||||
|
// The document already has listeners for the "MozAudioAvailable"
|
||||||
|
// event, so the decoder must be notified so it initiates
|
||||||
|
// "MozAudioAvailable" event dispatch.
|
||||||
|
NotifyAudioAvailableListener();
|
||||||
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
return rv;
|
return rv;
|
||||||
@ -1914,6 +1903,10 @@ nsresult nsHTMLMediaElement::FinishDecoderSetup(nsMediaDecoder* aDecoder)
|
|||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
|
if (OwnerDoc()->HasAudioAvailableListeners()) {
|
||||||
|
NotifyAudioAvailableListener();
|
||||||
|
}
|
||||||
|
|
||||||
mBegun = true;
|
mBegun = true;
|
||||||
return rv;
|
return rv;
|
||||||
}
|
}
|
||||||
@ -2714,3 +2707,10 @@ NS_IMETHODIMP nsHTMLMediaElement::GetMozFragmentEnd(double *aTime)
|
|||||||
*aTime = (mFragmentEnd < 0.0 || mFragmentEnd > duration) ? duration : mFragmentEnd;
|
*aTime = (mFragmentEnd < 0.0 || mFragmentEnd > duration) ? duration : mFragmentEnd;
|
||||||
return NS_OK;
|
return NS_OK;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
void nsHTMLMediaElement::NotifyAudioAvailableListener()
|
||||||
|
{
|
||||||
|
if (mDecoder) {
|
||||||
|
mDecoder->NotifyAudioAvailableListener();
|
||||||
|
}
|
||||||
|
}
|
||||||
|
@ -84,7 +84,8 @@ nsAudioAvailableEventManager::nsAudioAvailableEventManager(nsBuiltinDecoder* aDe
|
|||||||
mSignalBufferLength(mDecoder->GetFrameBufferLength()),
|
mSignalBufferLength(mDecoder->GetFrameBufferLength()),
|
||||||
mNewSignalBufferLength(mSignalBufferLength),
|
mNewSignalBufferLength(mSignalBufferLength),
|
||||||
mSignalBufferPosition(0),
|
mSignalBufferPosition(0),
|
||||||
mReentrantMonitor("media.audioavailableeventmanager")
|
mReentrantMonitor("media.audioavailableeventmanager"),
|
||||||
|
mHasListener(false)
|
||||||
{
|
{
|
||||||
MOZ_COUNT_CTOR(nsAudioAvailableEventManager);
|
MOZ_COUNT_CTOR(nsAudioAvailableEventManager);
|
||||||
}
|
}
|
||||||
@ -104,6 +105,10 @@ void nsAudioAvailableEventManager::DispatchPendingEvents(PRUint64 aCurrentTime)
|
|||||||
{
|
{
|
||||||
ReentrantMonitorAutoEnter mon(mReentrantMonitor);
|
ReentrantMonitorAutoEnter mon(mReentrantMonitor);
|
||||||
|
|
||||||
|
if (!mHasListener) {
|
||||||
|
return;
|
||||||
|
}
|
||||||
|
|
||||||
while (mPendingEvents.Length() > 0) {
|
while (mPendingEvents.Length() > 0) {
|
||||||
nsAudioAvailableEventRunner* e =
|
nsAudioAvailableEventRunner* e =
|
||||||
(nsAudioAvailableEventRunner*)mPendingEvents[0].get();
|
(nsAudioAvailableEventRunner*)mPendingEvents[0].get();
|
||||||
@ -122,6 +127,10 @@ void nsAudioAvailableEventManager::QueueWrittenAudioData(AudioDataValue* aAudioD
|
|||||||
{
|
{
|
||||||
ReentrantMonitorAutoEnter mon(mReentrantMonitor);
|
ReentrantMonitorAutoEnter mon(mReentrantMonitor);
|
||||||
|
|
||||||
|
if (!mHasListener) {
|
||||||
|
return;
|
||||||
|
}
|
||||||
|
|
||||||
PRUint32 currentBufferSize = mNewSignalBufferLength;
|
PRUint32 currentBufferSize = mNewSignalBufferLength;
|
||||||
if (currentBufferSize == 0) {
|
if (currentBufferSize == 0) {
|
||||||
NS_WARNING("Decoder framebuffer length not set.");
|
NS_WARNING("Decoder framebuffer length not set.");
|
||||||
@ -212,6 +221,10 @@ void nsAudioAvailableEventManager::Drain(PRUint64 aEndTime)
|
|||||||
{
|
{
|
||||||
ReentrantMonitorAutoEnter mon(mReentrantMonitor);
|
ReentrantMonitorAutoEnter mon(mReentrantMonitor);
|
||||||
|
|
||||||
|
if (!mHasListener) {
|
||||||
|
return;
|
||||||
|
}
|
||||||
|
|
||||||
// Force all pending events to go now.
|
// Force all pending events to go now.
|
||||||
for (PRUint32 i = 0; i < mPendingEvents.Length(); ++i) {
|
for (PRUint32 i = 0; i < mPendingEvents.Length(); ++i) {
|
||||||
nsCOMPtr<nsIRunnable> event = mPendingEvents[i];
|
nsCOMPtr<nsIRunnable> event = mPendingEvents[i];
|
||||||
@ -245,3 +258,9 @@ void nsAudioAvailableEventManager::SetSignalBufferLength(PRUint32 aLength)
|
|||||||
mNewSignalBufferLength = aLength;
|
mNewSignalBufferLength = aLength;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
void nsAudioAvailableEventManager::NotifyAudioAvailableListener()
|
||||||
|
{
|
||||||
|
ReentrantMonitorAutoEnter mon(mReentrantMonitor);
|
||||||
|
|
||||||
|
mHasListener = true;
|
||||||
|
}
|
||||||
|
@ -80,6 +80,11 @@ public:
|
|||||||
// Called from the main and the state machine thread.
|
// Called from the main and the state machine thread.
|
||||||
void SetSignalBufferLength(PRUint32 aLength);
|
void SetSignalBufferLength(PRUint32 aLength);
|
||||||
|
|
||||||
|
// Called by the media element to notify the manager that there is a
|
||||||
|
// listener on the "MozAudioAvailable" event, and that we need to dispatch
|
||||||
|
// such events. Called from the main thread.
|
||||||
|
void NotifyAudioAvailableListener();
|
||||||
|
|
||||||
private:
|
private:
|
||||||
// The decoder associated with the event manager. The event manager shares
|
// The decoder associated with the event manager. The event manager shares
|
||||||
// the same lifetime as the decoder (the decoder holds a reference to the
|
// the same lifetime as the decoder (the decoder holds a reference to the
|
||||||
@ -108,6 +113,11 @@ private:
|
|||||||
// ReentrantMonitor for shared access to mPendingEvents queue or
|
// ReentrantMonitor for shared access to mPendingEvents queue or
|
||||||
// buffer length.
|
// buffer length.
|
||||||
ReentrantMonitor mReentrantMonitor;
|
ReentrantMonitor mReentrantMonitor;
|
||||||
|
|
||||||
|
// True if something in the owning document has a listener on the
|
||||||
|
// "MozAudioAvailable" event. If not, we don't need to bother copying played
|
||||||
|
// audio data and dispatching the event. Synchronized by mReentrantMonitor.
|
||||||
|
bool mHasListener;
|
||||||
};
|
};
|
||||||
|
|
||||||
#endif
|
#endif
|
||||||
|
@ -397,14 +397,9 @@ void nsBuiltinDecoder::AudioAvailable(float* aFrameBuffer,
|
|||||||
// to HTMLMediaElement::NotifyAudioAvailable().
|
// to HTMLMediaElement::NotifyAudioAvailable().
|
||||||
nsAutoArrayPtr<float> frameBuffer(aFrameBuffer);
|
nsAutoArrayPtr<float> frameBuffer(aFrameBuffer);
|
||||||
NS_ASSERTION(NS_IsMainThread(), "Should be on main thread.");
|
NS_ASSERTION(NS_IsMainThread(), "Should be on main thread.");
|
||||||
if (mShuttingDown) {
|
if (mShuttingDown || !mElement) {
|
||||||
return;
|
return;
|
||||||
}
|
}
|
||||||
|
|
||||||
if (!mElement || !mElement->MayHaveAudioAvailableEventListener()) {
|
|
||||||
return;
|
|
||||||
}
|
|
||||||
|
|
||||||
mElement->NotifyAudioAvailable(frameBuffer.forget(), aFrameBufferLength, aTime);
|
mElement->NotifyAudioAvailable(frameBuffer.forget(), aFrameBufferLength, aTime);
|
||||||
}
|
}
|
||||||
|
|
||||||
@ -1005,6 +1000,16 @@ void nsBuiltinDecoder::UpdatePlaybackOffset(PRInt64 aOffset)
|
|||||||
mPlaybackPosition = NS_MAX(aOffset, mPlaybackPosition);
|
mPlaybackPosition = NS_MAX(aOffset, mPlaybackPosition);
|
||||||
}
|
}
|
||||||
|
|
||||||
bool nsBuiltinDecoder::OnStateMachineThread() const {
|
bool nsBuiltinDecoder::OnStateMachineThread() const
|
||||||
|
{
|
||||||
return IsCurrentThread(nsBuiltinDecoderStateMachine::GetStateMachineThread());
|
return IsCurrentThread(nsBuiltinDecoderStateMachine::GetStateMachineThread());
|
||||||
}
|
}
|
||||||
|
|
||||||
|
void nsBuiltinDecoder::NotifyAudioAvailableListener()
|
||||||
|
{
|
||||||
|
NS_ASSERTION(NS_IsMainThread(), "Should be on main thread.");
|
||||||
|
if (mDecoderStateMachine) {
|
||||||
|
ReentrantMonitorAutoEnter mon(mReentrantMonitor);
|
||||||
|
mDecoderStateMachine->NotifyAudioAvailableListener();
|
||||||
|
}
|
||||||
|
}
|
||||||
|
@ -344,6 +344,10 @@ public:
|
|||||||
// Sets the current size of the framebuffer used in MozAudioAvailable events.
|
// Sets the current size of the framebuffer used in MozAudioAvailable events.
|
||||||
// Called on the state machine thread and the main thread.
|
// Called on the state machine thread and the main thread.
|
||||||
virtual void SetFrameBufferLength(PRUint32 aLength) = 0;
|
virtual void SetFrameBufferLength(PRUint32 aLength) = 0;
|
||||||
|
|
||||||
|
// Called when a "MozAudioAvailable" event listener is added to the media
|
||||||
|
// element. Called on the main thread.
|
||||||
|
virtual void NotifyAudioAvailableListener() = 0;
|
||||||
};
|
};
|
||||||
|
|
||||||
class nsBuiltinDecoder : public nsMediaDecoder
|
class nsBuiltinDecoder : public nsMediaDecoder
|
||||||
@ -610,6 +614,10 @@ class nsBuiltinDecoder : public nsMediaDecoder
|
|||||||
// Drop reference to state machine. Only called during shutdown dance.
|
// Drop reference to state machine. Only called during shutdown dance.
|
||||||
void ReleaseStateMachine() { mDecoderStateMachine = nsnull; }
|
void ReleaseStateMachine() { mDecoderStateMachine = nsnull; }
|
||||||
|
|
||||||
|
// Called when a "MozAudioAvailable" event listener is added to the media
|
||||||
|
// element. Called on the main thread.
|
||||||
|
virtual void NotifyAudioAvailableListener();
|
||||||
|
|
||||||
public:
|
public:
|
||||||
// Notifies the element that decoding has failed.
|
// Notifies the element that decoding has failed.
|
||||||
void DecodeError();
|
void DecodeError();
|
||||||
|
@ -2201,4 +2201,8 @@ nsIThread* nsBuiltinDecoderStateMachine::GetStateMachineThread()
|
|||||||
return StateMachineTracker::Instance().GetGlobalStateMachineThread();
|
return StateMachineTracker::Instance().GetGlobalStateMachineThread();
|
||||||
}
|
}
|
||||||
|
|
||||||
|
void nsBuiltinDecoderStateMachine::NotifyAudioAvailableListener()
|
||||||
|
{
|
||||||
|
mDecoder->GetReentrantMonitor().AssertCurrentThreadIn();
|
||||||
|
mEventManager.NotifyAudioAvailableListener();
|
||||||
|
}
|
||||||
|
@ -265,6 +265,10 @@ public:
|
|||||||
// Drop reference to decoder. Only called during shutdown dance.
|
// Drop reference to decoder. Only called during shutdown dance.
|
||||||
void ReleaseDecoder() { mDecoder = nsnull; }
|
void ReleaseDecoder() { mDecoder = nsnull; }
|
||||||
|
|
||||||
|
// Called when a "MozAudioAvailable" event listener is added to the media
|
||||||
|
// element. Called on the main thread.
|
||||||
|
void NotifyAudioAvailableListener();
|
||||||
|
|
||||||
protected:
|
protected:
|
||||||
|
|
||||||
// Returns true if we've got less than aAudioUsecs microseconds of decoded
|
// Returns true if we've got less than aAudioUsecs microseconds of decoded
|
||||||
|
@ -158,6 +158,11 @@ public:
|
|||||||
// Call in the main thread only.
|
// Call in the main thread only.
|
||||||
virtual bool IsEnded() const = 0;
|
virtual bool IsEnded() const = 0;
|
||||||
|
|
||||||
|
// Called when a "MozAudioAvailable" event listener is added. This enables
|
||||||
|
// the decoder to only dispatch "MozAudioAvailable" events when a
|
||||||
|
// handler exists, reducing overhead. Called on the main thread.
|
||||||
|
virtual void NotifyAudioAvailableListener() = 0;
|
||||||
|
|
||||||
struct Statistics {
|
struct Statistics {
|
||||||
// Estimate of the current playback rate (bytes/second).
|
// Estimate of the current playback rate (bytes/second).
|
||||||
double mPlaybackRate;
|
double mPlaybackRate;
|
||||||
|
@ -766,7 +766,6 @@ nsPIDOMWindow::nsPIDOMWindow(nsPIDOMWindow *aOuterWindow)
|
|||||||
mRunningTimeout(nsnull), mMutationBits(0), mIsDocumentLoaded(false),
|
mRunningTimeout(nsnull), mMutationBits(0), mIsDocumentLoaded(false),
|
||||||
mIsHandlingResizeEvent(false), mIsInnerWindow(aOuterWindow != nsnull),
|
mIsHandlingResizeEvent(false), mIsInnerWindow(aOuterWindow != nsnull),
|
||||||
mMayHavePaintEventListener(false), mMayHaveTouchEventListener(false),
|
mMayHavePaintEventListener(false), mMayHaveTouchEventListener(false),
|
||||||
mMayHaveAudioAvailableEventListener(false),
|
|
||||||
mMayHaveMouseEnterLeaveEventListener(false),
|
mMayHaveMouseEnterLeaveEventListener(false),
|
||||||
mIsModalContentWindow(false),
|
mIsModalContentWindow(false),
|
||||||
mIsActive(false), mIsBackground(false),
|
mIsActive(false), mIsBackground(false),
|
||||||
@ -10676,6 +10675,14 @@ nsGlobalModalWindow::SetNewDocument(nsIDocument *aDocument,
|
|||||||
aForceReuseInnerWindow);
|
aForceReuseInnerWindow);
|
||||||
}
|
}
|
||||||
|
|
||||||
|
void
|
||||||
|
nsGlobalWindow::SetHasAudioAvailableEventListeners()
|
||||||
|
{
|
||||||
|
if (mDoc) {
|
||||||
|
mDoc->NotifyAudioAvailableListener();
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
//*****************************************************************************
|
//*****************************************************************************
|
||||||
// nsGlobalWindow: Creator Function (This should go away)
|
// nsGlobalWindow: Creator Function (This should go away)
|
||||||
//*****************************************************************************
|
//*****************************************************************************
|
||||||
|
@ -447,6 +447,8 @@ public:
|
|||||||
// Prevent further dialogs in this (top level) window
|
// Prevent further dialogs in this (top level) window
|
||||||
void PreventFurtherDialogs();
|
void PreventFurtherDialogs();
|
||||||
|
|
||||||
|
virtual void SetHasAudioAvailableEventListeners();
|
||||||
|
|
||||||
nsIScriptContext *GetContextInternal()
|
nsIScriptContext *GetContextInternal()
|
||||||
{
|
{
|
||||||
if (mOuterWindow) {
|
if (mOuterWindow) {
|
||||||
|
@ -927,8 +927,6 @@ static const char js_zeal_option_str[] = JS_OPTIONS_DOT_STR "gczeal";
|
|||||||
static const char js_zeal_frequency_str[] = JS_OPTIONS_DOT_STR "gczeal.frequency";
|
static const char js_zeal_frequency_str[] = JS_OPTIONS_DOT_STR "gczeal.frequency";
|
||||||
static const char js_zeal_compartment_str[] = JS_OPTIONS_DOT_STR "gczeal.compartment_gc";
|
static const char js_zeal_compartment_str[] = JS_OPTIONS_DOT_STR "gczeal.compartment_gc";
|
||||||
#endif
|
#endif
|
||||||
static const char js_tracejit_content_str[] = JS_OPTIONS_DOT_STR "tracejit.content";
|
|
||||||
static const char js_tracejit_chrome_str[] = JS_OPTIONS_DOT_STR "tracejit.chrome";
|
|
||||||
static const char js_methodjit_content_str[] = JS_OPTIONS_DOT_STR "methodjit.content";
|
static const char js_methodjit_content_str[] = JS_OPTIONS_DOT_STR "methodjit.content";
|
||||||
static const char js_methodjit_chrome_str[] = JS_OPTIONS_DOT_STR "methodjit.chrome";
|
static const char js_methodjit_chrome_str[] = JS_OPTIONS_DOT_STR "methodjit.chrome";
|
||||||
static const char js_profiling_content_str[] = JS_OPTIONS_DOT_STR "jitprofiling.content";
|
static const char js_profiling_content_str[] = JS_OPTIONS_DOT_STR "jitprofiling.content";
|
||||||
@ -960,9 +958,6 @@ nsJSContext::JSOptionChangedCallback(const char *pref, void *data)
|
|||||||
// XXX components be covered by the chrome pref instead of the content one?
|
// XXX components be covered by the chrome pref instead of the content one?
|
||||||
nsCOMPtr<nsIDOMChromeWindow> chromeWindow(do_QueryInterface(global));
|
nsCOMPtr<nsIDOMChromeWindow> chromeWindow(do_QueryInterface(global));
|
||||||
|
|
||||||
bool useTraceJIT = Preferences::GetBool(chromeWindow ?
|
|
||||||
js_tracejit_chrome_str :
|
|
||||||
js_tracejit_content_str);
|
|
||||||
bool useMethodJIT = Preferences::GetBool(chromeWindow ?
|
bool useMethodJIT = Preferences::GetBool(chromeWindow ?
|
||||||
js_methodjit_chrome_str :
|
js_methodjit_chrome_str :
|
||||||
js_methodjit_content_str);
|
js_methodjit_content_str);
|
||||||
@ -980,7 +975,6 @@ nsJSContext::JSOptionChangedCallback(const char *pref, void *data)
|
|||||||
bool safeMode = false;
|
bool safeMode = false;
|
||||||
xr->GetInSafeMode(&safeMode);
|
xr->GetInSafeMode(&safeMode);
|
||||||
if (safeMode) {
|
if (safeMode) {
|
||||||
useTraceJIT = false;
|
|
||||||
useMethodJIT = false;
|
useMethodJIT = false;
|
||||||
useProfiling = false;
|
useProfiling = false;
|
||||||
usePCCounts = false;
|
usePCCounts = false;
|
||||||
@ -990,11 +984,6 @@ nsJSContext::JSOptionChangedCallback(const char *pref, void *data)
|
|||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
if (useTraceJIT)
|
|
||||||
newDefaultJSOptions |= JSOPTION_JIT;
|
|
||||||
else
|
|
||||||
newDefaultJSOptions &= ~JSOPTION_JIT;
|
|
||||||
|
|
||||||
if (useMethodJIT)
|
if (useMethodJIT)
|
||||||
newDefaultJSOptions |= JSOPTION_METHODJIT;
|
newDefaultJSOptions |= JSOPTION_METHODJIT;
|
||||||
else
|
else
|
||||||
|
@ -80,8 +80,8 @@ class nsIArray;
|
|||||||
class nsPIWindowRoot;
|
class nsPIWindowRoot;
|
||||||
|
|
||||||
#define NS_PIDOMWINDOW_IID \
|
#define NS_PIDOMWINDOW_IID \
|
||||||
{ 0x8ce567b5, 0xcc8d, 0x410b, \
|
{ 0x9db588f7, 0x3472, 0x45d0, \
|
||||||
{ 0xa2, 0x7b, 0x07, 0xaf, 0x31, 0xc0, 0x33, 0xb8 } }
|
{ 0x9f, 0x9b, 0x95, 0xca, 0xf6, 0x4d, 0x1a, 0xb1 } }
|
||||||
|
|
||||||
class nsPIDOMWindow : public nsIDOMWindowInternal
|
class nsPIDOMWindow : public nsIDOMWindowInternal
|
||||||
{
|
{
|
||||||
@ -457,23 +457,11 @@ public:
|
|||||||
return mMayHaveTouchEventListener;
|
return mMayHaveTouchEventListener;
|
||||||
}
|
}
|
||||||
|
|
||||||
/**
|
|
||||||
* Call this to check whether some node (this window, its document,
|
|
||||||
* or content in that document) has a MozAudioAvailable event listener.
|
|
||||||
*/
|
|
||||||
bool HasAudioAvailableEventListeners()
|
|
||||||
{
|
|
||||||
return mMayHaveAudioAvailableEventListener;
|
|
||||||
}
|
|
||||||
|
|
||||||
/**
|
/**
|
||||||
* Call this to indicate that some node (this window, its document,
|
* Call this to indicate that some node (this window, its document,
|
||||||
* or content in that document) has a MozAudioAvailable event listener.
|
* or content in that document) has a "MozAudioAvailable" event listener.
|
||||||
*/
|
*/
|
||||||
void SetHasAudioAvailableEventListeners()
|
virtual void SetHasAudioAvailableEventListeners() = 0;
|
||||||
{
|
|
||||||
mMayHaveAudioAvailableEventListener = true;
|
|
||||||
}
|
|
||||||
|
|
||||||
/**
|
/**
|
||||||
* Call this to check whether some node (this window, its document,
|
* Call this to check whether some node (this window, its document,
|
||||||
@ -657,7 +645,6 @@ protected:
|
|||||||
bool mIsInnerWindow;
|
bool mIsInnerWindow;
|
||||||
bool mMayHavePaintEventListener;
|
bool mMayHavePaintEventListener;
|
||||||
bool mMayHaveTouchEventListener;
|
bool mMayHaveTouchEventListener;
|
||||||
bool mMayHaveAudioAvailableEventListener;
|
|
||||||
bool mMayHaveMouseEnterLeaveEventListener;
|
bool mMayHaveMouseEnterLeaveEventListener;
|
||||||
|
|
||||||
// This variable is used on both inner and outer windows (and they
|
// This variable is used on both inner and outer windows (and they
|
||||||
|
@ -408,7 +408,8 @@ AsyncConnectionHelper::Init()
|
|||||||
already_AddRefed<nsDOMEvent>
|
already_AddRefed<nsDOMEvent>
|
||||||
AsyncConnectionHelper::CreateSuccessEvent()
|
AsyncConnectionHelper::CreateSuccessEvent()
|
||||||
{
|
{
|
||||||
return CreateGenericEvent(NS_LITERAL_STRING(SUCCESS_EVT_STR));
|
return CreateGenericEvent(NS_LITERAL_STRING(SUCCESS_EVT_STR),
|
||||||
|
eDoesNotBubble, eNotCancelable);
|
||||||
}
|
}
|
||||||
|
|
||||||
nsresult
|
nsresult
|
||||||
@ -453,7 +454,8 @@ AsyncConnectionHelper::OnError()
|
|||||||
|
|
||||||
// Make an error event and fire it at the target.
|
// Make an error event and fire it at the target.
|
||||||
nsRefPtr<nsDOMEvent> event =
|
nsRefPtr<nsDOMEvent> event =
|
||||||
CreateGenericEvent(NS_LITERAL_STRING(ERROR_EVT_STR), true);
|
CreateGenericEvent(NS_LITERAL_STRING(ERROR_EVT_STR), eDoesBubble,
|
||||||
|
eCancelable);
|
||||||
if (!event) {
|
if (!event) {
|
||||||
NS_ERROR("Failed to create event!");
|
NS_ERROR("Failed to create event!");
|
||||||
return;
|
return;
|
||||||
|
@ -379,12 +379,14 @@ NS_IMPL_CYCLE_COLLECTION_CLASS(IDBDatabase)
|
|||||||
|
|
||||||
NS_IMPL_CYCLE_COLLECTION_TRAVERSE_BEGIN_INHERITED(IDBDatabase,
|
NS_IMPL_CYCLE_COLLECTION_TRAVERSE_BEGIN_INHERITED(IDBDatabase,
|
||||||
nsDOMEventTargetHelper)
|
nsDOMEventTargetHelper)
|
||||||
|
NS_IMPL_CYCLE_COLLECTION_TRAVERSE_NSCOMPTR(mOnAbortListener)
|
||||||
NS_IMPL_CYCLE_COLLECTION_TRAVERSE_NSCOMPTR(mOnErrorListener)
|
NS_IMPL_CYCLE_COLLECTION_TRAVERSE_NSCOMPTR(mOnErrorListener)
|
||||||
NS_IMPL_CYCLE_COLLECTION_TRAVERSE_NSCOMPTR(mOnVersionChangeListener)
|
NS_IMPL_CYCLE_COLLECTION_TRAVERSE_NSCOMPTR(mOnVersionChangeListener)
|
||||||
NS_IMPL_CYCLE_COLLECTION_TRAVERSE_END
|
NS_IMPL_CYCLE_COLLECTION_TRAVERSE_END
|
||||||
|
|
||||||
NS_IMPL_CYCLE_COLLECTION_UNLINK_BEGIN_INHERITED(IDBDatabase,
|
NS_IMPL_CYCLE_COLLECTION_UNLINK_BEGIN_INHERITED(IDBDatabase,
|
||||||
nsDOMEventTargetHelper)
|
nsDOMEventTargetHelper)
|
||||||
|
NS_IMPL_CYCLE_COLLECTION_UNLINK_NSCOMPTR(mOnAbortListener)
|
||||||
NS_IMPL_CYCLE_COLLECTION_UNLINK_NSCOMPTR(mOnErrorListener)
|
NS_IMPL_CYCLE_COLLECTION_UNLINK_NSCOMPTR(mOnErrorListener)
|
||||||
NS_IMPL_CYCLE_COLLECTION_UNLINK_NSCOMPTR(mOnVersionChangeListener)
|
NS_IMPL_CYCLE_COLLECTION_UNLINK_NSCOMPTR(mOnVersionChangeListener)
|
||||||
|
|
||||||
@ -725,6 +727,19 @@ IDBDatabase::Close()
|
|||||||
return NS_OK;
|
return NS_OK;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
NS_IMETHODIMP
|
||||||
|
IDBDatabase::SetOnabort(nsIDOMEventListener* aAbortListener)
|
||||||
|
{
|
||||||
|
return RemoveAddEventListener(NS_LITERAL_STRING(ABORT_EVT_STR),
|
||||||
|
mOnAbortListener, aAbortListener);
|
||||||
|
}
|
||||||
|
|
||||||
|
NS_IMETHODIMP
|
||||||
|
IDBDatabase::GetOnabort(nsIDOMEventListener** aAbortListener)
|
||||||
|
{
|
||||||
|
return GetInnerEventListener(mOnAbortListener, aAbortListener);
|
||||||
|
}
|
||||||
|
|
||||||
NS_IMETHODIMP
|
NS_IMETHODIMP
|
||||||
IDBDatabase::SetOnerror(nsIDOMEventListener* aErrorListener)
|
IDBDatabase::SetOnerror(nsIDOMEventListener* aErrorListener)
|
||||||
{
|
{
|
||||||
@ -764,7 +779,8 @@ IDBDatabase::PostHandleEvent(nsEventChainPostVisitor& aVisitor)
|
|||||||
NS_ENSURE_SUCCESS(rv, rv);
|
NS_ENSURE_SUCCESS(rv, rv);
|
||||||
|
|
||||||
if (type.EqualsLiteral(ERROR_EVT_STR)) {
|
if (type.EqualsLiteral(ERROR_EVT_STR)) {
|
||||||
nsRefPtr<nsDOMEvent> duplicateEvent = CreateGenericEvent(type);
|
nsRefPtr<nsDOMEvent> duplicateEvent =
|
||||||
|
CreateGenericEvent(type, eDoesNotBubble, eNotCancelable);
|
||||||
NS_ENSURE_STATE(duplicateEvent);
|
NS_ENSURE_STATE(duplicateEvent);
|
||||||
|
|
||||||
nsCOMPtr<nsIDOMEventTarget> target(do_QueryInterface(mOwner));
|
nsCOMPtr<nsIDOMEventTarget> target(do_QueryInterface(mOwner));
|
||||||
|
@ -161,6 +161,7 @@ private:
|
|||||||
bool mRunningVersionChange;
|
bool mRunningVersionChange;
|
||||||
|
|
||||||
// Only touched on the main thread.
|
// Only touched on the main thread.
|
||||||
|
nsRefPtr<nsDOMEventListenerWrapper> mOnAbortListener;
|
||||||
nsRefPtr<nsDOMEventListenerWrapper> mOnErrorListener;
|
nsRefPtr<nsDOMEventListenerWrapper> mOnErrorListener;
|
||||||
nsRefPtr<nsDOMEventListenerWrapper> mOnVersionChangeListener;
|
nsRefPtr<nsDOMEventListenerWrapper> mOnVersionChangeListener;
|
||||||
};
|
};
|
||||||
|
@ -78,11 +78,13 @@ private:
|
|||||||
|
|
||||||
already_AddRefed<nsDOMEvent>
|
already_AddRefed<nsDOMEvent>
|
||||||
mozilla::dom::indexedDB::CreateGenericEvent(const nsAString& aType,
|
mozilla::dom::indexedDB::CreateGenericEvent(const nsAString& aType,
|
||||||
bool aBubblesAndCancelable)
|
Bubbles aBubbles,
|
||||||
|
Cancelable aCancelable)
|
||||||
{
|
{
|
||||||
nsRefPtr<nsDOMEvent> event(new nsDOMEvent(nsnull, nsnull));
|
nsRefPtr<nsDOMEvent> event(new nsDOMEvent(nsnull, nsnull));
|
||||||
nsresult rv = event->InitEvent(aType, aBubblesAndCancelable,
|
nsresult rv = event->InitEvent(aType,
|
||||||
aBubblesAndCancelable);
|
aBubbles == eDoesBubble ? true : false,
|
||||||
|
aCancelable == eCancelable ? true : false);
|
||||||
NS_ENSURE_SUCCESS(rv, nsnull);
|
NS_ENSURE_SUCCESS(rv, nsnull);
|
||||||
|
|
||||||
rv = event->SetTrusted(true);
|
rv = event->SetTrusted(true);
|
||||||
@ -91,17 +93,6 @@ mozilla::dom::indexedDB::CreateGenericEvent(const nsAString& aType,
|
|||||||
return event.forget();
|
return event.forget();
|
||||||
}
|
}
|
||||||
|
|
||||||
already_AddRefed<nsIRunnable>
|
|
||||||
mozilla::dom::indexedDB::CreateGenericEventRunnable(const nsAString& aType,
|
|
||||||
nsIDOMEventTarget* aTarget)
|
|
||||||
{
|
|
||||||
nsCOMPtr<nsIDOMEvent> event(CreateGenericEvent(aType));
|
|
||||||
NS_ENSURE_TRUE(event, nsnull);
|
|
||||||
|
|
||||||
nsCOMPtr<nsIRunnable> runnable(new EventFiringRunnable(aTarget, event));
|
|
||||||
return runnable.forget();
|
|
||||||
}
|
|
||||||
|
|
||||||
// static
|
// static
|
||||||
already_AddRefed<nsDOMEvent>
|
already_AddRefed<nsDOMEvent>
|
||||||
IDBVersionChangeEvent::CreateInternal(const nsAString& aType,
|
IDBVersionChangeEvent::CreateInternal(const nsAString& aType,
|
||||||
|
@ -59,13 +59,20 @@
|
|||||||
|
|
||||||
BEGIN_INDEXEDDB_NAMESPACE
|
BEGIN_INDEXEDDB_NAMESPACE
|
||||||
|
|
||||||
|
enum Bubbles {
|
||||||
|
eDoesNotBubble,
|
||||||
|
eDoesBubble
|
||||||
|
};
|
||||||
|
|
||||||
|
enum Cancelable {
|
||||||
|
eNotCancelable,
|
||||||
|
eCancelable
|
||||||
|
};
|
||||||
|
|
||||||
already_AddRefed<nsDOMEvent>
|
already_AddRefed<nsDOMEvent>
|
||||||
CreateGenericEvent(const nsAString& aType,
|
CreateGenericEvent(const nsAString& aType,
|
||||||
bool aBubblesAndCancelable = false);
|
Bubbles aBubbles,
|
||||||
|
Cancelable aCancelable);
|
||||||
already_AddRefed<nsIRunnable>
|
|
||||||
CreateGenericEventRunnable(const nsAString& aType,
|
|
||||||
nsIDOMEventTarget* aTarget);
|
|
||||||
|
|
||||||
class IDBVersionChangeEvent : public nsDOMEvent,
|
class IDBVersionChangeEvent : public nsDOMEvent,
|
||||||
public nsIIDBVersionChangeEvent
|
public nsIIDBVersionChangeEvent
|
||||||
|
@ -1160,12 +1160,12 @@ OpenKeyCursorHelper::DoDatabaseWork(mozIStorageConnection* aConnection)
|
|||||||
queryStart);
|
queryStart);
|
||||||
mRangeKey = mKeyRange->Upper();
|
mRangeKey = mKeyRange->Upper();
|
||||||
}
|
}
|
||||||
mContinueQuery = queryStart + NS_LITERAL_CSTRING(" AND ( ( value = :") +
|
mContinueQuery = queryStart + NS_LITERAL_CSTRING(" AND value >= :") +
|
||||||
currentKey + NS_LITERAL_CSTRING(" AND ") + keyColumn +
|
currentKey + NS_LITERAL_CSTRING(" AND ( value > :") +
|
||||||
|
currentKey + NS_LITERAL_CSTRING(" OR ") + keyColumn +
|
||||||
NS_LITERAL_CSTRING(" > :") + objectKey +
|
NS_LITERAL_CSTRING(" > :") + objectKey +
|
||||||
NS_LITERAL_CSTRING(" ) OR ( value > :") + currentKey +
|
NS_LITERAL_CSTRING(" )") + directionClause +
|
||||||
NS_LITERAL_CSTRING(" ) )") + directionClause +
|
NS_LITERAL_CSTRING(" LIMIT ");
|
||||||
NS_LITERAL_CSTRING(" LIMIT 1");
|
|
||||||
mContinueToQuery = queryStart + NS_LITERAL_CSTRING(" AND value >= :") +
|
mContinueToQuery = queryStart + NS_LITERAL_CSTRING(" AND value >= :") +
|
||||||
currentKey + NS_LITERAL_CSTRING(" LIMIT ");
|
currentKey + NS_LITERAL_CSTRING(" LIMIT ");
|
||||||
break;
|
break;
|
||||||
@ -1178,7 +1178,7 @@ OpenKeyCursorHelper::DoDatabaseWork(mozIStorageConnection* aConnection)
|
|||||||
}
|
}
|
||||||
mContinueQuery = queryStart + NS_LITERAL_CSTRING(" AND value > :") +
|
mContinueQuery = queryStart + NS_LITERAL_CSTRING(" AND value > :") +
|
||||||
currentKey + directionClause +
|
currentKey + directionClause +
|
||||||
NS_LITERAL_CSTRING(" LIMIT 1");
|
NS_LITERAL_CSTRING(" LIMIT ");
|
||||||
mContinueToQuery = queryStart + NS_LITERAL_CSTRING(" AND value >= :") +
|
mContinueToQuery = queryStart + NS_LITERAL_CSTRING(" AND value >= :") +
|
||||||
currentKey + directionClause +
|
currentKey + directionClause +
|
||||||
NS_LITERAL_CSTRING(" LIMIT ");
|
NS_LITERAL_CSTRING(" LIMIT ");
|
||||||
@ -1190,12 +1190,13 @@ OpenKeyCursorHelper::DoDatabaseWork(mozIStorageConnection* aConnection)
|
|||||||
queryStart);
|
queryStart);
|
||||||
mRangeKey = mKeyRange->Lower();
|
mRangeKey = mKeyRange->Lower();
|
||||||
}
|
}
|
||||||
mContinueQuery = queryStart + NS_LITERAL_CSTRING(" AND ( ( value = :") +
|
|
||||||
currentKey + NS_LITERAL_CSTRING(" AND ") + keyColumn +
|
mContinueQuery = queryStart + NS_LITERAL_CSTRING(" AND value <= :") +
|
||||||
|
currentKey + NS_LITERAL_CSTRING(" AND ( value < :") +
|
||||||
|
currentKey + NS_LITERAL_CSTRING(" OR ") + keyColumn +
|
||||||
NS_LITERAL_CSTRING(" < :") + objectKey +
|
NS_LITERAL_CSTRING(" < :") + objectKey +
|
||||||
NS_LITERAL_CSTRING(" ) OR ( value < :") + currentKey +
|
NS_LITERAL_CSTRING(" ) ") + directionClause +
|
||||||
NS_LITERAL_CSTRING(" ) )") + directionClause +
|
NS_LITERAL_CSTRING(" LIMIT ");
|
||||||
NS_LITERAL_CSTRING(" LIMIT 1");
|
|
||||||
mContinueToQuery = queryStart + NS_LITERAL_CSTRING(" AND value <= :") +
|
mContinueToQuery = queryStart + NS_LITERAL_CSTRING(" AND value <= :") +
|
||||||
currentKey + NS_LITERAL_CSTRING(" LIMIT ");
|
currentKey + NS_LITERAL_CSTRING(" LIMIT ");
|
||||||
break;
|
break;
|
||||||
@ -1208,7 +1209,7 @@ OpenKeyCursorHelper::DoDatabaseWork(mozIStorageConnection* aConnection)
|
|||||||
}
|
}
|
||||||
mContinueQuery = queryStart + NS_LITERAL_CSTRING(" AND value < :") +
|
mContinueQuery = queryStart + NS_LITERAL_CSTRING(" AND value < :") +
|
||||||
currentKey + directionClause +
|
currentKey + directionClause +
|
||||||
NS_LITERAL_CSTRING(" LIMIT 1");
|
NS_LITERAL_CSTRING(" LIMIT ");
|
||||||
mContinueToQuery = queryStart + NS_LITERAL_CSTRING(" AND value <= :") +
|
mContinueToQuery = queryStart + NS_LITERAL_CSTRING(" AND value <= :") +
|
||||||
currentKey + directionClause +
|
currentKey + directionClause +
|
||||||
NS_LITERAL_CSTRING(" LIMIT ");
|
NS_LITERAL_CSTRING(" LIMIT ");
|
||||||
@ -1251,7 +1252,7 @@ OpenCursorHelper::DoDatabaseWork(mozIStorageConnection* aConnection)
|
|||||||
if (mIndex->IsAutoIncrement()) {
|
if (mIndex->IsAutoIncrement()) {
|
||||||
objectTable.AssignLiteral("ai_object_data");
|
objectTable.AssignLiteral("ai_object_data");
|
||||||
objectDataIdColumn.AssignLiteral("ai_object_data_id");
|
objectDataIdColumn.AssignLiteral("ai_object_data_id");
|
||||||
keyValueColumn.AssignLiteral("id");
|
keyValueColumn.AssignLiteral("ai_object_data_id");
|
||||||
if (mIndex->IsUnique()) {
|
if (mIndex->IsUnique()) {
|
||||||
indexTable.AssignLiteral("ai_unique_index_data");
|
indexTable.AssignLiteral("ai_unique_index_data");
|
||||||
}
|
}
|
||||||
@ -1262,7 +1263,7 @@ OpenCursorHelper::DoDatabaseWork(mozIStorageConnection* aConnection)
|
|||||||
else {
|
else {
|
||||||
objectTable.AssignLiteral("object_data");
|
objectTable.AssignLiteral("object_data");
|
||||||
objectDataIdColumn.AssignLiteral("object_data_id");
|
objectDataIdColumn.AssignLiteral("object_data_id");
|
||||||
keyValueColumn.AssignLiteral("key_value");
|
keyValueColumn.AssignLiteral("object_data_key");
|
||||||
if (mIndex->IsUnique()) {
|
if (mIndex->IsUnique()) {
|
||||||
indexTable.AssignLiteral("unique_index_data");
|
indexTable.AssignLiteral("unique_index_data");
|
||||||
}
|
}
|
||||||
@ -1271,11 +1272,8 @@ OpenCursorHelper::DoDatabaseWork(mozIStorageConnection* aConnection)
|
|||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
NS_NAMED_LITERAL_CSTRING(id, "id");
|
|
||||||
|
|
||||||
nsCString value = indexTable + NS_LITERAL_CSTRING(".value");
|
nsCString value = indexTable + NS_LITERAL_CSTRING(".value");
|
||||||
nsCString data = objectTable + NS_LITERAL_CSTRING(".data");
|
nsCString keyValue = indexTable + NS_LITERAL_CSTRING(".") + keyValueColumn;
|
||||||
nsCString keyValue = objectTable + NS_LITERAL_CSTRING(".") + keyValueColumn;
|
|
||||||
|
|
||||||
nsCString keyRangeClause;
|
nsCString keyRangeClause;
|
||||||
if (mKeyRange) {
|
if (mKeyRange) {
|
||||||
@ -1304,16 +1302,21 @@ OpenCursorHelper::DoDatabaseWork(mozIStorageConnection* aConnection)
|
|||||||
NS_NOTREACHED("Unknown direction!");
|
NS_NOTREACHED("Unknown direction!");
|
||||||
}
|
}
|
||||||
|
|
||||||
nsCString firstQuery = NS_LITERAL_CSTRING("SELECT ") + value +
|
NS_NAMED_LITERAL_CSTRING(id, "id");
|
||||||
NS_LITERAL_CSTRING(", ") + keyValue +
|
NS_NAMED_LITERAL_CSTRING(dot, ".");
|
||||||
NS_LITERAL_CSTRING(", ") + data +
|
NS_NAMED_LITERAL_CSTRING(commaspace, ", ");
|
||||||
NS_LITERAL_CSTRING(" FROM ") + objectTable +
|
|
||||||
NS_LITERAL_CSTRING(" INNER JOIN ") + indexTable +
|
nsCString data = objectTable + NS_LITERAL_CSTRING(".data");
|
||||||
NS_LITERAL_CSTRING(" ON ") + indexTable +
|
|
||||||
NS_LITERAL_CSTRING(".") + objectDataIdColumn +
|
nsCString firstQuery = NS_LITERAL_CSTRING("SELECT ") + value + commaspace +
|
||||||
NS_LITERAL_CSTRING(" = ") + objectTable +
|
keyValue + commaspace + data +
|
||||||
NS_LITERAL_CSTRING(".id WHERE ") + indexTable +
|
NS_LITERAL_CSTRING(" FROM ") + indexTable +
|
||||||
NS_LITERAL_CSTRING(".index_id = :id") +
|
NS_LITERAL_CSTRING(" INNER JOIN ") + objectTable +
|
||||||
|
NS_LITERAL_CSTRING(" ON ") + indexTable + dot +
|
||||||
|
objectDataIdColumn + NS_LITERAL_CSTRING(" = ") +
|
||||||
|
objectTable + dot + id +
|
||||||
|
NS_LITERAL_CSTRING(" WHERE ") + indexTable +
|
||||||
|
NS_LITERAL_CSTRING(".index_id = :") + id +
|
||||||
keyRangeClause + directionClause +
|
keyRangeClause + directionClause +
|
||||||
NS_LITERAL_CSTRING(" LIMIT 1");
|
NS_LITERAL_CSTRING(" LIMIT 1");
|
||||||
|
|
||||||
@ -1352,20 +1355,29 @@ OpenCursorHelper::DoDatabaseWork(mozIStorageConnection* aConnection)
|
|||||||
|
|
||||||
// Now we need to make the query to get the next match.
|
// Now we need to make the query to get the next match.
|
||||||
nsCAutoString queryStart = NS_LITERAL_CSTRING("SELECT ") + value +
|
nsCAutoString queryStart = NS_LITERAL_CSTRING("SELECT ") + value +
|
||||||
NS_LITERAL_CSTRING(", ") + keyValue +
|
commaspace + keyValue + commaspace + data +
|
||||||
NS_LITERAL_CSTRING(", ") + data +
|
NS_LITERAL_CSTRING(" FROM ") + indexTable +
|
||||||
NS_LITERAL_CSTRING(" FROM ") + objectTable +
|
NS_LITERAL_CSTRING(" INNER JOIN ") + objectTable +
|
||||||
NS_LITERAL_CSTRING(" INNER JOIN ") + indexTable +
|
NS_LITERAL_CSTRING(" ON ") + indexTable + dot +
|
||||||
NS_LITERAL_CSTRING(" ON ") + indexTable +
|
objectDataIdColumn + NS_LITERAL_CSTRING(" = ") +
|
||||||
NS_LITERAL_CSTRING(".") + objectDataIdColumn +
|
objectTable + dot + id +
|
||||||
NS_LITERAL_CSTRING(" = ") + objectTable +
|
NS_LITERAL_CSTRING(" WHERE ") + indexTable +
|
||||||
NS_LITERAL_CSTRING(".id WHERE ") + indexTable +
|
NS_LITERAL_CSTRING(".index_id = :") + id;
|
||||||
NS_LITERAL_CSTRING(".index_id = :id");
|
|
||||||
|
|
||||||
NS_NAMED_LITERAL_CSTRING(currentKey, "current_key");
|
NS_NAMED_LITERAL_CSTRING(currentKey, "current_key");
|
||||||
NS_NAMED_LITERAL_CSTRING(rangeKey, "range_key");
|
NS_NAMED_LITERAL_CSTRING(rangeKey, "range_key");
|
||||||
NS_NAMED_LITERAL_CSTRING(objectKey, "object_key");
|
NS_NAMED_LITERAL_CSTRING(objectKey, "object_key");
|
||||||
|
|
||||||
|
NS_NAMED_LITERAL_CSTRING(andStr, " AND ");
|
||||||
|
NS_NAMED_LITERAL_CSTRING(orStr, " OR ");
|
||||||
|
NS_NAMED_LITERAL_CSTRING(ge, " >= :");
|
||||||
|
NS_NAMED_LITERAL_CSTRING(gt, " > :");
|
||||||
|
NS_NAMED_LITERAL_CSTRING(le, " <= :");
|
||||||
|
NS_NAMED_LITERAL_CSTRING(lt, " < :");
|
||||||
|
NS_NAMED_LITERAL_CSTRING(openparen, " ( ");
|
||||||
|
NS_NAMED_LITERAL_CSTRING(closeparen, " ) ");
|
||||||
|
NS_NAMED_LITERAL_CSTRING(limit, " LIMIT ");
|
||||||
|
|
||||||
switch (mDirection) {
|
switch (mDirection) {
|
||||||
case nsIIDBCursor::NEXT:
|
case nsIIDBCursor::NEXT:
|
||||||
if (mKeyRange && !mKeyRange->Upper().IsUnset()) {
|
if (mKeyRange && !mKeyRange->Upper().IsUnset()) {
|
||||||
@ -1373,18 +1385,11 @@ OpenCursorHelper::DoDatabaseWork(mozIStorageConnection* aConnection)
|
|||||||
queryStart);
|
queryStart);
|
||||||
mRangeKey = mKeyRange->Upper();
|
mRangeKey = mKeyRange->Upper();
|
||||||
}
|
}
|
||||||
mContinueQuery = queryStart + NS_LITERAL_CSTRING(" AND ( ( ") +
|
mContinueQuery = queryStart + andStr + value + ge + currentKey + andStr +
|
||||||
value + NS_LITERAL_CSTRING(" = :") + currentKey +
|
openparen + value + gt + currentKey + orStr + keyValue +
|
||||||
NS_LITERAL_CSTRING(" AND ") + keyValue +
|
gt + objectKey + closeparen + directionClause + limit;
|
||||||
NS_LITERAL_CSTRING(" > :") + objectKey +
|
mContinueToQuery = queryStart + andStr + value + ge + currentKey +
|
||||||
NS_LITERAL_CSTRING(" ) OR ( ") + value +
|
directionClause + limit;
|
||||||
NS_LITERAL_CSTRING(" > :") + currentKey +
|
|
||||||
NS_LITERAL_CSTRING(" ) )") + directionClause +
|
|
||||||
NS_LITERAL_CSTRING(" LIMIT 1");
|
|
||||||
mContinueToQuery = queryStart + NS_LITERAL_CSTRING(" AND ") + value +
|
|
||||||
NS_LITERAL_CSTRING(" >= :") +
|
|
||||||
currentKey + directionClause +
|
|
||||||
NS_LITERAL_CSTRING(" LIMIT 1");
|
|
||||||
break;
|
break;
|
||||||
|
|
||||||
case nsIIDBCursor::NEXT_NO_DUPLICATE:
|
case nsIIDBCursor::NEXT_NO_DUPLICATE:
|
||||||
@ -1393,12 +1398,10 @@ OpenCursorHelper::DoDatabaseWork(mozIStorageConnection* aConnection)
|
|||||||
queryStart);
|
queryStart);
|
||||||
mRangeKey = mKeyRange->Upper();
|
mRangeKey = mKeyRange->Upper();
|
||||||
}
|
}
|
||||||
mContinueQuery = queryStart + NS_LITERAL_CSTRING(" AND ") + value +
|
mContinueQuery = queryStart + andStr + value + gt + currentKey +
|
||||||
NS_LITERAL_CSTRING(" > :") + currentKey +
|
directionClause + limit;
|
||||||
directionClause + NS_LITERAL_CSTRING(" LIMIT 1");
|
mContinueToQuery = queryStart + andStr + value + ge + currentKey +
|
||||||
mContinueToQuery = queryStart + NS_LITERAL_CSTRING(" AND ") + value +
|
directionClause + limit;
|
||||||
NS_LITERAL_CSTRING(" >= :") + currentKey +
|
|
||||||
directionClause + NS_LITERAL_CSTRING(" LIMIT 1");
|
|
||||||
break;
|
break;
|
||||||
|
|
||||||
case nsIIDBCursor::PREV:
|
case nsIIDBCursor::PREV:
|
||||||
@ -1407,18 +1410,11 @@ OpenCursorHelper::DoDatabaseWork(mozIStorageConnection* aConnection)
|
|||||||
queryStart);
|
queryStart);
|
||||||
mRangeKey = mKeyRange->Lower();
|
mRangeKey = mKeyRange->Lower();
|
||||||
}
|
}
|
||||||
mContinueQuery = queryStart + NS_LITERAL_CSTRING(" AND ( ( ") +
|
mContinueQuery = queryStart + andStr + value + le + currentKey + andStr +
|
||||||
value + NS_LITERAL_CSTRING(" = :") + currentKey +
|
openparen + value + lt + currentKey + orStr + keyValue +
|
||||||
NS_LITERAL_CSTRING(" AND ") + keyValue +
|
lt + objectKey + closeparen + directionClause + limit;
|
||||||
NS_LITERAL_CSTRING(" < :") + objectKey +
|
mContinueToQuery = queryStart + andStr + value + le + currentKey +
|
||||||
NS_LITERAL_CSTRING(" ) OR ( ") + value +
|
directionClause + limit;
|
||||||
NS_LITERAL_CSTRING(" < :") + currentKey +
|
|
||||||
NS_LITERAL_CSTRING(" ) )") + directionClause +
|
|
||||||
NS_LITERAL_CSTRING(" LIMIT 1");
|
|
||||||
mContinueToQuery = queryStart + NS_LITERAL_CSTRING(" AND ") + value +
|
|
||||||
NS_LITERAL_CSTRING(" <= :") +
|
|
||||||
currentKey + directionClause +
|
|
||||||
NS_LITERAL_CSTRING(" LIMIT 1");
|
|
||||||
break;
|
break;
|
||||||
|
|
||||||
case nsIIDBCursor::PREV_NO_DUPLICATE:
|
case nsIIDBCursor::PREV_NO_DUPLICATE:
|
||||||
@ -1427,12 +1423,10 @@ OpenCursorHelper::DoDatabaseWork(mozIStorageConnection* aConnection)
|
|||||||
queryStart);
|
queryStart);
|
||||||
mRangeKey = mKeyRange->Lower();
|
mRangeKey = mKeyRange->Lower();
|
||||||
}
|
}
|
||||||
mContinueQuery = queryStart + NS_LITERAL_CSTRING(" AND ") + value +
|
mContinueQuery = queryStart + andStr + value + lt + currentKey +
|
||||||
NS_LITERAL_CSTRING(" < :") + currentKey +
|
directionClause +limit;
|
||||||
directionClause + NS_LITERAL_CSTRING(" LIMIT 1");
|
mContinueToQuery = queryStart + andStr + value + le + currentKey +
|
||||||
mContinueToQuery = queryStart + NS_LITERAL_CSTRING(" AND ") + value +
|
directionClause + limit;
|
||||||
NS_LITERAL_CSTRING(" <= :") + currentKey +
|
|
||||||
directionClause + NS_LITERAL_CSTRING(" LIMIT 1");
|
|
||||||
break;
|
break;
|
||||||
|
|
||||||
default:
|
default:
|
||||||
|
@ -428,7 +428,9 @@ GetKeyFromValue(JSContext* aCx,
|
|||||||
Key& aKey)
|
Key& aKey)
|
||||||
{
|
{
|
||||||
NS_ASSERTION(aCx, "Null pointer!");
|
NS_ASSERTION(aCx, "Null pointer!");
|
||||||
NS_ASSERTION(!JSVAL_IS_PRIMITIVE(aVal), "Why are we here!?");
|
// aVal can be primitive iff the key path is empty.
|
||||||
|
NS_ASSERTION(!JSVAL_IS_PRIMITIVE(aVal) || aKeyPath.IsEmpty(),
|
||||||
|
"Why are we here!?");
|
||||||
NS_ASSERTION(IDBObjectStore::IsValidKeyPath(aCx, aKeyPath),
|
NS_ASSERTION(IDBObjectStore::IsValidKeyPath(aCx, aKeyPath),
|
||||||
"This will explode!");
|
"This will explode!");
|
||||||
|
|
||||||
@ -580,7 +582,6 @@ IDBObjectStore::GetKeyPathValueFromStructuredData(const PRUint8* aData,
|
|||||||
{
|
{
|
||||||
NS_ASSERTION(aData, "Null pointer!");
|
NS_ASSERTION(aData, "Null pointer!");
|
||||||
NS_ASSERTION(aDataLength, "Empty data!");
|
NS_ASSERTION(aDataLength, "Empty data!");
|
||||||
NS_ASSERTION(!aKeyPath.IsEmpty(), "Empty keyPath!");
|
|
||||||
NS_ASSERTION(aCx, "Null pointer!");
|
NS_ASSERTION(aCx, "Null pointer!");
|
||||||
|
|
||||||
JSAutoRequest ar(aCx);
|
JSAutoRequest ar(aCx);
|
||||||
@ -592,7 +593,7 @@ IDBObjectStore::GetKeyPathValueFromStructuredData(const PRUint8* aData,
|
|||||||
return NS_ERROR_DOM_DATA_CLONE_ERR;
|
return NS_ERROR_DOM_DATA_CLONE_ERR;
|
||||||
}
|
}
|
||||||
|
|
||||||
if (JSVAL_IS_PRIMITIVE(clone)) {
|
if (JSVAL_IS_PRIMITIVE(clone) && !aKeyPath.IsEmpty()) {
|
||||||
// This isn't an object, so just leave the key unset.
|
// This isn't an object, so just leave the key unset.
|
||||||
aValue.Unset();
|
aValue.Unset();
|
||||||
return NS_OK;
|
return NS_OK;
|
||||||
@ -614,7 +615,7 @@ IDBObjectStore::GetIndexUpdateInfo(ObjectStoreInfo* aObjectStoreInfo,
|
|||||||
JSObject* cloneObj = nsnull;
|
JSObject* cloneObj = nsnull;
|
||||||
|
|
||||||
PRUint32 count = aObjectStoreInfo->indexes.Length();
|
PRUint32 count = aObjectStoreInfo->indexes.Length();
|
||||||
if (count && !JSVAL_IS_PRIMITIVE(aObject)) {
|
if (count) {
|
||||||
if (!aUpdateInfoArray.SetCapacity(count)) {
|
if (!aUpdateInfoArray.SetCapacity(count)) {
|
||||||
NS_ERROR("Out of memory!");
|
NS_ERROR("Out of memory!");
|
||||||
return NS_ERROR_OUT_OF_MEMORY;
|
return NS_ERROR_OUT_OF_MEMORY;
|
||||||
@ -623,6 +624,10 @@ IDBObjectStore::GetIndexUpdateInfo(ObjectStoreInfo* aObjectStoreInfo,
|
|||||||
for (PRUint32 indexesIndex = 0; indexesIndex < count; indexesIndex++) {
|
for (PRUint32 indexesIndex = 0; indexesIndex < count; indexesIndex++) {
|
||||||
const IndexInfo& indexInfo = aObjectStoreInfo->indexes[indexesIndex];
|
const IndexInfo& indexInfo = aObjectStoreInfo->indexes[indexesIndex];
|
||||||
|
|
||||||
|
if (JSVAL_IS_PRIMITIVE(aObject) && !indexInfo.keyPath.IsEmpty()) {
|
||||||
|
continue;
|
||||||
|
}
|
||||||
|
|
||||||
Key value;
|
Key value;
|
||||||
nsresult rv = GetKeyFromValue(aCx, aObject, indexInfo.keyPath, value);
|
nsresult rv = GetKeyFromValue(aCx, aObject, indexInfo.keyPath, value);
|
||||||
NS_ENSURE_SUCCESS(rv, rv);
|
NS_ENSURE_SUCCESS(rv, rv);
|
||||||
@ -664,7 +669,6 @@ IDBObjectStore::UpdateIndexes(IDBTransaction* aTransaction,
|
|||||||
#endif
|
#endif
|
||||||
|
|
||||||
PRUint32 indexCount = aUpdateInfoArray.Length();
|
PRUint32 indexCount = aUpdateInfoArray.Length();
|
||||||
NS_ASSERTION(indexCount, "Don't call me!");
|
|
||||||
|
|
||||||
nsCOMPtr<mozIStorageStatement> stmt;
|
nsCOMPtr<mozIStorageStatement> stmt;
|
||||||
nsresult rv;
|
nsresult rv;
|
||||||
@ -702,34 +706,59 @@ IDBObjectStore::UpdateIndexes(IDBTransaction* aTransaction,
|
|||||||
|
|
||||||
NS_ASSERTION(aObjectDataId != LL_MININT, "Bad objectData id!");
|
NS_ASSERTION(aObjectDataId != LL_MININT, "Bad objectData id!");
|
||||||
|
|
||||||
for (PRUint32 indexIndex = 0; indexIndex < indexCount; indexIndex++) {
|
NS_NAMED_LITERAL_CSTRING(indexId, "index_id");
|
||||||
const IndexUpdateInfo& updateInfo = aUpdateInfoArray[indexIndex];
|
NS_NAMED_LITERAL_CSTRING(objectDataId, "object_data_id");
|
||||||
|
NS_NAMED_LITERAL_CSTRING(objectDataKey, "object_data_key");
|
||||||
|
NS_NAMED_LITERAL_CSTRING(value, "value");
|
||||||
|
|
||||||
stmt = aTransaction->IndexUpdateStatement(updateInfo.info.autoIncrement,
|
if (aOverwrite) {
|
||||||
updateInfo.info.unique,
|
stmt = aTransaction->IndexDataDeleteStatement(aAutoIncrement, false);
|
||||||
aOverwrite);
|
|
||||||
NS_ENSURE_TRUE(stmt, NS_ERROR_FAILURE);
|
NS_ENSURE_TRUE(stmt, NS_ERROR_FAILURE);
|
||||||
|
|
||||||
mozStorageStatementScoper scoper2(stmt);
|
mozStorageStatementScoper scoper2(stmt);
|
||||||
|
|
||||||
rv = stmt->BindInt64ByName(NS_LITERAL_CSTRING("index_id"),
|
rv = stmt->BindInt64ByName(objectDataId, aObjectDataId);
|
||||||
updateInfo.info.id);
|
|
||||||
NS_ENSURE_SUCCESS(rv, rv);
|
NS_ENSURE_SUCCESS(rv, rv);
|
||||||
|
|
||||||
rv = stmt->BindInt64ByName(NS_LITERAL_CSTRING("object_data_id"),
|
rv = stmt->Execute();
|
||||||
aObjectDataId);
|
NS_ENSURE_SUCCESS(rv, rv);
|
||||||
|
|
||||||
|
stmt = aTransaction->IndexDataDeleteStatement(aAutoIncrement, true);
|
||||||
|
NS_ENSURE_TRUE(stmt, NS_ERROR_FAILURE);
|
||||||
|
|
||||||
|
mozStorageStatementScoper scoper3(stmt);
|
||||||
|
|
||||||
|
rv = stmt->BindInt64ByName(objectDataId, aObjectDataId);
|
||||||
|
NS_ENSURE_SUCCESS(rv, rv);
|
||||||
|
|
||||||
|
rv = stmt->Execute();
|
||||||
|
NS_ENSURE_SUCCESS(rv, rv);
|
||||||
|
}
|
||||||
|
|
||||||
|
for (PRUint32 indexIndex = 0; indexIndex < indexCount; indexIndex++) {
|
||||||
|
const IndexUpdateInfo& updateInfo = aUpdateInfoArray[indexIndex];
|
||||||
|
|
||||||
|
NS_ASSERTION(updateInfo.info.autoIncrement == aAutoIncrement, "Huh?!");
|
||||||
|
|
||||||
|
// Insert new values.
|
||||||
|
stmt = aTransaction->IndexDataInsertStatement(aAutoIncrement,
|
||||||
|
updateInfo.info.unique);
|
||||||
|
NS_ENSURE_TRUE(stmt, NS_ERROR_FAILURE);
|
||||||
|
|
||||||
|
mozStorageStatementScoper scoper4(stmt);
|
||||||
|
|
||||||
|
rv = stmt->BindInt64ByName(indexId, updateInfo.info.id);
|
||||||
|
NS_ENSURE_SUCCESS(rv, rv);
|
||||||
|
|
||||||
|
rv = stmt->BindInt64ByName(objectDataId, aObjectDataId);
|
||||||
NS_ENSURE_SUCCESS(rv, rv);
|
NS_ENSURE_SUCCESS(rv, rv);
|
||||||
|
|
||||||
if (!updateInfo.info.autoIncrement) {
|
if (!updateInfo.info.autoIncrement) {
|
||||||
rv =
|
rv = aObjectStoreKey.BindToStatement(stmt, objectDataKey);
|
||||||
aObjectStoreKey.BindToStatement(stmt,
|
|
||||||
NS_LITERAL_CSTRING("object_data_key"));
|
|
||||||
NS_ENSURE_SUCCESS(rv, rv);
|
NS_ENSURE_SUCCESS(rv, rv);
|
||||||
}
|
}
|
||||||
|
|
||||||
rv =
|
rv = updateInfo.value.BindToStatement(stmt, value);
|
||||||
updateInfo.value.BindToStatementAllowUnset(stmt,
|
|
||||||
NS_LITERAL_CSTRING("value"));
|
|
||||||
NS_ENSURE_SUCCESS(rv, rv);
|
NS_ENSURE_SUCCESS(rv, rv);
|
||||||
|
|
||||||
rv = stmt->Execute();
|
rv = stmt->Execute();
|
||||||
@ -1310,10 +1339,6 @@ IDBObjectStore::CreateIndex(const nsAString& aName,
|
|||||||
{
|
{
|
||||||
NS_PRECONDITION(NS_IsMainThread(), "Wrong thread!");
|
NS_PRECONDITION(NS_IsMainThread(), "Wrong thread!");
|
||||||
|
|
||||||
if (aKeyPath.IsEmpty()) {
|
|
||||||
return NS_ERROR_DOM_INDEXEDDB_NON_TRANSIENT_ERR;
|
|
||||||
}
|
|
||||||
|
|
||||||
if (!IsValidKeyPath(aCx, aKeyPath)) {
|
if (!IsValidKeyPath(aCx, aKeyPath)) {
|
||||||
return NS_ERROR_DOM_SYNTAX_ERR;
|
return NS_ERROR_DOM_SYNTAX_ERR;
|
||||||
}
|
}
|
||||||
@ -1718,7 +1743,7 @@ AddHelper::DoDatabaseWork(mozIStorageConnection* aConnection)
|
|||||||
}
|
}
|
||||||
|
|
||||||
// Update our indexes if needed.
|
// Update our indexes if needed.
|
||||||
if (!mIndexUpdateInfo.IsEmpty()) {
|
if (mOverwrite || !mIndexUpdateInfo.IsEmpty()) {
|
||||||
PRInt64 objectDataId = autoIncrement ? mKey.ToInteger() : LL_MININT;
|
PRInt64 objectDataId = autoIncrement ? mKey.ToInteger() : LL_MININT;
|
||||||
rv = IDBObjectStore::UpdateIndexes(mTransaction, osid, mKey,
|
rv = IDBObjectStore::UpdateIndexes(mTransaction, osid, mKey,
|
||||||
autoIncrement, mOverwrite,
|
autoIncrement, mOverwrite,
|
||||||
@ -1930,7 +1955,8 @@ OpenCursorHelper::DoDatabaseWork(mozIStorageConnection* aConnection)
|
|||||||
nsCString firstQuery = NS_LITERAL_CSTRING("SELECT ") + keyColumn +
|
nsCString firstQuery = NS_LITERAL_CSTRING("SELECT ") + keyColumn +
|
||||||
NS_LITERAL_CSTRING(", data FROM ") + table +
|
NS_LITERAL_CSTRING(", data FROM ") + table +
|
||||||
NS_LITERAL_CSTRING(" WHERE object_store_id = :") +
|
NS_LITERAL_CSTRING(" WHERE object_store_id = :") +
|
||||||
id + keyRangeClause + directionClause;
|
id + keyRangeClause + directionClause +
|
||||||
|
NS_LITERAL_CSTRING(" LIMIT 1");
|
||||||
|
|
||||||
nsCOMPtr<mozIStorageStatement> stmt =
|
nsCOMPtr<mozIStorageStatement> stmt =
|
||||||
mTransaction->GetCachedStatement(firstQuery);
|
mTransaction->GetCachedStatement(firstQuery);
|
||||||
@ -2009,7 +2035,7 @@ OpenCursorHelper::DoDatabaseWork(mozIStorageConnection* aConnection)
|
|||||||
NS_LITERAL_CSTRING(", data FROM ") + table +
|
NS_LITERAL_CSTRING(", data FROM ") + table +
|
||||||
NS_LITERAL_CSTRING(" WHERE object_store_id = :") + id +
|
NS_LITERAL_CSTRING(" WHERE object_store_id = :") + id +
|
||||||
keyRangeClause + directionClause +
|
keyRangeClause + directionClause +
|
||||||
NS_LITERAL_CSTRING(" LIMIT 1");
|
NS_LITERAL_CSTRING(" LIMIT ");
|
||||||
|
|
||||||
mContinueToQuery = NS_LITERAL_CSTRING("SELECT ") + keyColumn +
|
mContinueToQuery = NS_LITERAL_CSTRING("SELECT ") + keyColumn +
|
||||||
NS_LITERAL_CSTRING(", data FROM ") + table +
|
NS_LITERAL_CSTRING(", data FROM ") + table +
|
||||||
@ -2215,8 +2241,8 @@ CreateIndexHelper::InsertDataFromObjectStore(mozIStorageConnection* aConnection)
|
|||||||
bool hasResult;
|
bool hasResult;
|
||||||
while (NS_SUCCEEDED(stmt->ExecuteStep(&hasResult)) && hasResult) {
|
while (NS_SUCCEEDED(stmt->ExecuteStep(&hasResult)) && hasResult) {
|
||||||
nsCOMPtr<mozIStorageStatement> insertStmt =
|
nsCOMPtr<mozIStorageStatement> insertStmt =
|
||||||
mTransaction->IndexUpdateStatement(mIndex->IsAutoIncrement(),
|
mTransaction->IndexDataInsertStatement(mIndex->IsAutoIncrement(),
|
||||||
mIndex->IsUnique(), false);
|
mIndex->IsUnique());
|
||||||
NS_ENSURE_TRUE(insertStmt, NS_ERROR_DOM_INDEXEDDB_UNKNOWN_ERR);
|
NS_ENSURE_TRUE(insertStmt, NS_ERROR_DOM_INDEXEDDB_UNKNOWN_ERR);
|
||||||
|
|
||||||
mozStorageStatementScoper scoper2(insertStmt);
|
mozStorageStatementScoper scoper2(insertStmt);
|
||||||
|
@ -394,28 +394,13 @@ IDBTransaction::AddStatement(bool aCreate,
|
|||||||
}
|
}
|
||||||
|
|
||||||
already_AddRefed<mozIStorageStatement>
|
already_AddRefed<mozIStorageStatement>
|
||||||
IDBTransaction::IndexUpdateStatement(bool aAutoIncrement,
|
IDBTransaction::IndexDataInsertStatement(bool aAutoIncrement,
|
||||||
bool aUnique,
|
bool aUnique)
|
||||||
bool aOverwrite)
|
|
||||||
{
|
{
|
||||||
if (aAutoIncrement) {
|
if (aAutoIncrement) {
|
||||||
if (aUnique) {
|
if (aUnique) {
|
||||||
if (aOverwrite) {
|
|
||||||
return GetCachedStatement(
|
|
||||||
"INSERT OR REPLACE INTO ai_unique_index_data "
|
|
||||||
"(index_id, ai_object_data_id, value) "
|
|
||||||
"VALUES (:index_id, :object_data_id, :value)"
|
|
||||||
);
|
|
||||||
}
|
|
||||||
return GetCachedStatement(
|
return GetCachedStatement(
|
||||||
"INSERT INTO ai_unique_index_data "
|
"INSERT INTO ai_unique_index_data "
|
||||||
"(index_id, aI_object_data_id, value) "
|
|
||||||
"VALUES (:index_id, :object_data_id, :value)"
|
|
||||||
);
|
|
||||||
}
|
|
||||||
if (aOverwrite) {
|
|
||||||
return GetCachedStatement(
|
|
||||||
"INSERT OR REPLACE INTO ai_index_data "
|
|
||||||
"(index_id, ai_object_data_id, value) "
|
"(index_id, ai_object_data_id, value) "
|
||||||
"VALUES (:index_id, :object_data_id, :value)"
|
"VALUES (:index_id, :object_data_id, :value)"
|
||||||
);
|
);
|
||||||
@ -427,26 +412,12 @@ IDBTransaction::IndexUpdateStatement(bool aAutoIncrement,
|
|||||||
);
|
);
|
||||||
}
|
}
|
||||||
if (aUnique) {
|
if (aUnique) {
|
||||||
if (aOverwrite) {
|
|
||||||
return GetCachedStatement(
|
|
||||||
"INSERT OR REPLACE INTO unique_index_data "
|
|
||||||
"(index_id, object_data_id, object_data_key, value) "
|
|
||||||
"VALUES (:index_id, :object_data_id, :object_data_key, :value)"
|
|
||||||
);
|
|
||||||
}
|
|
||||||
return GetCachedStatement(
|
return GetCachedStatement(
|
||||||
"INSERT INTO unique_index_data "
|
"INSERT INTO unique_index_data "
|
||||||
"(index_id, object_data_id, object_data_key, value) "
|
"(index_id, object_data_id, object_data_key, value) "
|
||||||
"VALUES (:index_id, :object_data_id, :object_data_key, :value)"
|
"VALUES (:index_id, :object_data_id, :object_data_key, :value)"
|
||||||
);
|
);
|
||||||
}
|
}
|
||||||
if (aOverwrite) {
|
|
||||||
return GetCachedStatement(
|
|
||||||
"INSERT INTO index_data ("
|
|
||||||
"index_id, object_data_id, object_data_key, value) "
|
|
||||||
"VALUES (:index_id, :object_data_id, :object_data_key, :value)"
|
|
||||||
);
|
|
||||||
}
|
|
||||||
return GetCachedStatement(
|
return GetCachedStatement(
|
||||||
"INSERT INTO index_data ("
|
"INSERT INTO index_data ("
|
||||||
"index_id, object_data_id, object_data_key, value) "
|
"index_id, object_data_id, object_data_key, value) "
|
||||||
@ -454,6 +425,34 @@ IDBTransaction::IndexUpdateStatement(bool aAutoIncrement,
|
|||||||
);
|
);
|
||||||
}
|
}
|
||||||
|
|
||||||
|
already_AddRefed<mozIStorageStatement>
|
||||||
|
IDBTransaction::IndexDataDeleteStatement(bool aAutoIncrement,
|
||||||
|
bool aUnique)
|
||||||
|
{
|
||||||
|
if (aAutoIncrement) {
|
||||||
|
if (aUnique) {
|
||||||
|
return GetCachedStatement(
|
||||||
|
"DELETE FROM ai_unique_index_data "
|
||||||
|
"WHERE ai_object_data_id = :object_data_id"
|
||||||
|
);
|
||||||
|
}
|
||||||
|
return GetCachedStatement(
|
||||||
|
"DELETE FROM ai_index_data "
|
||||||
|
"WHERE ai_object_data_id = :object_data_id"
|
||||||
|
);
|
||||||
|
}
|
||||||
|
if (aUnique) {
|
||||||
|
return GetCachedStatement(
|
||||||
|
"DELETE FROM unique_index_data "
|
||||||
|
"WHERE object_data_id = :object_data_id"
|
||||||
|
);
|
||||||
|
}
|
||||||
|
return GetCachedStatement(
|
||||||
|
"DELETE FROM index_data "
|
||||||
|
"WHERE object_data_id = :object_data_id"
|
||||||
|
);
|
||||||
|
}
|
||||||
|
|
||||||
already_AddRefed<mozIStorageStatement>
|
already_AddRefed<mozIStorageStatement>
|
||||||
IDBTransaction::GetCachedStatement(const nsACString& aQuery)
|
IDBTransaction::GetCachedStatement(const nsACString& aQuery)
|
||||||
{
|
{
|
||||||
@ -854,10 +853,12 @@ CommitHelper::Run()
|
|||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
event = CreateGenericEvent(NS_LITERAL_STRING(ABORT_EVT_STR));
|
event = CreateGenericEvent(NS_LITERAL_STRING(ABORT_EVT_STR),
|
||||||
|
eDoesBubble, eNotCancelable);
|
||||||
}
|
}
|
||||||
else {
|
else {
|
||||||
event = CreateGenericEvent(NS_LITERAL_STRING(COMPLETE_EVT_STR));
|
event = CreateGenericEvent(NS_LITERAL_STRING(COMPLETE_EVT_STR),
|
||||||
|
eDoesNotBubble, eNotCancelable);
|
||||||
}
|
}
|
||||||
NS_ENSURE_TRUE(event, NS_ERROR_DOM_INDEXEDDB_UNKNOWN_ERR);
|
NS_ENSURE_TRUE(event, NS_ERROR_DOM_INDEXEDDB_UNKNOWN_ERR);
|
||||||
|
|
||||||
|
@ -118,9 +118,12 @@ public:
|
|||||||
bool aAutoIncrement);
|
bool aAutoIncrement);
|
||||||
|
|
||||||
already_AddRefed<mozIStorageStatement>
|
already_AddRefed<mozIStorageStatement>
|
||||||
IndexUpdateStatement(bool aAutoIncrement,
|
IndexDataInsertStatement(bool aAutoIncrement,
|
||||||
bool aUnique,
|
bool aUnique);
|
||||||
bool aOverwrite);
|
|
||||||
|
already_AddRefed<mozIStorageStatement>
|
||||||
|
IndexDataDeleteStatement(bool aAutoIncrement,
|
||||||
|
bool aUnique);
|
||||||
|
|
||||||
already_AddRefed<mozIStorageStatement>
|
already_AddRefed<mozIStorageStatement>
|
||||||
GetCachedStatement(const nsACString& aQuery);
|
GetCachedStatement(const nsACString& aQuery);
|
||||||
|
@ -51,7 +51,7 @@
|
|||||||
#include "nsStringGlue.h"
|
#include "nsStringGlue.h"
|
||||||
#include "nsTArray.h"
|
#include "nsTArray.h"
|
||||||
|
|
||||||
#define DB_SCHEMA_VERSION 5
|
#define DB_SCHEMA_VERSION 6
|
||||||
|
|
||||||
#define BEGIN_INDEXEDDB_NAMESPACE \
|
#define BEGIN_INDEXEDDB_NAMESPACE \
|
||||||
namespace mozilla { namespace dom { namespace indexedDB {
|
namespace mozilla { namespace dom { namespace indexedDB {
|
||||||
|
@ -248,19 +248,6 @@ public:
|
|||||||
return NS_SUCCEEDED(rv) ? NS_OK : NS_ERROR_DOM_INDEXEDDB_UNKNOWN_ERR;
|
return NS_SUCCEEDED(rv) ? NS_OK : NS_ERROR_DOM_INDEXEDDB_UNKNOWN_ERR;
|
||||||
}
|
}
|
||||||
|
|
||||||
nsresult BindToStatementAllowUnset(mozIStorageStatement* aStatement,
|
|
||||||
const nsACString& aParamName) const
|
|
||||||
{
|
|
||||||
nsresult rv;
|
|
||||||
|
|
||||||
if (IsUnset()) {
|
|
||||||
rv = aStatement->BindStringByName(aParamName, EmptyString());
|
|
||||||
return NS_SUCCEEDED(rv) ? NS_OK : NS_ERROR_DOM_INDEXEDDB_UNKNOWN_ERR;
|
|
||||||
}
|
|
||||||
|
|
||||||
return BindToStatement(aStatement, aParamName);
|
|
||||||
}
|
|
||||||
|
|
||||||
nsresult SetFromStatement(mozIStorageStatement* aStatement,
|
nsresult SetFromStatement(mozIStorageStatement* aStatement,
|
||||||
PRUint32 aIndex)
|
PRUint32 aIndex)
|
||||||
{
|
{
|
||||||
|
@ -121,11 +121,10 @@ CreateTables(mozIStorageConnection* aDBConn)
|
|||||||
// Table `object_store`
|
// Table `object_store`
|
||||||
rv = aDBConn->ExecuteSimpleSQL(NS_LITERAL_CSTRING(
|
rv = aDBConn->ExecuteSimpleSQL(NS_LITERAL_CSTRING(
|
||||||
"CREATE TABLE object_store ("
|
"CREATE TABLE object_store ("
|
||||||
"id INTEGER, "
|
"id INTEGER PRIMARY KEY, "
|
||||||
"name TEXT NOT NULL, "
|
"name TEXT NOT NULL, "
|
||||||
"key_path TEXT NOT NULL, "
|
"key_path TEXT NOT NULL, "
|
||||||
"auto_increment INTEGER NOT NULL DEFAULT 0, "
|
"auto_increment INTEGER NOT NULL DEFAULT 0, "
|
||||||
"PRIMARY KEY (id), "
|
|
||||||
"UNIQUE (name)"
|
"UNIQUE (name)"
|
||||||
");"
|
");"
|
||||||
));
|
));
|
||||||
@ -134,41 +133,30 @@ CreateTables(mozIStorageConnection* aDBConn)
|
|||||||
// Table `object_data`
|
// Table `object_data`
|
||||||
rv = aDBConn->ExecuteSimpleSQL(NS_LITERAL_CSTRING(
|
rv = aDBConn->ExecuteSimpleSQL(NS_LITERAL_CSTRING(
|
||||||
"CREATE TABLE object_data ("
|
"CREATE TABLE object_data ("
|
||||||
"id INTEGER, "
|
"id INTEGER PRIMARY KEY, "
|
||||||
"object_store_id INTEGER NOT NULL, "
|
"object_store_id INTEGER NOT NULL, "
|
||||||
|
"key_value DEFAULT NULL, "
|
||||||
"data BLOB NOT NULL, "
|
"data BLOB NOT NULL, "
|
||||||
"key_value DEFAULT NULL, " // NONE affinity
|
"UNIQUE (object_store_id, key_value), "
|
||||||
"PRIMARY KEY (id), "
|
|
||||||
"FOREIGN KEY (object_store_id) REFERENCES object_store(id) ON DELETE "
|
"FOREIGN KEY (object_store_id) REFERENCES object_store(id) ON DELETE "
|
||||||
"CASCADE"
|
"CASCADE"
|
||||||
");"
|
");"
|
||||||
));
|
));
|
||||||
NS_ENSURE_SUCCESS(rv, rv);
|
NS_ENSURE_SUCCESS(rv, rv);
|
||||||
|
|
||||||
rv = aDBConn->ExecuteSimpleSQL(NS_LITERAL_CSTRING(
|
|
||||||
"CREATE UNIQUE INDEX key_index "
|
|
||||||
"ON object_data (key_value, object_store_id);"
|
|
||||||
));
|
|
||||||
NS_ENSURE_SUCCESS(rv, rv);
|
|
||||||
|
|
||||||
// Table `ai_object_data`
|
// Table `ai_object_data`
|
||||||
rv = aDBConn->ExecuteSimpleSQL(NS_LITERAL_CSTRING(
|
rv = aDBConn->ExecuteSimpleSQL(NS_LITERAL_CSTRING(
|
||||||
"CREATE TABLE ai_object_data ("
|
"CREATE TABLE ai_object_data ("
|
||||||
"id INTEGER PRIMARY KEY AUTOINCREMENT, "
|
"id INTEGER PRIMARY KEY AUTOINCREMENT, "
|
||||||
"object_store_id INTEGER NOT NULL, "
|
"object_store_id INTEGER NOT NULL, "
|
||||||
"data BLOB NOT NULL, "
|
"data BLOB NOT NULL, "
|
||||||
|
"UNIQUE (object_store_id, id), "
|
||||||
"FOREIGN KEY (object_store_id) REFERENCES object_store(id) ON DELETE "
|
"FOREIGN KEY (object_store_id) REFERENCES object_store(id) ON DELETE "
|
||||||
"CASCADE"
|
"CASCADE"
|
||||||
");"
|
");"
|
||||||
));
|
));
|
||||||
NS_ENSURE_SUCCESS(rv, rv);
|
NS_ENSURE_SUCCESS(rv, rv);
|
||||||
|
|
||||||
rv = aDBConn->ExecuteSimpleSQL(NS_LITERAL_CSTRING(
|
|
||||||
"CREATE UNIQUE INDEX ai_key_index "
|
|
||||||
"ON ai_object_data (id, object_store_id);"
|
|
||||||
));
|
|
||||||
NS_ENSURE_SUCCESS(rv, rv);
|
|
||||||
|
|
||||||
// Table `index`
|
// Table `index`
|
||||||
rv = aDBConn->ExecuteSimpleSQL(NS_LITERAL_CSTRING(
|
rv = aDBConn->ExecuteSimpleSQL(NS_LITERAL_CSTRING(
|
||||||
"CREATE TABLE object_store_index ("
|
"CREATE TABLE object_store_index ("
|
||||||
@ -189,12 +177,11 @@ CreateTables(mozIStorageConnection* aDBConn)
|
|||||||
// Table `index_data`
|
// Table `index_data`
|
||||||
rv = aDBConn->ExecuteSimpleSQL(NS_LITERAL_CSTRING(
|
rv = aDBConn->ExecuteSimpleSQL(NS_LITERAL_CSTRING(
|
||||||
"CREATE TABLE index_data ("
|
"CREATE TABLE index_data ("
|
||||||
"id INTEGER, "
|
|
||||||
"index_id INTEGER NOT NULL, "
|
"index_id INTEGER NOT NULL, "
|
||||||
"object_data_id INTEGER NOT NULL, "
|
|
||||||
"object_data_key NOT NULL, " // NONE affinity
|
|
||||||
"value NOT NULL, "
|
"value NOT NULL, "
|
||||||
"PRIMARY KEY (id), "
|
"object_data_key NOT NULL, "
|
||||||
|
"object_data_id INTEGER NOT NULL, "
|
||||||
|
"PRIMARY KEY (index_id, value, object_data_key), "
|
||||||
"FOREIGN KEY (index_id) REFERENCES object_store_index(id) ON DELETE "
|
"FOREIGN KEY (index_id) REFERENCES object_store_index(id) ON DELETE "
|
||||||
"CASCADE, "
|
"CASCADE, "
|
||||||
"FOREIGN KEY (object_data_id) REFERENCES object_data(id) ON DELETE "
|
"FOREIGN KEY (object_data_id) REFERENCES object_data(id) ON DELETE "
|
||||||
@ -203,21 +190,21 @@ CreateTables(mozIStorageConnection* aDBConn)
|
|||||||
));
|
));
|
||||||
NS_ENSURE_SUCCESS(rv, rv);
|
NS_ENSURE_SUCCESS(rv, rv);
|
||||||
|
|
||||||
|
// Need this to make cascading deletes from object_data and object_store fast.
|
||||||
rv = aDBConn->ExecuteSimpleSQL(NS_LITERAL_CSTRING(
|
rv = aDBConn->ExecuteSimpleSQL(NS_LITERAL_CSTRING(
|
||||||
"CREATE INDEX value_index "
|
"CREATE INDEX index_data_object_data_id_index "
|
||||||
"ON index_data (index_id, value);"
|
"ON index_data (object_data_id);"
|
||||||
));
|
));
|
||||||
NS_ENSURE_SUCCESS(rv, rv);
|
NS_ENSURE_SUCCESS(rv, rv);
|
||||||
|
|
||||||
// Table `unique_index_data`
|
// Table `unique_index_data`
|
||||||
rv = aDBConn->ExecuteSimpleSQL(NS_LITERAL_CSTRING(
|
rv = aDBConn->ExecuteSimpleSQL(NS_LITERAL_CSTRING(
|
||||||
"CREATE TABLE unique_index_data ("
|
"CREATE TABLE unique_index_data ("
|
||||||
"id INTEGER, "
|
|
||||||
"index_id INTEGER NOT NULL, "
|
"index_id INTEGER NOT NULL, "
|
||||||
"object_data_id INTEGER NOT NULL, "
|
|
||||||
"object_data_key NOT NULL, " // NONE affinity
|
|
||||||
"value NOT NULL, "
|
"value NOT NULL, "
|
||||||
"PRIMARY KEY (id), "
|
"object_data_key NOT NULL, " // NONE affinity
|
||||||
|
"object_data_id INTEGER NOT NULL, "
|
||||||
|
"PRIMARY KEY (index_id, value, object_data_key), "
|
||||||
"UNIQUE (index_id, value), "
|
"UNIQUE (index_id, value), "
|
||||||
"FOREIGN KEY (index_id) REFERENCES object_store_index(id) ON DELETE "
|
"FOREIGN KEY (index_id) REFERENCES object_store_index(id) ON DELETE "
|
||||||
"CASCADE "
|
"CASCADE "
|
||||||
@ -227,14 +214,20 @@ CreateTables(mozIStorageConnection* aDBConn)
|
|||||||
));
|
));
|
||||||
NS_ENSURE_SUCCESS(rv, rv);
|
NS_ENSURE_SUCCESS(rv, rv);
|
||||||
|
|
||||||
|
// Need this to make cascading deletes from object_data and object_store fast.
|
||||||
|
rv = aDBConn->ExecuteSimpleSQL(NS_LITERAL_CSTRING(
|
||||||
|
"CREATE INDEX unique_index_data_object_data_id_index "
|
||||||
|
"ON unique_index_data (object_data_id);"
|
||||||
|
));
|
||||||
|
NS_ENSURE_SUCCESS(rv, rv);
|
||||||
|
|
||||||
// Table `ai_index_data`
|
// Table `ai_index_data`
|
||||||
rv = aDBConn->ExecuteSimpleSQL(NS_LITERAL_CSTRING(
|
rv = aDBConn->ExecuteSimpleSQL(NS_LITERAL_CSTRING(
|
||||||
"CREATE TABLE ai_index_data ("
|
"CREATE TABLE ai_index_data ("
|
||||||
"id INTEGER, "
|
|
||||||
"index_id INTEGER NOT NULL, "
|
"index_id INTEGER NOT NULL, "
|
||||||
"ai_object_data_id INTEGER NOT NULL, "
|
|
||||||
"value NOT NULL, "
|
"value NOT NULL, "
|
||||||
"PRIMARY KEY (id), "
|
"ai_object_data_id INTEGER NOT NULL, "
|
||||||
|
"PRIMARY KEY (index_id, value, ai_object_data_id), "
|
||||||
"FOREIGN KEY (index_id) REFERENCES object_store_index(id) ON DELETE "
|
"FOREIGN KEY (index_id) REFERENCES object_store_index(id) ON DELETE "
|
||||||
"CASCADE, "
|
"CASCADE, "
|
||||||
"FOREIGN KEY (ai_object_data_id) REFERENCES ai_object_data(id) ON DELETE "
|
"FOREIGN KEY (ai_object_data_id) REFERENCES ai_object_data(id) ON DELETE "
|
||||||
@ -243,21 +236,22 @@ CreateTables(mozIStorageConnection* aDBConn)
|
|||||||
));
|
));
|
||||||
NS_ENSURE_SUCCESS(rv, rv);
|
NS_ENSURE_SUCCESS(rv, rv);
|
||||||
|
|
||||||
|
// Need this to make cascading deletes from ai_object_data and object_store
|
||||||
|
// fast.
|
||||||
rv = aDBConn->ExecuteSimpleSQL(NS_LITERAL_CSTRING(
|
rv = aDBConn->ExecuteSimpleSQL(NS_LITERAL_CSTRING(
|
||||||
"CREATE INDEX ai_value_index "
|
"CREATE INDEX ai_index_data_ai_object_data_id_index "
|
||||||
"ON ai_index_data (index_id, value);"
|
"ON ai_index_data (ai_object_data_id);"
|
||||||
));
|
));
|
||||||
NS_ENSURE_SUCCESS(rv, rv);
|
NS_ENSURE_SUCCESS(rv, rv);
|
||||||
|
|
||||||
// Table `ai_unique_index_data`
|
// Table `ai_unique_index_data`
|
||||||
rv = aDBConn->ExecuteSimpleSQL(NS_LITERAL_CSTRING(
|
rv = aDBConn->ExecuteSimpleSQL(NS_LITERAL_CSTRING(
|
||||||
"CREATE TABLE ai_unique_index_data ("
|
"CREATE TABLE ai_unique_index_data ("
|
||||||
"id INTEGER, "
|
|
||||||
"index_id INTEGER NOT NULL, "
|
"index_id INTEGER NOT NULL, "
|
||||||
"ai_object_data_id INTEGER NOT NULL, "
|
|
||||||
"value NOT NULL, "
|
"value NOT NULL, "
|
||||||
"PRIMARY KEY (id), "
|
"ai_object_data_id INTEGER NOT NULL, "
|
||||||
"UNIQUE (index_id, value), "
|
"UNIQUE (index_id, value), "
|
||||||
|
"PRIMARY KEY (index_id, value, ai_object_data_id), "
|
||||||
"FOREIGN KEY (index_id) REFERENCES object_store_index(id) ON DELETE "
|
"FOREIGN KEY (index_id) REFERENCES object_store_index(id) ON DELETE "
|
||||||
"CASCADE, "
|
"CASCADE, "
|
||||||
"FOREIGN KEY (ai_object_data_id) REFERENCES ai_object_data(id) ON DELETE "
|
"FOREIGN KEY (ai_object_data_id) REFERENCES ai_object_data(id) ON DELETE "
|
||||||
@ -266,6 +260,14 @@ CreateTables(mozIStorageConnection* aDBConn)
|
|||||||
));
|
));
|
||||||
NS_ENSURE_SUCCESS(rv, rv);
|
NS_ENSURE_SUCCESS(rv, rv);
|
||||||
|
|
||||||
|
// Need this to make cascading deletes from ai_object_data and object_store
|
||||||
|
// fast.
|
||||||
|
rv = aDBConn->ExecuteSimpleSQL(NS_LITERAL_CSTRING(
|
||||||
|
"CREATE INDEX ai_unique_index_data_ai_object_data_id_index "
|
||||||
|
"ON ai_unique_index_data (ai_object_data_id);"
|
||||||
|
));
|
||||||
|
NS_ENSURE_SUCCESS(rv, rv);
|
||||||
|
|
||||||
rv = aDBConn->SetSchemaVersion(DB_SCHEMA_VERSION);
|
rv = aDBConn->SetSchemaVersion(DB_SCHEMA_VERSION);
|
||||||
NS_ENSURE_SUCCESS(rv, rv);
|
NS_ENSURE_SUCCESS(rv, rv);
|
||||||
|
|
||||||
@ -377,7 +379,372 @@ UpgradeSchemaFrom4To5(mozIStorageConnection* aConnection)
|
|||||||
NS_ENSURE_SUCCESS(rv, rv);
|
NS_ENSURE_SUCCESS(rv, rv);
|
||||||
}
|
}
|
||||||
|
|
||||||
rv = aConnection->SetSchemaVersion(DB_SCHEMA_VERSION);
|
rv = aConnection->SetSchemaVersion(5);
|
||||||
|
NS_ENSURE_SUCCESS(rv, rv);
|
||||||
|
|
||||||
|
rv = transaction.Commit();
|
||||||
|
NS_ENSURE_SUCCESS(rv, rv);
|
||||||
|
|
||||||
|
return NS_OK;
|
||||||
|
}
|
||||||
|
|
||||||
|
nsresult
|
||||||
|
UpgradeSchemaFrom5To6(mozIStorageConnection* aConnection)
|
||||||
|
{
|
||||||
|
mozStorageTransaction transaction(aConnection, false,
|
||||||
|
mozIStorageConnection::TRANSACTION_IMMEDIATE);
|
||||||
|
|
||||||
|
// Turn off foreign key constraints before we do anything here.
|
||||||
|
nsresult rv = aConnection->ExecuteSimpleSQL(NS_LITERAL_CSTRING(
|
||||||
|
"PRAGMA foreign_keys = OFF;"
|
||||||
|
));
|
||||||
|
NS_ENSURE_SUCCESS(rv, rv);
|
||||||
|
|
||||||
|
// First, drop all the indexes we're no longer going to use.
|
||||||
|
rv = aConnection->ExecuteSimpleSQL(NS_LITERAL_CSTRING(
|
||||||
|
"DROP INDEX key_index;"
|
||||||
|
));
|
||||||
|
NS_ENSURE_SUCCESS(rv, rv);
|
||||||
|
|
||||||
|
rv = aConnection->ExecuteSimpleSQL(NS_LITERAL_CSTRING(
|
||||||
|
"DROP INDEX ai_key_index;"
|
||||||
|
));
|
||||||
|
NS_ENSURE_SUCCESS(rv, rv);
|
||||||
|
|
||||||
|
rv = aConnection->ExecuteSimpleSQL(NS_LITERAL_CSTRING(
|
||||||
|
"DROP INDEX value_index;"
|
||||||
|
));
|
||||||
|
NS_ENSURE_SUCCESS(rv, rv);
|
||||||
|
|
||||||
|
rv = aConnection->ExecuteSimpleSQL(NS_LITERAL_CSTRING(
|
||||||
|
"DROP INDEX ai_value_index;"
|
||||||
|
));
|
||||||
|
NS_ENSURE_SUCCESS(rv, rv);
|
||||||
|
|
||||||
|
// Now, reorder the columns of object_data to put the blob data last. We do
|
||||||
|
// this by copying into a temporary table, dropping the original, then copying
|
||||||
|
// back into a newly created table.
|
||||||
|
rv = aConnection->ExecuteSimpleSQL(NS_LITERAL_CSTRING(
|
||||||
|
"CREATE TEMPORARY TABLE temp_upgrade ("
|
||||||
|
"id INTEGER PRIMARY KEY, "
|
||||||
|
"object_store_id, "
|
||||||
|
"key_value, "
|
||||||
|
"data "
|
||||||
|
");"
|
||||||
|
));
|
||||||
|
NS_ENSURE_SUCCESS(rv, rv);
|
||||||
|
|
||||||
|
rv = aConnection->ExecuteSimpleSQL(NS_LITERAL_CSTRING(
|
||||||
|
"INSERT INTO temp_upgrade "
|
||||||
|
"SELECT id, object_store_id, key_value, data "
|
||||||
|
"FROM object_data;"
|
||||||
|
));
|
||||||
|
NS_ENSURE_SUCCESS(rv, rv);
|
||||||
|
|
||||||
|
rv = aConnection->ExecuteSimpleSQL(NS_LITERAL_CSTRING(
|
||||||
|
"DROP TABLE object_data;"
|
||||||
|
));
|
||||||
|
NS_ENSURE_SUCCESS(rv, rv);
|
||||||
|
|
||||||
|
rv = aConnection->ExecuteSimpleSQL(NS_LITERAL_CSTRING(
|
||||||
|
"CREATE TABLE object_data ("
|
||||||
|
"id INTEGER PRIMARY KEY, "
|
||||||
|
"object_store_id INTEGER NOT NULL, "
|
||||||
|
"key_value DEFAULT NULL, "
|
||||||
|
"data BLOB NOT NULL, "
|
||||||
|
"UNIQUE (object_store_id, key_value), "
|
||||||
|
"FOREIGN KEY (object_store_id) REFERENCES object_store(id) ON DELETE "
|
||||||
|
"CASCADE"
|
||||||
|
");"
|
||||||
|
));
|
||||||
|
NS_ENSURE_SUCCESS(rv, rv);
|
||||||
|
|
||||||
|
rv = aConnection->ExecuteSimpleSQL(NS_LITERAL_CSTRING(
|
||||||
|
"INSERT INTO object_data "
|
||||||
|
"SELECT id, object_store_id, key_value, data "
|
||||||
|
"FROM temp_upgrade;"
|
||||||
|
));
|
||||||
|
NS_ENSURE_SUCCESS(rv, rv);
|
||||||
|
|
||||||
|
rv = aConnection->ExecuteSimpleSQL(NS_LITERAL_CSTRING(
|
||||||
|
"DROP TABLE temp_upgrade;"
|
||||||
|
));
|
||||||
|
NS_ENSURE_SUCCESS(rv, rv);
|
||||||
|
|
||||||
|
// We need to add a unique constraint to our ai_object_data table. Copy all
|
||||||
|
// the data out of it using a temporary table as before.
|
||||||
|
rv = aConnection->ExecuteSimpleSQL(NS_LITERAL_CSTRING(
|
||||||
|
"CREATE TEMPORARY TABLE temp_upgrade ("
|
||||||
|
"id INTEGER PRIMARY KEY, "
|
||||||
|
"object_store_id, "
|
||||||
|
"data "
|
||||||
|
");"
|
||||||
|
));
|
||||||
|
NS_ENSURE_SUCCESS(rv, rv);
|
||||||
|
|
||||||
|
rv = aConnection->ExecuteSimpleSQL(NS_LITERAL_CSTRING(
|
||||||
|
"INSERT INTO temp_upgrade "
|
||||||
|
"SELECT id, object_store_id, data "
|
||||||
|
"FROM ai_object_data;"
|
||||||
|
));
|
||||||
|
NS_ENSURE_SUCCESS(rv, rv);
|
||||||
|
|
||||||
|
rv = aConnection->ExecuteSimpleSQL(NS_LITERAL_CSTRING(
|
||||||
|
"DROP TABLE ai_object_data;"
|
||||||
|
));
|
||||||
|
NS_ENSURE_SUCCESS(rv, rv);
|
||||||
|
|
||||||
|
rv = aConnection->ExecuteSimpleSQL(NS_LITERAL_CSTRING(
|
||||||
|
"CREATE TABLE ai_object_data ("
|
||||||
|
"id INTEGER PRIMARY KEY AUTOINCREMENT, "
|
||||||
|
"object_store_id INTEGER NOT NULL, "
|
||||||
|
"data BLOB NOT NULL, "
|
||||||
|
"UNIQUE (object_store_id, id), "
|
||||||
|
"FOREIGN KEY (object_store_id) REFERENCES object_store(id) ON DELETE "
|
||||||
|
"CASCADE"
|
||||||
|
");"
|
||||||
|
));
|
||||||
|
NS_ENSURE_SUCCESS(rv, rv);
|
||||||
|
|
||||||
|
rv = aConnection->ExecuteSimpleSQL(NS_LITERAL_CSTRING(
|
||||||
|
"INSERT INTO ai_object_data "
|
||||||
|
"SELECT id, object_store_id, data "
|
||||||
|
"FROM temp_upgrade;"
|
||||||
|
));
|
||||||
|
NS_ENSURE_SUCCESS(rv, rv);
|
||||||
|
|
||||||
|
rv = aConnection->ExecuteSimpleSQL(NS_LITERAL_CSTRING(
|
||||||
|
"DROP TABLE temp_upgrade;"
|
||||||
|
));
|
||||||
|
NS_ENSURE_SUCCESS(rv, rv);
|
||||||
|
|
||||||
|
// Fix up the index_data table. We're reordering the columns as well as
|
||||||
|
// changing the primary key from being a simple id to being a composite.
|
||||||
|
rv = aConnection->ExecuteSimpleSQL(NS_LITERAL_CSTRING(
|
||||||
|
"CREATE TEMPORARY TABLE temp_upgrade ("
|
||||||
|
"index_id, "
|
||||||
|
"value, "
|
||||||
|
"object_data_key, "
|
||||||
|
"object_data_id "
|
||||||
|
");"
|
||||||
|
));
|
||||||
|
NS_ENSURE_SUCCESS(rv, rv);
|
||||||
|
|
||||||
|
rv = aConnection->ExecuteSimpleSQL(NS_LITERAL_CSTRING(
|
||||||
|
"INSERT INTO temp_upgrade "
|
||||||
|
"SELECT index_id, value, object_data_key, object_data_id "
|
||||||
|
"FROM index_data;"
|
||||||
|
));
|
||||||
|
NS_ENSURE_SUCCESS(rv, rv);
|
||||||
|
|
||||||
|
rv = aConnection->ExecuteSimpleSQL(NS_LITERAL_CSTRING(
|
||||||
|
"DROP TABLE index_data;"
|
||||||
|
));
|
||||||
|
NS_ENSURE_SUCCESS(rv, rv);
|
||||||
|
|
||||||
|
rv = aConnection->ExecuteSimpleSQL(NS_LITERAL_CSTRING(
|
||||||
|
"CREATE TABLE index_data ("
|
||||||
|
"index_id INTEGER NOT NULL, "
|
||||||
|
"value NOT NULL, "
|
||||||
|
"object_data_key NOT NULL, "
|
||||||
|
"object_data_id INTEGER NOT NULL, "
|
||||||
|
"PRIMARY KEY (index_id, value, object_data_key), "
|
||||||
|
"FOREIGN KEY (index_id) REFERENCES object_store_index(id) ON DELETE "
|
||||||
|
"CASCADE, "
|
||||||
|
"FOREIGN KEY (object_data_id) REFERENCES object_data(id) ON DELETE "
|
||||||
|
"CASCADE"
|
||||||
|
");"
|
||||||
|
));
|
||||||
|
NS_ENSURE_SUCCESS(rv, rv);
|
||||||
|
|
||||||
|
rv = aConnection->ExecuteSimpleSQL(NS_LITERAL_CSTRING(
|
||||||
|
"INSERT OR IGNORE INTO index_data "
|
||||||
|
"SELECT index_id, value, object_data_key, object_data_id "
|
||||||
|
"FROM temp_upgrade;"
|
||||||
|
));
|
||||||
|
NS_ENSURE_SUCCESS(rv, rv);
|
||||||
|
|
||||||
|
rv = aConnection->ExecuteSimpleSQL(NS_LITERAL_CSTRING(
|
||||||
|
"DROP TABLE temp_upgrade;"
|
||||||
|
));
|
||||||
|
NS_ENSURE_SUCCESS(rv, rv);
|
||||||
|
|
||||||
|
rv = aConnection->ExecuteSimpleSQL(NS_LITERAL_CSTRING(
|
||||||
|
"CREATE INDEX index_data_object_data_id_index "
|
||||||
|
"ON index_data (object_data_id);"
|
||||||
|
));
|
||||||
|
NS_ENSURE_SUCCESS(rv, rv);
|
||||||
|
|
||||||
|
// Fix up the unique_index_data table. We're reordering the columns as well as
|
||||||
|
// changing the primary key from being a simple id to being a composite.
|
||||||
|
rv = aConnection->ExecuteSimpleSQL(NS_LITERAL_CSTRING(
|
||||||
|
"CREATE TEMPORARY TABLE temp_upgrade ("
|
||||||
|
"index_id, "
|
||||||
|
"value, "
|
||||||
|
"object_data_key, "
|
||||||
|
"object_data_id "
|
||||||
|
");"
|
||||||
|
));
|
||||||
|
NS_ENSURE_SUCCESS(rv, rv);
|
||||||
|
|
||||||
|
rv = aConnection->ExecuteSimpleSQL(NS_LITERAL_CSTRING(
|
||||||
|
"INSERT INTO temp_upgrade "
|
||||||
|
"SELECT index_id, value, object_data_key, object_data_id "
|
||||||
|
"FROM unique_index_data;"
|
||||||
|
));
|
||||||
|
NS_ENSURE_SUCCESS(rv, rv);
|
||||||
|
|
||||||
|
rv = aConnection->ExecuteSimpleSQL(NS_LITERAL_CSTRING(
|
||||||
|
"DROP TABLE unique_index_data;"
|
||||||
|
));
|
||||||
|
NS_ENSURE_SUCCESS(rv, rv);
|
||||||
|
|
||||||
|
rv = aConnection->ExecuteSimpleSQL(NS_LITERAL_CSTRING(
|
||||||
|
"CREATE TABLE unique_index_data ("
|
||||||
|
"index_id INTEGER NOT NULL, "
|
||||||
|
"value NOT NULL, "
|
||||||
|
"object_data_key NOT NULL, "
|
||||||
|
"object_data_id INTEGER NOT NULL, "
|
||||||
|
"PRIMARY KEY (index_id, value, object_data_key), "
|
||||||
|
"UNIQUE (index_id, value), "
|
||||||
|
"FOREIGN KEY (index_id) REFERENCES object_store_index(id) ON DELETE "
|
||||||
|
"CASCADE "
|
||||||
|
"FOREIGN KEY (object_data_id) REFERENCES object_data(id) ON DELETE "
|
||||||
|
"CASCADE"
|
||||||
|
");"
|
||||||
|
));
|
||||||
|
NS_ENSURE_SUCCESS(rv, rv);
|
||||||
|
|
||||||
|
rv = aConnection->ExecuteSimpleSQL(NS_LITERAL_CSTRING(
|
||||||
|
"INSERT INTO unique_index_data "
|
||||||
|
"SELECT index_id, value, object_data_key, object_data_id "
|
||||||
|
"FROM temp_upgrade;"
|
||||||
|
));
|
||||||
|
NS_ENSURE_SUCCESS(rv, rv);
|
||||||
|
|
||||||
|
rv = aConnection->ExecuteSimpleSQL(NS_LITERAL_CSTRING(
|
||||||
|
"DROP TABLE temp_upgrade;"
|
||||||
|
));
|
||||||
|
NS_ENSURE_SUCCESS(rv, rv);
|
||||||
|
|
||||||
|
rv = aConnection->ExecuteSimpleSQL(NS_LITERAL_CSTRING(
|
||||||
|
"CREATE INDEX unique_index_data_object_data_id_index "
|
||||||
|
"ON unique_index_data (object_data_id);"
|
||||||
|
));
|
||||||
|
NS_ENSURE_SUCCESS(rv, rv);
|
||||||
|
|
||||||
|
// Fix up the ai_index_data table. We're reordering the columns as well as
|
||||||
|
// changing the primary key from being a simple id to being a composite.
|
||||||
|
rv = aConnection->ExecuteSimpleSQL(NS_LITERAL_CSTRING(
|
||||||
|
"CREATE TEMPORARY TABLE temp_upgrade ("
|
||||||
|
"index_id, "
|
||||||
|
"value, "
|
||||||
|
"ai_object_data_id "
|
||||||
|
");"
|
||||||
|
));
|
||||||
|
NS_ENSURE_SUCCESS(rv, rv);
|
||||||
|
|
||||||
|
rv = aConnection->ExecuteSimpleSQL(NS_LITERAL_CSTRING(
|
||||||
|
"INSERT INTO temp_upgrade "
|
||||||
|
"SELECT index_id, value, ai_object_data_id "
|
||||||
|
"FROM ai_index_data;"
|
||||||
|
));
|
||||||
|
NS_ENSURE_SUCCESS(rv, rv);
|
||||||
|
|
||||||
|
rv = aConnection->ExecuteSimpleSQL(NS_LITERAL_CSTRING(
|
||||||
|
"DROP TABLE ai_index_data;"
|
||||||
|
));
|
||||||
|
NS_ENSURE_SUCCESS(rv, rv);
|
||||||
|
|
||||||
|
rv = aConnection->ExecuteSimpleSQL(NS_LITERAL_CSTRING(
|
||||||
|
"CREATE TABLE ai_index_data ("
|
||||||
|
"index_id INTEGER NOT NULL, "
|
||||||
|
"value NOT NULL, "
|
||||||
|
"ai_object_data_id INTEGER NOT NULL, "
|
||||||
|
"PRIMARY KEY (index_id, value, ai_object_data_id), "
|
||||||
|
"FOREIGN KEY (index_id) REFERENCES object_store_index(id) ON DELETE "
|
||||||
|
"CASCADE, "
|
||||||
|
"FOREIGN KEY (ai_object_data_id) REFERENCES ai_object_data(id) ON DELETE "
|
||||||
|
"CASCADE"
|
||||||
|
");"
|
||||||
|
));
|
||||||
|
NS_ENSURE_SUCCESS(rv, rv);
|
||||||
|
|
||||||
|
rv = aConnection->ExecuteSimpleSQL(NS_LITERAL_CSTRING(
|
||||||
|
"INSERT OR IGNORE INTO ai_index_data "
|
||||||
|
"SELECT index_id, value, ai_object_data_id "
|
||||||
|
"FROM temp_upgrade;"
|
||||||
|
));
|
||||||
|
NS_ENSURE_SUCCESS(rv, rv);
|
||||||
|
|
||||||
|
rv = aConnection->ExecuteSimpleSQL(NS_LITERAL_CSTRING(
|
||||||
|
"DROP TABLE temp_upgrade;"
|
||||||
|
));
|
||||||
|
NS_ENSURE_SUCCESS(rv, rv);
|
||||||
|
|
||||||
|
rv = aConnection->ExecuteSimpleSQL(NS_LITERAL_CSTRING(
|
||||||
|
"CREATE INDEX ai_index_data_ai_object_data_id_index "
|
||||||
|
"ON ai_index_data (ai_object_data_id);"
|
||||||
|
));
|
||||||
|
NS_ENSURE_SUCCESS(rv, rv);
|
||||||
|
|
||||||
|
// Fix up the ai_unique_index_data table. We're reordering the columns as well
|
||||||
|
// as changing the primary key from being a simple id to being a composite.
|
||||||
|
rv = aConnection->ExecuteSimpleSQL(NS_LITERAL_CSTRING(
|
||||||
|
"CREATE TEMPORARY TABLE temp_upgrade ("
|
||||||
|
"index_id, "
|
||||||
|
"value, "
|
||||||
|
"ai_object_data_id "
|
||||||
|
");"
|
||||||
|
));
|
||||||
|
NS_ENSURE_SUCCESS(rv, rv);
|
||||||
|
|
||||||
|
rv = aConnection->ExecuteSimpleSQL(NS_LITERAL_CSTRING(
|
||||||
|
"INSERT INTO temp_upgrade "
|
||||||
|
"SELECT index_id, value, ai_object_data_id "
|
||||||
|
"FROM ai_unique_index_data;"
|
||||||
|
));
|
||||||
|
NS_ENSURE_SUCCESS(rv, rv);
|
||||||
|
|
||||||
|
rv = aConnection->ExecuteSimpleSQL(NS_LITERAL_CSTRING(
|
||||||
|
"DROP TABLE ai_unique_index_data;"
|
||||||
|
));
|
||||||
|
NS_ENSURE_SUCCESS(rv, rv);
|
||||||
|
|
||||||
|
rv = aConnection->ExecuteSimpleSQL(NS_LITERAL_CSTRING(
|
||||||
|
"CREATE TABLE ai_unique_index_data ("
|
||||||
|
"index_id INTEGER NOT NULL, "
|
||||||
|
"value NOT NULL, "
|
||||||
|
"ai_object_data_id INTEGER NOT NULL, "
|
||||||
|
"UNIQUE (index_id, value), "
|
||||||
|
"PRIMARY KEY (index_id, value, ai_object_data_id), "
|
||||||
|
"FOREIGN KEY (index_id) REFERENCES object_store_index(id) ON DELETE "
|
||||||
|
"CASCADE, "
|
||||||
|
"FOREIGN KEY (ai_object_data_id) REFERENCES ai_object_data(id) ON DELETE "
|
||||||
|
"CASCADE"
|
||||||
|
");"
|
||||||
|
));
|
||||||
|
NS_ENSURE_SUCCESS(rv, rv);
|
||||||
|
|
||||||
|
rv = aConnection->ExecuteSimpleSQL(NS_LITERAL_CSTRING(
|
||||||
|
"INSERT INTO ai_unique_index_data "
|
||||||
|
"SELECT index_id, value, ai_object_data_id "
|
||||||
|
"FROM temp_upgrade;"
|
||||||
|
));
|
||||||
|
NS_ENSURE_SUCCESS(rv, rv);
|
||||||
|
|
||||||
|
rv = aConnection->ExecuteSimpleSQL(NS_LITERAL_CSTRING(
|
||||||
|
"DROP TABLE temp_upgrade;"
|
||||||
|
));
|
||||||
|
NS_ENSURE_SUCCESS(rv, rv);
|
||||||
|
|
||||||
|
rv = aConnection->ExecuteSimpleSQL(NS_LITERAL_CSTRING(
|
||||||
|
"CREATE INDEX ai_unique_index_data_ai_object_data_id_index "
|
||||||
|
"ON ai_unique_index_data (ai_object_data_id);"
|
||||||
|
));
|
||||||
|
NS_ENSURE_SUCCESS(rv, rv);
|
||||||
|
|
||||||
|
rv = aConnection->SetSchemaVersion(6);
|
||||||
NS_ENSURE_SUCCESS(rv, rv);
|
NS_ENSURE_SUCCESS(rv, rv);
|
||||||
|
|
||||||
rv = transaction.Commit();
|
rv = transaction.Commit();
|
||||||
@ -393,14 +760,6 @@ CreateDatabaseConnection(const nsAString& aName,
|
|||||||
{
|
{
|
||||||
NS_ASSERTION(!NS_IsMainThread(), "Wrong thread!");
|
NS_ASSERTION(!NS_IsMainThread(), "Wrong thread!");
|
||||||
|
|
||||||
nsCOMPtr<nsIFile> dbDirectory;
|
|
||||||
nsresult rv = aDBFile->GetParent(getter_AddRefs(dbDirectory));
|
|
||||||
NS_ENSURE_SUCCESS(rv, rv);
|
|
||||||
|
|
||||||
bool exists;
|
|
||||||
rv = aDBFile->Exists(&exists);
|
|
||||||
NS_ENSURE_SUCCESS(rv, rv);
|
|
||||||
|
|
||||||
NS_NAMED_LITERAL_CSTRING(quotaVFSName, "quota");
|
NS_NAMED_LITERAL_CSTRING(quotaVFSName, "quota");
|
||||||
|
|
||||||
nsCOMPtr<mozIStorageServiceQuotaManagement> ss =
|
nsCOMPtr<mozIStorageServiceQuotaManagement> ss =
|
||||||
@ -408,15 +767,13 @@ CreateDatabaseConnection(const nsAString& aName,
|
|||||||
NS_ENSURE_TRUE(ss, NS_ERROR_FAILURE);
|
NS_ENSURE_TRUE(ss, NS_ERROR_FAILURE);
|
||||||
|
|
||||||
nsCOMPtr<mozIStorageConnection> connection;
|
nsCOMPtr<mozIStorageConnection> connection;
|
||||||
rv = ss->OpenDatabaseWithVFS(aDBFile, quotaVFSName,
|
nsresult rv = ss->OpenDatabaseWithVFS(aDBFile, quotaVFSName,
|
||||||
getter_AddRefs(connection));
|
getter_AddRefs(connection));
|
||||||
if (rv == NS_ERROR_FILE_CORRUPTED) {
|
if (rv == NS_ERROR_FILE_CORRUPTED) {
|
||||||
// Nuke the database file. The web services can recreate their data.
|
// Nuke the database file. The web services can recreate their data.
|
||||||
rv = aDBFile->Remove(false);
|
rv = aDBFile->Remove(false);
|
||||||
NS_ENSURE_SUCCESS(rv, rv);
|
NS_ENSURE_SUCCESS(rv, rv);
|
||||||
|
|
||||||
exists = false;
|
|
||||||
|
|
||||||
rv = ss->OpenDatabaseWithVFS(aDBFile, quotaVFSName,
|
rv = ss->OpenDatabaseWithVFS(aDBFile, quotaVFSName,
|
||||||
getter_AddRefs(connection));
|
getter_AddRefs(connection));
|
||||||
}
|
}
|
||||||
@ -427,42 +784,49 @@ CreateDatabaseConnection(const nsAString& aName,
|
|||||||
rv = connection->GetSchemaVersion(&schemaVersion);
|
rv = connection->GetSchemaVersion(&schemaVersion);
|
||||||
NS_ENSURE_SUCCESS(rv, rv);
|
NS_ENSURE_SUCCESS(rv, rv);
|
||||||
|
|
||||||
if (schemaVersion != DB_SCHEMA_VERSION) {
|
if (!schemaVersion) {
|
||||||
|
// Brand new file, initialize our tables.
|
||||||
|
mozStorageTransaction transaction(connection, false,
|
||||||
|
mozIStorageConnection::TRANSACTION_IMMEDIATE);
|
||||||
|
|
||||||
|
rv = CreateTables(connection);
|
||||||
|
NS_ENSURE_SUCCESS(rv, rv);
|
||||||
|
|
||||||
|
rv = CreateMetaData(connection, aName);
|
||||||
|
NS_ENSURE_SUCCESS(rv, rv);
|
||||||
|
|
||||||
|
rv = transaction.Commit();
|
||||||
|
NS_ENSURE_SUCCESS(rv, rv);
|
||||||
|
|
||||||
|
NS_ASSERTION(NS_SUCCEEDED(connection->GetSchemaVersion(&schemaVersion)) &&
|
||||||
|
schemaVersion == DB_SCHEMA_VERSION,
|
||||||
|
"CreateTables set a bad schema version!");
|
||||||
|
}
|
||||||
|
else if (schemaVersion != DB_SCHEMA_VERSION) {
|
||||||
// This logic needs to change next time we change the schema!
|
// This logic needs to change next time we change the schema!
|
||||||
PR_STATIC_ASSERT(DB_SCHEMA_VERSION == 5);
|
PR_STATIC_ASSERT(DB_SCHEMA_VERSION == 6);
|
||||||
if (schemaVersion == 4) {
|
|
||||||
rv = UpgradeSchemaFrom4To5(connection);
|
|
||||||
NS_ENSURE_SUCCESS(rv, rv);
|
|
||||||
}
|
|
||||||
else {
|
|
||||||
// Nuke it from orbit, it's the only way to be sure.
|
|
||||||
if (exists) {
|
|
||||||
// If the connection is not at the right schema version, nuke it.
|
|
||||||
rv = aDBFile->Remove(false);
|
|
||||||
NS_ENSURE_SUCCESS(rv, rv);
|
|
||||||
|
|
||||||
rv = ss->OpenDatabaseWithVFS(aDBFile, quotaVFSName,
|
#define UPGRADE_SCHEMA_CASE(_from, _to) \
|
||||||
getter_AddRefs(connection));
|
if (schemaVersion == _from) { \
|
||||||
NS_ENSURE_SUCCESS(rv, rv);
|
rv = UpgradeSchemaFrom##_from##To##_to (connection); \
|
||||||
}
|
NS_ENSURE_SUCCESS(rv, rv); \
|
||||||
|
\
|
||||||
mozStorageTransaction transaction(connection, false,
|
rv = connection->GetSchemaVersion(&schemaVersion); \
|
||||||
mozIStorageConnection::TRANSACTION_IMMEDIATE);
|
NS_ENSURE_SUCCESS(rv, rv); \
|
||||||
rv = CreateTables(connection);
|
\
|
||||||
NS_ENSURE_SUCCESS(rv, rv);
|
NS_ASSERTION(schemaVersion == _to, "Bad upgrade function!"); \
|
||||||
|
|
||||||
rv = CreateMetaData(connection, aName);
|
|
||||||
NS_ENSURE_SUCCESS(rv, rv);
|
|
||||||
|
|
||||||
rv = transaction.Commit();
|
|
||||||
NS_ENSURE_SUCCESS(rv, rv);
|
|
||||||
}
|
|
||||||
}
|
}
|
||||||
|
|
||||||
// Check to make sure that the database schema is correct again.
|
UPGRADE_SCHEMA_CASE(4, 5)
|
||||||
NS_ASSERTION(NS_SUCCEEDED(connection->GetSchemaVersion(&schemaVersion)) &&
|
UPGRADE_SCHEMA_CASE(5, 6)
|
||||||
schemaVersion == DB_SCHEMA_VERSION,
|
|
||||||
"CreateTables failed!");
|
#undef UPGRADE_SCHEMA_CASE
|
||||||
|
|
||||||
|
if (schemaVersion != DB_SCHEMA_VERSION) {
|
||||||
|
NS_WARNING("Unable to open IndexedDB database, schema doesn't match");
|
||||||
|
return NS_ERROR_DOM_INDEXEDDB_UNKNOWN_ERR;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
// Turn on foreign key constraints.
|
// Turn on foreign key constraints.
|
||||||
rv = connection->ExecuteSimpleSQL(NS_LITERAL_CSTRING(
|
rv = connection->ExecuteSimpleSQL(NS_LITERAL_CSTRING(
|
||||||
@ -1143,7 +1507,8 @@ void
|
|||||||
OpenDatabaseHelper::DispatchSuccessEvent()
|
OpenDatabaseHelper::DispatchSuccessEvent()
|
||||||
{
|
{
|
||||||
nsRefPtr<nsDOMEvent> event =
|
nsRefPtr<nsDOMEvent> event =
|
||||||
CreateGenericEvent(NS_LITERAL_STRING(SUCCESS_EVT_STR));
|
CreateGenericEvent(NS_LITERAL_STRING(SUCCESS_EVT_STR),
|
||||||
|
eDoesNotBubble, eNotCancelable);
|
||||||
if (!event) {
|
if (!event) {
|
||||||
NS_ERROR("Failed to create event!");
|
NS_ERROR("Failed to create event!");
|
||||||
return;
|
return;
|
||||||
@ -1157,7 +1522,8 @@ void
|
|||||||
OpenDatabaseHelper::DispatchErrorEvent()
|
OpenDatabaseHelper::DispatchErrorEvent()
|
||||||
{
|
{
|
||||||
nsRefPtr<nsDOMEvent> event =
|
nsRefPtr<nsDOMEvent> event =
|
||||||
CreateGenericEvent(NS_LITERAL_STRING(ERROR_EVT_STR));
|
CreateGenericEvent(NS_LITERAL_STRING(ERROR_EVT_STR),
|
||||||
|
eDoesBubble, eCancelable);
|
||||||
if (!event) {
|
if (!event) {
|
||||||
NS_ERROR("Failed to create event!");
|
NS_ERROR("Failed to create event!");
|
||||||
return;
|
return;
|
||||||
|
@ -50,7 +50,7 @@ interface nsIDOMEventListener;
|
|||||||
* http://dvcs.w3.org/hg/IndexedDB/raw-file/tip/Overview.html#idl-def-IDBDatabase
|
* http://dvcs.w3.org/hg/IndexedDB/raw-file/tip/Overview.html#idl-def-IDBDatabase
|
||||||
* for more information.
|
* for more information.
|
||||||
*/
|
*/
|
||||||
[scriptable, builtinclass, uuid(7ad626df-3328-476f-ba10-8ccec4924340)]
|
[scriptable, builtinclass, uuid(bb877dff-ab5b-4ebb-9b3c-a7fa97cd4b51)]
|
||||||
interface nsIIDBDatabase : nsISupports
|
interface nsIIDBDatabase : nsISupports
|
||||||
{
|
{
|
||||||
readonly attribute DOMString name;
|
readonly attribute DOMString name;
|
||||||
@ -83,6 +83,8 @@ interface nsIIDBDatabase : nsISupports
|
|||||||
void
|
void
|
||||||
close();
|
close();
|
||||||
|
|
||||||
|
attribute nsIDOMEventListener onabort;
|
||||||
|
|
||||||
attribute nsIDOMEventListener onerror;
|
attribute nsIDOMEventListener onerror;
|
||||||
|
|
||||||
attribute nsIDOMEventListener onversionchange;
|
attribute nsIDOMEventListener onversionchange;
|
||||||
|
@ -75,9 +75,11 @@ TEST_FILES = \
|
|||||||
test_exceptions_in_success_events.html \
|
test_exceptions_in_success_events.html \
|
||||||
test_getAll.html \
|
test_getAll.html \
|
||||||
test_global_data.html \
|
test_global_data.html \
|
||||||
|
test_index_empty_keyPath.html \
|
||||||
test_index_getAll.html \
|
test_index_getAll.html \
|
||||||
test_index_getAllObjects.html \
|
test_index_getAllObjects.html \
|
||||||
test_index_object_cursors.html \
|
test_index_object_cursors.html \
|
||||||
|
test_index_update_delete.html \
|
||||||
test_indexes.html \
|
test_indexes.html \
|
||||||
test_indexes_bad_values.html \
|
test_indexes_bad_values.html \
|
||||||
test_key_requirements.html \
|
test_key_requirements.html \
|
||||||
@ -108,6 +110,7 @@ TEST_FILES = \
|
|||||||
test_setVersion_abort.html \
|
test_setVersion_abort.html \
|
||||||
test_setVersion_events.html \
|
test_setVersion_events.html \
|
||||||
test_setVersion_exclusion.html \
|
test_setVersion_exclusion.html \
|
||||||
|
test_unique_index_update.html \
|
||||||
test_writer_starvation.html \
|
test_writer_starvation.html \
|
||||||
third_party_iframe1.html \
|
third_party_iframe1.html \
|
||||||
third_party_iframe2.html \
|
third_party_iframe2.html \
|
||||||
|
95
dom/indexedDB/test/test_index_empty_keyPath.html
Normal file
95
dom/indexedDB/test/test_index_empty_keyPath.html
Normal file
@ -0,0 +1,95 @@
|
|||||||
|
<!--
|
||||||
|
Any copyright is dedicated to the Public Domain.
|
||||||
|
http://creativecommons.org/publicdomain/zero/1.0/
|
||||||
|
-->
|
||||||
|
<html>
|
||||||
|
<head>
|
||||||
|
<title>Indexed Database Property Test</title>
|
||||||
|
|
||||||
|
<script type="text/javascript" src="/tests/SimpleTest/SimpleTest.js"></script>
|
||||||
|
<link rel="stylesheet" type="text/css" href="/tests/SimpleTest/test.css"/>
|
||||||
|
|
||||||
|
<script type="text/javascript;version=1.7">
|
||||||
|
function testSteps()
|
||||||
|
{
|
||||||
|
const name = window.location.pathname;
|
||||||
|
|
||||||
|
const objectStoreData = [
|
||||||
|
{ key: "1", value: "foo" },
|
||||||
|
{ key: "2", value: "bar" },
|
||||||
|
{ key: "3", value: "baz" }
|
||||||
|
];
|
||||||
|
|
||||||
|
let request = mozIndexedDB.open(name, 1);
|
||||||
|
request.onerror = errorHandler;
|
||||||
|
request.onupgradeneeded = grabEventAndContinueHandler;
|
||||||
|
request.onsuccess = grabEventAndContinueHandler;
|
||||||
|
let event = yield; // upgradeneeded
|
||||||
|
|
||||||
|
let db = event.target.result;
|
||||||
|
|
||||||
|
let objectStore = db.createObjectStore("data", { keyPath: null });
|
||||||
|
|
||||||
|
// First, add all our data to the object store.
|
||||||
|
let addedData = 0;
|
||||||
|
for (let i in objectStoreData) {
|
||||||
|
request = objectStore.add(objectStoreData[i].value,
|
||||||
|
objectStoreData[i].key);
|
||||||
|
request.onerror = errorHandler;
|
||||||
|
request.onsuccess = function(event) {
|
||||||
|
if (++addedData == objectStoreData.length) {
|
||||||
|
testGenerator.send(event);
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
||||||
|
event = yield; // testGenerator.send
|
||||||
|
|
||||||
|
// Now create the index.
|
||||||
|
objectStore.createIndex("set", "", { unique: true });
|
||||||
|
yield; // success
|
||||||
|
|
||||||
|
let trans = db.transaction("data", IDBTransaction.READ_WRITE);
|
||||||
|
objectStore = trans.objectStore("data");
|
||||||
|
index = objectStore.index("set");
|
||||||
|
|
||||||
|
let request = index.get("bar");
|
||||||
|
request.onerror = errorHandler;
|
||||||
|
request.onsuccess = grabEventAndContinueHandler;
|
||||||
|
|
||||||
|
let event = yield;
|
||||||
|
|
||||||
|
is(event.target.result, "bar", "Got correct result");
|
||||||
|
|
||||||
|
let request = objectStore.add("foopy", 4);
|
||||||
|
request.onerror = errorHandler;
|
||||||
|
request.onsuccess = grabEventAndContinueHandler;
|
||||||
|
|
||||||
|
yield;
|
||||||
|
|
||||||
|
let request = index.get("foopy");
|
||||||
|
request.onerror = errorHandler;
|
||||||
|
request.onsuccess = grabEventAndContinueHandler;
|
||||||
|
|
||||||
|
let event = yield;
|
||||||
|
|
||||||
|
is(event.target.result, "foopy", "Got correct result");
|
||||||
|
|
||||||
|
let request = objectStore.add("foopy", 5);
|
||||||
|
request.onerror = new ExpectError(IDBDatabaseException.CONSTRAINT_ERR);
|
||||||
|
request.onsuccess = unexpectedSuccessHandler;
|
||||||
|
|
||||||
|
trans.oncomplete = grabEventAndContinueHandler;
|
||||||
|
|
||||||
|
yield;
|
||||||
|
yield;
|
||||||
|
|
||||||
|
finishTest();
|
||||||
|
yield;
|
||||||
|
}
|
||||||
|
</script>
|
||||||
|
<script type="text/javascript;version=1.7" src="helpers.js"></script>
|
||||||
|
</head>
|
||||||
|
|
||||||
|
<body onload="runTest();"></body>
|
||||||
|
|
||||||
|
</html>
|
180
dom/indexedDB/test/test_index_update_delete.html
Normal file
180
dom/indexedDB/test/test_index_update_delete.html
Normal file
@ -0,0 +1,180 @@
|
|||||||
|
<!--
|
||||||
|
Any copyright is dedicated to the Public Domain.
|
||||||
|
http://creativecommons.org/publicdomain/zero/1.0/
|
||||||
|
-->
|
||||||
|
<html>
|
||||||
|
<head>
|
||||||
|
<title>Indexed Database Property Test</title>
|
||||||
|
|
||||||
|
<script type="text/javascript" src="/tests/SimpleTest/SimpleTest.js"></script>
|
||||||
|
<link rel="stylesheet" type="text/css" href="/tests/SimpleTest/test.css"/>
|
||||||
|
|
||||||
|
<script type="text/javascript;version=1.7">
|
||||||
|
function testSteps()
|
||||||
|
{
|
||||||
|
let request = mozIndexedDB.open(window.location.pathname, 1);
|
||||||
|
request.onerror = errorHandler;
|
||||||
|
request.onupgradeneeded = grabEventAndContinueHandler;
|
||||||
|
request.onsuccess = grabEventAndContinueHandler;
|
||||||
|
|
||||||
|
let event = yield;
|
||||||
|
|
||||||
|
let db = event.target.result;
|
||||||
|
db.onerror = errorHandler;
|
||||||
|
|
||||||
|
for each (let autoIncrement in [false, true]) {
|
||||||
|
let objectStore =
|
||||||
|
db.createObjectStore(autoIncrement, { keyPath: "id",
|
||||||
|
autoIncrement: autoIncrement });
|
||||||
|
|
||||||
|
for (let i = 0; i < 10; i++) {
|
||||||
|
objectStore.add({ id: i, index: i });
|
||||||
|
}
|
||||||
|
|
||||||
|
for each (let unique in [false, true]) {
|
||||||
|
objectStore.createIndex(unique, "index", { unique: unique });
|
||||||
|
}
|
||||||
|
|
||||||
|
for (let i = 10; i < 20; i++) {
|
||||||
|
objectStore.add({ id: i, index: i });
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
event = yield;
|
||||||
|
is(event.type, "success", "expect a success event");
|
||||||
|
|
||||||
|
for each (let autoIncrement in [false, true]) {
|
||||||
|
let objectStore = db.transaction(autoIncrement)
|
||||||
|
.objectStore(autoIncrement);
|
||||||
|
|
||||||
|
objectStore.count().onsuccess = grabEventAndContinueHandler;
|
||||||
|
let event = yield;
|
||||||
|
|
||||||
|
is(event.target.result, 20, "Correct number of entries in objectStore");
|
||||||
|
|
||||||
|
let objectStoreCount = event.target.result;
|
||||||
|
let indexCount = event.target.result;
|
||||||
|
|
||||||
|
for each (let unique in [false, true]) {
|
||||||
|
let index = db.transaction(autoIncrement, IDBTransaction.READ_WRITE)
|
||||||
|
.objectStore(autoIncrement)
|
||||||
|
.index(unique);
|
||||||
|
|
||||||
|
index.count().onsuccess = grabEventAndContinueHandler;
|
||||||
|
let event = yield;
|
||||||
|
|
||||||
|
is(event.target.result, indexCount,
|
||||||
|
"Correct number of entries in index");
|
||||||
|
|
||||||
|
let modifiedEntry = unique ? 5 : 10;
|
||||||
|
let keyRange = IDBKeyRange.only(modifiedEntry);
|
||||||
|
|
||||||
|
let sawEntry = false;
|
||||||
|
index.openCursor(keyRange).onsuccess = function(event) {
|
||||||
|
let cursor = event.target.result;
|
||||||
|
if (cursor) {
|
||||||
|
sawEntry = true;
|
||||||
|
is(cursor.key, modifiedEntry, "Correct key");
|
||||||
|
|
||||||
|
cursor.value.index = unique ? 30 : 35;
|
||||||
|
cursor.update(cursor.value).onsuccess = function(event) {
|
||||||
|
cursor.continue();
|
||||||
|
}
|
||||||
|
}
|
||||||
|
else {
|
||||||
|
continueToNextStep();
|
||||||
|
}
|
||||||
|
}
|
||||||
|
yield;
|
||||||
|
|
||||||
|
is(sawEntry, true, "Saw entry for key value " + modifiedEntry);
|
||||||
|
|
||||||
|
// Recount index. Shouldn't change.
|
||||||
|
index = db.transaction(autoIncrement, IDBTransaction.READ_WRITE)
|
||||||
|
.objectStore(autoIncrement)
|
||||||
|
.index(unique);
|
||||||
|
|
||||||
|
index.count().onsuccess = grabEventAndContinueHandler;
|
||||||
|
event = yield;
|
||||||
|
|
||||||
|
is(event.target.result, indexCount,
|
||||||
|
"Correct number of entries in index");
|
||||||
|
|
||||||
|
modifiedEntry = unique ? 30 : 35;
|
||||||
|
keyRange = IDBKeyRange.only(modifiedEntry);
|
||||||
|
|
||||||
|
sawEntry = false;
|
||||||
|
index.openCursor(keyRange).onsuccess = function(event) {
|
||||||
|
let cursor = event.target.result;
|
||||||
|
if (cursor) {
|
||||||
|
sawEntry = true;
|
||||||
|
is(cursor.key, modifiedEntry, "Correct key");
|
||||||
|
|
||||||
|
delete cursor.value.index;
|
||||||
|
cursor.update(cursor.value).onsuccess = function(event) {
|
||||||
|
indexCount--;
|
||||||
|
cursor.continue();
|
||||||
|
}
|
||||||
|
}
|
||||||
|
else {
|
||||||
|
continueToNextStep();
|
||||||
|
}
|
||||||
|
}
|
||||||
|
yield;
|
||||||
|
|
||||||
|
is(sawEntry, true, "Saw entry for key value " + modifiedEntry);
|
||||||
|
|
||||||
|
// Recount objectStore. Should be unchanged.
|
||||||
|
objectStore = db.transaction(autoIncrement, IDBTransaction.READ_WRITE)
|
||||||
|
.objectStore(autoIncrement);
|
||||||
|
|
||||||
|
objectStore.count().onsuccess = grabEventAndContinueHandler;
|
||||||
|
event = yield;
|
||||||
|
|
||||||
|
is(event.target.result, objectStoreCount,
|
||||||
|
"Correct number of entries in objectStore");
|
||||||
|
|
||||||
|
// Recount index. Should be one item less.
|
||||||
|
index = objectStore.index(unique);
|
||||||
|
|
||||||
|
index.count().onsuccess = grabEventAndContinueHandler;
|
||||||
|
event = yield;
|
||||||
|
|
||||||
|
is(event.target.result, indexCount,
|
||||||
|
"Correct number of entries in index");
|
||||||
|
|
||||||
|
modifiedEntry = objectStoreCount - 1;
|
||||||
|
|
||||||
|
objectStore.delete(modifiedEntry).onsuccess =
|
||||||
|
grabEventAndContinueHandler;
|
||||||
|
event = yield;
|
||||||
|
|
||||||
|
objectStoreCount--;
|
||||||
|
indexCount--;
|
||||||
|
|
||||||
|
objectStore.count().onsuccess = grabEventAndContinueHandler;
|
||||||
|
event = yield;
|
||||||
|
|
||||||
|
is(event.target.result, objectStoreCount,
|
||||||
|
"Correct number of entries in objectStore");
|
||||||
|
|
||||||
|
index.count().onsuccess = grabEventAndContinueHandler;
|
||||||
|
event = yield;
|
||||||
|
|
||||||
|
is(event.target.result, indexCount,
|
||||||
|
"Correct number of entries in index");
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
finishTest();
|
||||||
|
yield;
|
||||||
|
}
|
||||||
|
|
||||||
|
</script>
|
||||||
|
<script type="text/javascript;version=1.7" src="helpers.js"></script>
|
||||||
|
|
||||||
|
</head>
|
||||||
|
|
||||||
|
<body onload="runTest();"></body>
|
||||||
|
|
||||||
|
</html>
|
@ -10,6 +10,10 @@
|
|||||||
<link rel="stylesheet" type="text/css" href="/tests/SimpleTest/test.css"/>
|
<link rel="stylesheet" type="text/css" href="/tests/SimpleTest/test.css"/>
|
||||||
|
|
||||||
<script type="text/javascript;version=1.7">
|
<script type="text/javascript;version=1.7">
|
||||||
|
var abortFired = false;
|
||||||
|
|
||||||
|
function abortListener() { abortFired = true; }
|
||||||
|
|
||||||
function testSteps()
|
function testSteps()
|
||||||
{
|
{
|
||||||
const Ci = Components.interfaces;
|
const Ci = Components.interfaces;
|
||||||
@ -33,6 +37,7 @@
|
|||||||
let event = yield;
|
let event = yield;
|
||||||
|
|
||||||
let db = event.target.result;
|
let db = event.target.result;
|
||||||
|
db.onabort = abortListener;
|
||||||
|
|
||||||
let transaction;
|
let transaction;
|
||||||
let objectStore;
|
let objectStore;
|
||||||
@ -398,6 +403,8 @@
|
|||||||
is(event.type, "abort", "transaction should fail");
|
is(event.type, "abort", "transaction should fail");
|
||||||
is(event.target, transaction, "transaction should fail");
|
is(event.target, transaction, "transaction should fail");
|
||||||
|
|
||||||
|
ok(abortFired, "Abort should have fired!");
|
||||||
|
|
||||||
finishTest();
|
finishTest();
|
||||||
yield;
|
yield;
|
||||||
}
|
}
|
||||||
|
79
dom/indexedDB/test/test_unique_index_update.html
Normal file
79
dom/indexedDB/test/test_unique_index_update.html
Normal file
@ -0,0 +1,79 @@
|
|||||||
|
<!--
|
||||||
|
Any copyright is dedicated to the Public Domain.
|
||||||
|
http://creativecommons.org/publicdomain/zero/1.0/
|
||||||
|
-->
|
||||||
|
<html>
|
||||||
|
<head>
|
||||||
|
<title>Indexed Database Property Test</title>
|
||||||
|
|
||||||
|
<script type="text/javascript" src="/tests/SimpleTest/SimpleTest.js"></script>
|
||||||
|
<link rel="stylesheet" type="text/css" href="/tests/SimpleTest/test.css"/>
|
||||||
|
|
||||||
|
<script type="text/javascript;version=1.7">
|
||||||
|
function testSteps()
|
||||||
|
{
|
||||||
|
let request = mozIndexedDB.open(window.location.pathname, 1);
|
||||||
|
request.onerror = errorHandler;
|
||||||
|
request.onupgradeneeded = grabEventAndContinueHandler;
|
||||||
|
request.onsuccess = grabEventAndContinueHandler;
|
||||||
|
|
||||||
|
let event = yield;
|
||||||
|
|
||||||
|
let db = event.target.result;
|
||||||
|
|
||||||
|
for each (let autoIncrement in [false, true]) {
|
||||||
|
let objectStore =
|
||||||
|
db.createObjectStore(autoIncrement, { keyPath: "id",
|
||||||
|
autoIncrement: autoIncrement });
|
||||||
|
objectStore.createIndex("", "index", { unique: true });
|
||||||
|
|
||||||
|
for (let i = 0; i < 10; i++) {
|
||||||
|
objectStore.add({ id: i, index: i });
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
event = yield;
|
||||||
|
is(event.type, "success", "expect a success event");
|
||||||
|
|
||||||
|
for each (let autoIncrement in [false, true]) {
|
||||||
|
objectStore = db.transaction(autoIncrement, IDBTransaction.READ_WRITE)
|
||||||
|
.objectStore(autoIncrement);
|
||||||
|
|
||||||
|
request = objectStore.put({ id: 5, index: 6 });
|
||||||
|
request.onsuccess = unexpectedSuccessHandler;
|
||||||
|
request.onerror = new ExpectError(IDBDatabaseException.CONSTRAINT_ERR);
|
||||||
|
event = yield;
|
||||||
|
|
||||||
|
event.preventDefault();
|
||||||
|
|
||||||
|
let keyRange = IDBKeyRange.only(5);
|
||||||
|
|
||||||
|
objectStore.index("").openCursor(keyRange).onsuccess = function(event) {
|
||||||
|
let cursor = event.target.result;
|
||||||
|
ok(cursor, "Must have a cursor here");
|
||||||
|
|
||||||
|
is(cursor.value.index, 5, "Still have the right index value");
|
||||||
|
|
||||||
|
cursor.value.index = 6;
|
||||||
|
|
||||||
|
request = cursor.update(cursor.value);
|
||||||
|
request.onsuccess = unexpectedSuccessHandler;
|
||||||
|
request.onerror =
|
||||||
|
new ExpectError(IDBDatabaseException.CONSTRAINT_ERR);
|
||||||
|
};
|
||||||
|
|
||||||
|
yield;
|
||||||
|
}
|
||||||
|
|
||||||
|
finishTest();
|
||||||
|
yield;
|
||||||
|
}
|
||||||
|
|
||||||
|
</script>
|
||||||
|
<script type="text/javascript;version=1.7" src="helpers.js"></script>
|
||||||
|
|
||||||
|
</head>
|
||||||
|
|
||||||
|
<body onload="runTest();"></body>
|
||||||
|
|
||||||
|
</html>
|
@ -51,7 +51,7 @@
|
|||||||
* http://www.w3.org/TR/DOM-Level-2-Style
|
* http://www.w3.org/TR/DOM-Level-2-Style
|
||||||
*/
|
*/
|
||||||
|
|
||||||
[builtinclass, scriptable, uuid(519ae4fa-0fee-4aaa-bcb9-34b503236801)]
|
[builtinclass, scriptable, uuid(0a6fc4c6-a62a-4f52-9ab6-3d398b958843)]
|
||||||
interface nsIDOMCSS2Properties : nsISupports
|
interface nsIDOMCSS2Properties : nsISupports
|
||||||
{
|
{
|
||||||
attribute DOMString background;
|
attribute DOMString background;
|
||||||
@ -764,4 +764,7 @@ interface nsIDOMCSS2Properties : nsISupports
|
|||||||
|
|
||||||
attribute DOMString MozAnimation;
|
attribute DOMString MozAnimation;
|
||||||
// raises(DOMException) on setting
|
// raises(DOMException) on setting
|
||||||
|
|
||||||
|
attribute DOMString MozTextSizeAdjust;
|
||||||
|
// raises(DOMException) on setting
|
||||||
};
|
};
|
||||||
|
@ -654,9 +654,6 @@ nsresult nsPluginHost::GetURLWithHeaders(nsNPAPIPluginInstance* pluginInst,
|
|||||||
PRUint32 getHeadersLength,
|
PRUint32 getHeadersLength,
|
||||||
const char* getHeaders)
|
const char* getHeaders)
|
||||||
{
|
{
|
||||||
nsAutoString string;
|
|
||||||
string.AssignWithConversion(url);
|
|
||||||
|
|
||||||
// we can only send a stream back to the plugin (as specified by a
|
// we can only send a stream back to the plugin (as specified by a
|
||||||
// null target) if we also have a nsIPluginStreamListener to talk to
|
// null target) if we also have a nsIPluginStreamListener to talk to
|
||||||
if (!target && !streamListener)
|
if (!target && !streamListener)
|
||||||
@ -681,7 +678,8 @@ nsresult nsPluginHost::GetURLWithHeaders(nsNPAPIPluginInstance* pluginInst,
|
|||||||
}
|
}
|
||||||
|
|
||||||
if (streamListener)
|
if (streamListener)
|
||||||
rv = NewPluginURLStream(string, pluginInst, streamListener, nsnull,
|
rv = NewPluginURLStream(NS_ConvertUTF8toUTF16(url), pluginInst,
|
||||||
|
streamListener, nsnull,
|
||||||
getHeaders, getHeadersLength);
|
getHeaders, getHeadersLength);
|
||||||
|
|
||||||
return rv;
|
return rv;
|
||||||
@ -700,11 +698,8 @@ nsresult nsPluginHost::PostURL(nsISupports* pluginInst,
|
|||||||
PRUint32 postHeadersLength,
|
PRUint32 postHeadersLength,
|
||||||
const char* postHeaders)
|
const char* postHeaders)
|
||||||
{
|
{
|
||||||
nsAutoString string;
|
|
||||||
nsresult rv;
|
nsresult rv;
|
||||||
|
|
||||||
string.AssignWithConversion(url);
|
|
||||||
|
|
||||||
// we can only send a stream back to the plugin (as specified
|
// we can only send a stream back to the plugin (as specified
|
||||||
// by a null target) if we also have a nsIPluginStreamListener
|
// by a null target) if we also have a nsIPluginStreamListener
|
||||||
// to talk to also
|
// to talk to also
|
||||||
@ -775,7 +770,8 @@ nsresult nsPluginHost::PostURL(nsISupports* pluginInst,
|
|||||||
// if we don't have a target, just create a stream. This does
|
// if we don't have a target, just create a stream. This does
|
||||||
// NS_OpenURI()!
|
// NS_OpenURI()!
|
||||||
if (streamListener)
|
if (streamListener)
|
||||||
rv = NewPluginURLStream(string, instance, streamListener,
|
rv = NewPluginURLStream(NS_ConvertUTF8toUTF16(url), instance,
|
||||||
|
streamListener,
|
||||||
postStream, postHeaders, postHeadersLength);
|
postStream, postHeaders, postHeadersLength);
|
||||||
|
|
||||||
return rv;
|
return rv;
|
||||||
|
@ -150,7 +150,6 @@ enum {
|
|||||||
PREF_strict = 0,
|
PREF_strict = 0,
|
||||||
PREF_werror,
|
PREF_werror,
|
||||||
PREF_relimit,
|
PREF_relimit,
|
||||||
PREF_tracejit,
|
|
||||||
PREF_methodjit,
|
PREF_methodjit,
|
||||||
PREF_jitprofiling,
|
PREF_jitprofiling,
|
||||||
PREF_methodjit_always,
|
PREF_methodjit_always,
|
||||||
@ -168,7 +167,6 @@ const char* gPrefsToWatch[] = {
|
|||||||
JS_OPTIONS_DOT_STR "strict",
|
JS_OPTIONS_DOT_STR "strict",
|
||||||
JS_OPTIONS_DOT_STR "werror",
|
JS_OPTIONS_DOT_STR "werror",
|
||||||
JS_OPTIONS_DOT_STR "relimit",
|
JS_OPTIONS_DOT_STR "relimit",
|
||||||
JS_OPTIONS_DOT_STR "tracejit.content",
|
|
||||||
JS_OPTIONS_DOT_STR "methodjit.content",
|
JS_OPTIONS_DOT_STR "methodjit.content",
|
||||||
JS_OPTIONS_DOT_STR "jitprofiling.content",
|
JS_OPTIONS_DOT_STR "jitprofiling.content",
|
||||||
JS_OPTIONS_DOT_STR "methodjit_always"
|
JS_OPTIONS_DOT_STR "methodjit_always"
|
||||||
@ -201,9 +199,6 @@ PrefCallback(const char* aPrefName, void* aClosure)
|
|||||||
if (Preferences::GetBool(gPrefsToWatch[PREF_relimit])) {
|
if (Preferences::GetBool(gPrefsToWatch[PREF_relimit])) {
|
||||||
newOptions |= JSOPTION_RELIMIT;
|
newOptions |= JSOPTION_RELIMIT;
|
||||||
}
|
}
|
||||||
if (Preferences::GetBool(gPrefsToWatch[PREF_tracejit])) {
|
|
||||||
newOptions |= JSOPTION_JIT;
|
|
||||||
}
|
|
||||||
if (Preferences::GetBool(gPrefsToWatch[PREF_methodjit])) {
|
if (Preferences::GetBool(gPrefsToWatch[PREF_methodjit])) {
|
||||||
newOptions |= JSOPTION_METHODJIT;
|
newOptions |= JSOPTION_METHODJIT;
|
||||||
}
|
}
|
||||||
|
@ -87,7 +87,6 @@ abstract public class GeckoApp
|
|||||||
public Handler mMainHandler;
|
public Handler mMainHandler;
|
||||||
private IntentFilter mConnectivityFilter;
|
private IntentFilter mConnectivityFilter;
|
||||||
private BroadcastReceiver mConnectivityReceiver;
|
private BroadcastReceiver mConnectivityReceiver;
|
||||||
private IntentFilter mBatteryFilter;
|
|
||||||
private BroadcastReceiver mBatteryReceiver;
|
private BroadcastReceiver mBatteryReceiver;
|
||||||
|
|
||||||
enum LaunchState {PreLaunch, Launching, WaitForDebugger,
|
enum LaunchState {PreLaunch, Launching, WaitForDebugger,
|
||||||
@ -409,9 +408,10 @@ abstract public class GeckoApp
|
|||||||
mConnectivityFilter.addAction(ConnectivityManager.CONNECTIVITY_ACTION);
|
mConnectivityFilter.addAction(ConnectivityManager.CONNECTIVITY_ACTION);
|
||||||
mConnectivityReceiver = new GeckoConnectivityReceiver();
|
mConnectivityReceiver = new GeckoConnectivityReceiver();
|
||||||
|
|
||||||
mBatteryFilter = new IntentFilter();
|
IntentFilter batteryFilter = new IntentFilter();
|
||||||
mBatteryFilter.addAction(Intent.ACTION_BATTERY_CHANGED);
|
batteryFilter.addAction(Intent.ACTION_BATTERY_CHANGED);
|
||||||
mBatteryReceiver = new GeckoBatteryManager();
|
mBatteryReceiver = new GeckoBatteryManager();
|
||||||
|
registerReceiver(mBatteryReceiver, batteryFilter);
|
||||||
|
|
||||||
if (!checkAndSetLaunchState(LaunchState.PreLaunch,
|
if (!checkAndSetLaunchState(LaunchState.PreLaunch,
|
||||||
LaunchState.Launching))
|
LaunchState.Launching))
|
||||||
@ -505,7 +505,6 @@ abstract public class GeckoApp
|
|||||||
super.onPause();
|
super.onPause();
|
||||||
|
|
||||||
unregisterReceiver(mConnectivityReceiver);
|
unregisterReceiver(mConnectivityReceiver);
|
||||||
unregisterReceiver(mBatteryReceiver);
|
|
||||||
}
|
}
|
||||||
|
|
||||||
@Override
|
@Override
|
||||||
@ -524,7 +523,6 @@ abstract public class GeckoApp
|
|||||||
onNewIntent(getIntent());
|
onNewIntent(getIntent());
|
||||||
|
|
||||||
registerReceiver(mConnectivityReceiver, mConnectivityFilter);
|
registerReceiver(mConnectivityReceiver, mConnectivityFilter);
|
||||||
registerReceiver(mBatteryReceiver, mBatteryFilter);
|
|
||||||
}
|
}
|
||||||
|
|
||||||
@Override
|
@Override
|
||||||
@ -573,6 +571,8 @@ abstract public class GeckoApp
|
|||||||
GeckoAppShell.sendEventToGecko(new GeckoEvent(GeckoEvent.ACTIVITY_SHUTDOWN));
|
GeckoAppShell.sendEventToGecko(new GeckoEvent(GeckoEvent.ACTIVITY_SHUTDOWN));
|
||||||
|
|
||||||
super.onDestroy();
|
super.onDestroy();
|
||||||
|
|
||||||
|
unregisterReceiver(mBatteryReceiver);
|
||||||
}
|
}
|
||||||
|
|
||||||
@Override
|
@Override
|
||||||
@ -618,10 +618,6 @@ abstract public class GeckoApp
|
|||||||
// This file may not be there, so just log any errors and move on
|
// This file may not be there, so just log any errors and move on
|
||||||
Log.w(LOG_FILE_NAME, "error removing files", ex);
|
Log.w(LOG_FILE_NAME, "error removing files", ex);
|
||||||
}
|
}
|
||||||
unpackFile(zip, buf, null, "application.ini");
|
|
||||||
try {
|
|
||||||
unpackFile(zip, buf, null, "update.locale");
|
|
||||||
} catch (Exception e) {/* this is non-fatal */}
|
|
||||||
|
|
||||||
// copy any .xpi file into an extensions/ directory
|
// copy any .xpi file into an extensions/ directory
|
||||||
Enumeration<? extends ZipEntry> zipEntries = zip.entries();
|
Enumeration<? extends ZipEntry> zipEntries = zip.entries();
|
||||||
|
@ -185,16 +185,13 @@ endif # GNU_CC
|
|||||||
|
|
||||||
# special rule for pixman-mmx to get the right cflags
|
# special rule for pixman-mmx to get the right cflags
|
||||||
pixman-mmx.$(OBJ_SUFFIX): pixman-mmx.c $(GLOBAL_DEPS)
|
pixman-mmx.$(OBJ_SUFFIX): pixman-mmx.c $(GLOBAL_DEPS)
|
||||||
$(REPORT_BUILD)
|
|
||||||
@$(MAKE_DEPS_AUTO_CC)
|
@$(MAKE_DEPS_AUTO_CC)
|
||||||
$(ELOG) $(CC) $(OUTOPTION)$@ -c $(COMPILE_CFLAGS) $(MMX_CFLAGS) $(_VPATH_SRCS)
|
$(ELOG) $(CC) $(OUTOPTION)$@ -c $(COMPILE_CFLAGS) $(MMX_CFLAGS) $(_VPATH_SRCS)
|
||||||
|
|
||||||
pixman-sse2.$(OBJ_SUFFIX): pixman-sse2.c $(GLOBAL_DEPS)
|
pixman-sse2.$(OBJ_SUFFIX): pixman-sse2.c $(GLOBAL_DEPS)
|
||||||
$(REPORT_BUILD)
|
|
||||||
@$(MAKE_DEPS_AUTO_CC)
|
@$(MAKE_DEPS_AUTO_CC)
|
||||||
$(ELOG) $(CC) $(OUTOPTION)$@ -c $(COMPILE_CFLAGS) $(SSE2_CFLAGS) $(_VPATH_SRCS)
|
$(ELOG) $(CC) $(OUTOPTION)$@ -c $(COMPILE_CFLAGS) $(SSE2_CFLAGS) $(_VPATH_SRCS)
|
||||||
|
|
||||||
pixman-arm-neon.$(OBJ_SUFFIX): pixman-arm-neon.c $(GLOBAL_DEPS)
|
pixman-arm-neon.$(OBJ_SUFFIX): pixman-arm-neon.c $(GLOBAL_DEPS)
|
||||||
$(REPORT_BUILD)
|
|
||||||
@$(MAKE_DEPS_AUTO_CC)
|
@$(MAKE_DEPS_AUTO_CC)
|
||||||
$(ELOG) $(CC) $(OUTOPTION)$@ -c $(COMPILE_CFLAGS) $(ARM_NEON_CFLAGS) $(_VPATH_SRCS)
|
$(ELOG) $(CC) $(OUTOPTION)$@ -c $(COMPILE_CFLAGS) $(ARM_NEON_CFLAGS) $(_VPATH_SRCS)
|
||||||
|
@ -621,21 +621,21 @@ struct PairPosFormat1
|
|||||||
inline bool apply (hb_apply_context_t *c) const
|
inline bool apply (hb_apply_context_t *c) const
|
||||||
{
|
{
|
||||||
TRACE_APPLY ();
|
TRACE_APPLY ();
|
||||||
unsigned int end = MIN (c->buffer->len, c->buffer->i + c->context_length);
|
unsigned int j = c->buffer->i;
|
||||||
if (unlikely (c->buffer->i + 2 > end))
|
unsigned int end = MIN (c->buffer->len, j + c->context_length);
|
||||||
|
if (unlikely (j >= end))
|
||||||
return false;
|
return false;
|
||||||
|
|
||||||
unsigned int index = (this+coverage) (c->buffer->info[c->buffer->i].codepoint);
|
unsigned int index = (this+coverage) (c->buffer->info[j].codepoint);
|
||||||
if (likely (index == NOT_COVERED))
|
if (likely (index == NOT_COVERED))
|
||||||
return false;
|
return false;
|
||||||
|
|
||||||
unsigned int j = c->buffer->i + 1;
|
do
|
||||||
while (_hb_ot_layout_skip_mark (c->layout->face, &c->buffer->info[j], c->lookup_props, NULL))
|
|
||||||
{
|
{
|
||||||
if (unlikely (j == end))
|
|
||||||
return false;
|
|
||||||
j++;
|
j++;
|
||||||
}
|
if (unlikely (j == end))
|
||||||
|
return false;
|
||||||
|
} while (_hb_ot_layout_skip_mark (c->layout->face, &c->buffer->info[j], c->lookup_props, NULL));
|
||||||
|
|
||||||
return (this+pairSet[index]).apply (c, &valueFormat1, j);
|
return (this+pairSet[index]).apply (c, &valueFormat1, j);
|
||||||
}
|
}
|
||||||
@ -683,21 +683,21 @@ struct PairPosFormat2
|
|||||||
inline bool apply (hb_apply_context_t *c) const
|
inline bool apply (hb_apply_context_t *c) const
|
||||||
{
|
{
|
||||||
TRACE_APPLY ();
|
TRACE_APPLY ();
|
||||||
unsigned int end = MIN (c->buffer->len, c->buffer->i + c->context_length);
|
unsigned int j = c->buffer->i;
|
||||||
if (unlikely (c->buffer->i + 2 > end))
|
unsigned int end = MIN (c->buffer->len, j + c->context_length);
|
||||||
|
if (unlikely (j >= end))
|
||||||
return false;
|
return false;
|
||||||
|
|
||||||
unsigned int index = (this+coverage) (c->buffer->info[c->buffer->i].codepoint);
|
unsigned int index = (this+coverage) (c->buffer->info[j].codepoint);
|
||||||
if (likely (index == NOT_COVERED))
|
if (likely (index == NOT_COVERED))
|
||||||
return false;
|
return false;
|
||||||
|
|
||||||
unsigned int j = c->buffer->i + 1;
|
do
|
||||||
while (_hb_ot_layout_skip_mark (c->layout->face, &c->buffer->info[j], c->lookup_props, NULL))
|
|
||||||
{
|
{
|
||||||
|
j++;
|
||||||
if (unlikely (j == end))
|
if (unlikely (j == end))
|
||||||
return false;
|
return false;
|
||||||
j++;
|
} while (_hb_ot_layout_skip_mark (c->layout->face, &c->buffer->info[j], c->lookup_props, NULL));
|
||||||
}
|
|
||||||
|
|
||||||
unsigned int len1 = valueFormat1.get_len ();
|
unsigned int len1 = valueFormat1.get_len ();
|
||||||
unsigned int len2 = valueFormat2.get_len ();
|
unsigned int len2 = valueFormat2.get_len ();
|
||||||
@ -836,21 +836,21 @@ struct CursivePosFormat1
|
|||||||
if (c->property & HB_OT_LAYOUT_GLYPH_CLASS_MARK)
|
if (c->property & HB_OT_LAYOUT_GLYPH_CLASS_MARK)
|
||||||
return false;
|
return false;
|
||||||
|
|
||||||
unsigned int end = MIN (c->buffer->len, c->buffer->i + c->context_length);
|
unsigned int j = c->buffer->i;
|
||||||
if (unlikely (c->buffer->i + 2 > end))
|
unsigned int end = MIN (c->buffer->len, j + c->context_length);
|
||||||
|
if (unlikely (j >= end))
|
||||||
return false;
|
return false;
|
||||||
|
|
||||||
const EntryExitRecord &this_record = entryExitRecord[(this+coverage) (c->buffer->info[c->buffer->i].codepoint)];
|
const EntryExitRecord &this_record = entryExitRecord[(this+coverage) (c->buffer->info[j].codepoint)];
|
||||||
if (!this_record.exitAnchor)
|
if (!this_record.exitAnchor)
|
||||||
return false;
|
return false;
|
||||||
|
|
||||||
unsigned int j = c->buffer->i + 1;
|
do
|
||||||
while (_hb_ot_layout_skip_mark (c->layout->face, &c->buffer->info[j], c->lookup_props, NULL))
|
|
||||||
{
|
{
|
||||||
|
j++;
|
||||||
if (unlikely (j == end))
|
if (unlikely (j == end))
|
||||||
return false;
|
return false;
|
||||||
j++;
|
} while (_hb_ot_layout_skip_mark (c->layout->face, &c->buffer->info[j], c->lookup_props, NULL));
|
||||||
}
|
|
||||||
|
|
||||||
const EntryExitRecord &next_record = entryExitRecord[(this+coverage) (c->buffer->info[j].codepoint)];
|
const EntryExitRecord &next_record = entryExitRecord[(this+coverage) (c->buffer->info[j].codepoint)];
|
||||||
if (!next_record.entryAnchor)
|
if (!next_record.entryAnchor)
|
||||||
|
@ -342,24 +342,25 @@ struct Ligature
|
|||||||
inline bool apply (hb_apply_context_t *c) const
|
inline bool apply (hb_apply_context_t *c) const
|
||||||
{
|
{
|
||||||
TRACE_APPLY ();
|
TRACE_APPLY ();
|
||||||
unsigned int i, j;
|
unsigned int i;
|
||||||
|
unsigned int j = c->buffer->i;
|
||||||
unsigned int count = component.len;
|
unsigned int count = component.len;
|
||||||
unsigned int end = MIN (c->buffer->len, c->buffer->i + c->context_length);
|
unsigned int end = MIN (c->buffer->len, j + c->context_length);
|
||||||
if (unlikely (c->buffer->i + count > end))
|
if (unlikely (j >= end))
|
||||||
return false;
|
return false;
|
||||||
|
|
||||||
bool first_was_mark = (c->property & HB_OT_LAYOUT_GLYPH_CLASS_MARK);
|
bool first_was_mark = (c->property & HB_OT_LAYOUT_GLYPH_CLASS_MARK);
|
||||||
bool found_non_mark = false;
|
bool found_non_mark = false;
|
||||||
|
|
||||||
for (i = 1, j = c->buffer->i + 1; i < count; i++, j++)
|
for (i = 1; i < count; i++)
|
||||||
{
|
{
|
||||||
unsigned int property;
|
unsigned int property;
|
||||||
while (_hb_ot_layout_skip_mark (c->layout->face, &c->buffer->info[j], c->lookup_props, &property))
|
do
|
||||||
{
|
{
|
||||||
if (unlikely (j + count - i == end))
|
|
||||||
return false;
|
|
||||||
j++;
|
j++;
|
||||||
}
|
if (unlikely (j == end))
|
||||||
|
return false;
|
||||||
|
} while (_hb_ot_layout_skip_mark (c->layout->face, &c->buffer->info[j], c->lookup_props, &property));
|
||||||
|
|
||||||
found_non_mark |= !(property & HB_OT_LAYOUT_GLYPH_CLASS_MARK);
|
found_non_mark |= !(property & HB_OT_LAYOUT_GLYPH_CLASS_MARK);
|
||||||
|
|
||||||
|
@ -126,25 +126,26 @@ static inline bool match_input (hb_apply_context_t *c,
|
|||||||
const void *match_data,
|
const void *match_data,
|
||||||
unsigned int *context_length_out)
|
unsigned int *context_length_out)
|
||||||
{
|
{
|
||||||
unsigned int i, j;
|
unsigned int i;
|
||||||
unsigned int end = MIN (c->buffer->len, c->buffer->i + c->context_length);
|
unsigned int j = c->buffer->i;
|
||||||
if (unlikely (c->buffer->i + count > end))
|
unsigned int end = MIN (c->buffer->len, j + c->context_length);
|
||||||
|
if (unlikely (j + count > end))
|
||||||
return false;
|
return false;
|
||||||
|
|
||||||
for (i = 1, j = c->buffer->i + 1; i < count; i++, j++)
|
for (i = 1; i < count; i++)
|
||||||
{
|
{
|
||||||
while (_hb_ot_layout_skip_mark (c->layout->face, &c->buffer->info[j], c->lookup_props, NULL))
|
do
|
||||||
{
|
{
|
||||||
if (unlikely (j + count - i == end))
|
|
||||||
return false;
|
|
||||||
j++;
|
j++;
|
||||||
}
|
if (unlikely (j >= end))
|
||||||
|
return false;
|
||||||
|
} while (_hb_ot_layout_skip_mark (c->layout->face, &c->buffer->info[j], c->lookup_props, NULL));
|
||||||
|
|
||||||
if (likely (!match_func (c->buffer->info[j].codepoint, input[i - 1], match_data)))
|
if (likely (!match_func (c->buffer->info[j].codepoint, input[i - 1], match_data)))
|
||||||
return false;
|
return false;
|
||||||
}
|
}
|
||||||
|
|
||||||
*context_length_out = j - c->buffer->i;
|
*context_length_out = j - c->buffer->i + 1;
|
||||||
|
|
||||||
return true;
|
return true;
|
||||||
}
|
}
|
||||||
@ -155,17 +156,16 @@ static inline bool match_backtrack (hb_apply_context_t *c,
|
|||||||
match_func_t match_func,
|
match_func_t match_func,
|
||||||
const void *match_data)
|
const void *match_data)
|
||||||
{
|
{
|
||||||
if (unlikely (c->buffer->backtrack_len () < count))
|
unsigned int j = c->buffer->backtrack_len ();
|
||||||
return false;
|
|
||||||
|
|
||||||
for (unsigned int i = 0, j = c->buffer->backtrack_len () - 1; i < count; i++, j--)
|
for (unsigned int i = 0; i < count; i++)
|
||||||
{
|
{
|
||||||
while (_hb_ot_layout_skip_mark (c->layout->face, &c->buffer->out_info[j], c->lookup_props, NULL))
|
do
|
||||||
{
|
{
|
||||||
if (unlikely (j + 1 == count - i))
|
if (unlikely (!j))
|
||||||
return false;
|
return false;
|
||||||
j--;
|
j--;
|
||||||
}
|
} while (_hb_ot_layout_skip_mark (c->layout->face, &c->buffer->out_info[j], c->lookup_props, NULL));
|
||||||
|
|
||||||
if (likely (!match_func (c->buffer->out_info[j].codepoint, backtrack[i], match_data)))
|
if (likely (!match_func (c->buffer->out_info[j].codepoint, backtrack[i], match_data)))
|
||||||
return false;
|
return false;
|
||||||
@ -181,19 +181,18 @@ static inline bool match_lookahead (hb_apply_context_t *c,
|
|||||||
const void *match_data,
|
const void *match_data,
|
||||||
unsigned int offset)
|
unsigned int offset)
|
||||||
{
|
{
|
||||||
unsigned int i, j;
|
unsigned int i;
|
||||||
|
unsigned int j = c->buffer->i + offset - 1;
|
||||||
unsigned int end = MIN (c->buffer->len, c->buffer->i + c->context_length);
|
unsigned int end = MIN (c->buffer->len, c->buffer->i + c->context_length);
|
||||||
if (unlikely (c->buffer->i + offset + count > end))
|
|
||||||
return false;
|
|
||||||
|
|
||||||
for (i = 0, j = c->buffer->i + offset; i < count; i++, j++)
|
for (i = 0; i < count; i++)
|
||||||
{
|
{
|
||||||
while (_hb_ot_layout_skip_mark (c->layout->face, &c->buffer->info[j], c->lookup_props, NULL))
|
do
|
||||||
{
|
{
|
||||||
if (unlikely (j + count - i == end))
|
|
||||||
return false;
|
|
||||||
j++;
|
j++;
|
||||||
}
|
if (unlikely (j >= end))
|
||||||
|
return false;
|
||||||
|
} while (_hb_ot_layout_skip_mark (c->layout->face, &c->buffer->info[j], c->lookup_props, NULL));
|
||||||
|
|
||||||
if (likely (!match_func (c->buffer->info[j].codepoint, lookahead[i], match_data)))
|
if (likely (!match_func (c->buffer->info[j].codepoint, lookahead[i], match_data)))
|
||||||
return false;
|
return false;
|
||||||
|
@ -36,6 +36,8 @@
|
|||||||
*
|
*
|
||||||
* ***** END LICENSE BLOCK ***** */
|
* ***** END LICENSE BLOCK ***** */
|
||||||
|
|
||||||
|
#include "mozilla/Attributes.h"
|
||||||
|
|
||||||
#include "gfxSharedImageSurface.h"
|
#include "gfxSharedImageSurface.h"
|
||||||
|
|
||||||
#include "mozilla/layers/PLayerChild.h"
|
#include "mozilla/layers/PLayerChild.h"
|
||||||
@ -43,8 +45,6 @@
|
|||||||
#include "mozilla/layers/PLayersParent.h"
|
#include "mozilla/layers/PLayersParent.h"
|
||||||
#include "mozilla/gfx/2D.h"
|
#include "mozilla/gfx/2D.h"
|
||||||
|
|
||||||
#include "mozilla/Types.h"
|
|
||||||
|
|
||||||
#include "ipc/ShadowLayerChild.h"
|
#include "ipc/ShadowLayerChild.h"
|
||||||
|
|
||||||
#include "BasicLayers.h"
|
#include "BasicLayers.h"
|
||||||
|
@ -68,11 +68,9 @@ endif # GNU_CC
|
|||||||
|
|
||||||
# special rules for transform-sse*.c to get the right cflags. (taken from pixman/src/Makefile.in)
|
# special rules for transform-sse*.c to get the right cflags. (taken from pixman/src/Makefile.in)
|
||||||
transform-sse1.$(OBJ_SUFFIX): transform-sse1.c $(GLOBAL_DEPS)
|
transform-sse1.$(OBJ_SUFFIX): transform-sse1.c $(GLOBAL_DEPS)
|
||||||
$(REPORT_BUILD)
|
|
||||||
@$(MAKE_DEPS_AUTO_CC)
|
@$(MAKE_DEPS_AUTO_CC)
|
||||||
$(ELOG) $(CC) $(OUTOPTION)$@ -c $(COMPILE_CFLAGS) $(SSE1_FLAGS) $(_VPATH_SRCS)
|
$(ELOG) $(CC) $(OUTOPTION)$@ -c $(COMPILE_CFLAGS) $(SSE1_FLAGS) $(_VPATH_SRCS)
|
||||||
|
|
||||||
transform-sse2.$(OBJ_SUFFIX): transform-sse2.c $(GLOBAL_DEPS)
|
transform-sse2.$(OBJ_SUFFIX): transform-sse2.c $(GLOBAL_DEPS)
|
||||||
$(REPORT_BUILD)
|
|
||||||
@$(MAKE_DEPS_AUTO_CC)
|
@$(MAKE_DEPS_AUTO_CC)
|
||||||
$(ELOG) $(CC) $(OUTOPTION)$@ -c $(COMPILE_CFLAGS) $(SSE2_FLAGS) $(_VPATH_SRCS)
|
$(ELOG) $(CC) $(OUTOPTION)$@ -c $(COMPILE_CFLAGS) $(SSE2_FLAGS) $(_VPATH_SRCS)
|
||||||
|
@ -66,7 +66,7 @@ CPPSRCS = \
|
|||||||
SandboxHal.cpp \
|
SandboxHal.cpp \
|
||||||
$(NULL)
|
$(NULL)
|
||||||
|
|
||||||
ifeq (Android,$(OS_TARGET))
|
ifeq (android,$(MOZ_WIDGET_TOOLKIT))
|
||||||
CPPSRCS += AndroidHal.cpp
|
CPPSRCS += AndroidHal.cpp
|
||||||
else ifeq (Linux,$(OS_TARGET))
|
else ifeq (Linux,$(OS_TARGET))
|
||||||
CPPSRCS += LinuxHal.cpp
|
CPPSRCS += LinuxHal.cpp
|
||||||
|
@ -384,8 +384,6 @@ UPowerClient::UpdateSavedInfo(GHashTable* aHashTable)
|
|||||||
{
|
{
|
||||||
bool isFull = false;
|
bool isFull = false;
|
||||||
|
|
||||||
mLevel = g_value_get_double(static_cast<const GValue*>(g_hash_table_lookup(aHashTable, "Percentage")))*0.01;
|
|
||||||
|
|
||||||
/*
|
/*
|
||||||
* State values are confusing...
|
* State values are confusing...
|
||||||
* First of all, after looking at upower sources (0.9.13), it seems that
|
* First of all, after looking at upower sources (0.9.13), it seems that
|
||||||
@ -420,6 +418,17 @@ UPowerClient::UpdateSavedInfo(GHashTable* aHashTable)
|
|||||||
break;
|
break;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
/*
|
||||||
|
* The battery level might be very close to 100% (like 99.xxxx%) without
|
||||||
|
* increasing. It seems that upower sets the battery state as 'full' in that
|
||||||
|
* case so we should trust it and not even try to get the value.
|
||||||
|
*/
|
||||||
|
if (isFull) {
|
||||||
|
mLevel = 1.0;
|
||||||
|
} else {
|
||||||
|
mLevel = g_value_get_double(static_cast<const GValue*>(g_hash_table_lookup(aHashTable, "Percentage")))*0.01;
|
||||||
|
}
|
||||||
|
|
||||||
if (isFull) {
|
if (isFull) {
|
||||||
mRemainingTime = 0;
|
mRemainingTime = 0;
|
||||||
} else {
|
} else {
|
||||||
|
@ -41,6 +41,8 @@
|
|||||||
#ifndef mozilla_ipc_Shmem_h
|
#ifndef mozilla_ipc_Shmem_h
|
||||||
#define mozilla_ipc_Shmem_h
|
#define mozilla_ipc_Shmem_h
|
||||||
|
|
||||||
|
#include "mozilla/Attributes.h"
|
||||||
|
|
||||||
#include "base/basictypes.h"
|
#include "base/basictypes.h"
|
||||||
#include "base/process.h"
|
#include "base/process.h"
|
||||||
|
|
||||||
@ -87,7 +89,7 @@
|
|||||||
namespace mozilla {
|
namespace mozilla {
|
||||||
namespace ipc {
|
namespace ipc {
|
||||||
|
|
||||||
class NS_FINAL_CLASS Shmem
|
class Shmem MOZ_FINAL
|
||||||
{
|
{
|
||||||
friend struct IPC::ParamTraits<mozilla::ipc::Shmem>;
|
friend struct IPC::ParamTraits<mozilla::ipc::Shmem>;
|
||||||
|
|
||||||
|
@ -92,6 +92,7 @@ Types = (
|
|||||||
|
|
||||||
|
|
||||||
Includes = (
|
Includes = (
|
||||||
|
'mozilla/Attributes.h',
|
||||||
'base/basictypes.h',
|
'base/basictypes.h',
|
||||||
'prtime.h',
|
'prtime.h',
|
||||||
'nscore.h',
|
'nscore.h',
|
||||||
|
@ -161,9 +161,9 @@ class CxxCodeGen(CodePrinter, Visitor):
|
|||||||
if c.abstract:
|
if c.abstract:
|
||||||
# FIXME/cjones: turn this "on" when we get the analysis
|
# FIXME/cjones: turn this "on" when we get the analysis
|
||||||
self.write(' /*NS_ABSTRACT_CLASS*/')
|
self.write(' /*NS_ABSTRACT_CLASS*/')
|
||||||
if c.final:
|
|
||||||
self.write(' NS_FINAL_CLASS')
|
|
||||||
self.write(' '+ c.name)
|
self.write(' '+ c.name)
|
||||||
|
if c.final:
|
||||||
|
self.write(' MOZ_FINAL')
|
||||||
|
|
||||||
if c.specializes is not None:
|
if c.specializes is not None:
|
||||||
self.write(' <')
|
self.write(' <')
|
||||||
|
@ -220,7 +220,6 @@ INSTALLED_HEADERS = \
|
|||||||
jsreflect.h \
|
jsreflect.h \
|
||||||
jsstdint.h \
|
jsstdint.h \
|
||||||
jsstr.h \
|
jsstr.h \
|
||||||
jstracer.h \
|
|
||||||
jstypedarray.h \
|
jstypedarray.h \
|
||||||
jstypes.h \
|
jstypes.h \
|
||||||
jsutil.h \
|
jsutil.h \
|
||||||
@ -283,6 +282,7 @@ VPATH += \
|
|||||||
EXPORTS_NAMESPACES += mozilla
|
EXPORTS_NAMESPACES += mozilla
|
||||||
|
|
||||||
EXPORTS_mozilla = \
|
EXPORTS_mozilla = \
|
||||||
|
Attributes.h \
|
||||||
GuardObjects.h \
|
GuardObjects.h \
|
||||||
RangedPtr.h \
|
RangedPtr.h \
|
||||||
RefPtr.h \
|
RefPtr.h \
|
||||||
@ -290,53 +290,6 @@ EXPORTS_mozilla = \
|
|||||||
Util.h \
|
Util.h \
|
||||||
$(NULL)
|
$(NULL)
|
||||||
|
|
||||||
ifdef ENABLE_TRACEJIT
|
|
||||||
VPATH += \
|
|
||||||
$(srcdir)/tracejit \
|
|
||||||
$(srcdir)/nanojit \
|
|
||||||
|
|
||||||
INSTALLED_HEADERS += \
|
|
||||||
jsbuiltins.h \
|
|
||||||
Assembler.h \
|
|
||||||
Allocator.h \
|
|
||||||
CodeAlloc.h \
|
|
||||||
Containers.h \
|
|
||||||
LIR.h \
|
|
||||||
LIRopcode.tbl \
|
|
||||||
avmplus.h \
|
|
||||||
Fragmento.h \
|
|
||||||
Native.h \
|
|
||||||
NativeCommon.h \
|
|
||||||
Native$(NANOJIT_ARCH).h \
|
|
||||||
njconfig.h \
|
|
||||||
njcpudetect.h \
|
|
||||||
RegAlloc.h \
|
|
||||||
nanojit.h \
|
|
||||||
VMPI.h \
|
|
||||||
Writer.h \
|
|
||||||
$(NULL)
|
|
||||||
|
|
||||||
CPPSRCS += \
|
|
||||||
jstracer.cpp \
|
|
||||||
Assembler.cpp \
|
|
||||||
Allocator.cpp \
|
|
||||||
CodeAlloc.cpp \
|
|
||||||
Containers.cpp \
|
|
||||||
Fragmento.cpp \
|
|
||||||
LIR.cpp \
|
|
||||||
njconfig.cpp \
|
|
||||||
avmplus.cpp \
|
|
||||||
Native$(NANOJIT_ARCH).cpp \
|
|
||||||
jsbuiltins.cpp \
|
|
||||||
VMPI.cpp \
|
|
||||||
Writer.cpp \
|
|
||||||
$(NULL)
|
|
||||||
|
|
||||||
ifdef MOZ_DEBUG
|
|
||||||
CPPSRCS += RegAlloc.cpp
|
|
||||||
endif
|
|
||||||
|
|
||||||
endif # ENABLE_TRACEJIT
|
|
||||||
ifdef ENABLE_METHODJIT
|
ifdef ENABLE_METHODJIT
|
||||||
|
|
||||||
###############################################
|
###############################################
|
||||||
@ -691,7 +644,7 @@ ifneq ($(OS_ARCH),WINNT) # FIXME: this should be made work on Windows too.
|
|||||||
#check:: check-malloc-function-usage FIXME: disable on JM until closer to merge time.
|
#check:: check-malloc-function-usage FIXME: disable on JM until closer to merge time.
|
||||||
endif
|
endif
|
||||||
|
|
||||||
JITFLAGS = ,m,j,mj,mjp,am,amj,amjp,amd,n,mn,jn,mjn,mjpn,amn,amjn,amjpn,amdn
|
JITFLAGS = ,m,am,amd,n,mn,amn,amdn,mdn
|
||||||
check-jit-test::
|
check-jit-test::
|
||||||
$(wildcard $(RUN_TEST_PROGRAM)) $(PYTHON) -u $(srcdir)/jit-test/jit_test.py \
|
$(wildcard $(RUN_TEST_PROGRAM)) $(PYTHON) -u $(srcdir)/jit-test/jit_test.py \
|
||||||
--valgrind --no-slow --no-progress --tinderbox --jitflags=$(JITFLAGS) $(DIST)/bin/js$(BIN_SUFFIX)
|
--valgrind --no-slow --no-progress --tinderbox --jitflags=$(JITFLAGS) $(DIST)/bin/js$(BIN_SUFFIX)
|
||||||
@ -729,9 +682,6 @@ check-jstests:
|
|||||||
|
|
||||||
ifeq ($(OS_ARCH),WINNT)
|
ifeq ($(OS_ARCH),WINNT)
|
||||||
ifdef ENABLE_METHODJIT
|
ifdef ENABLE_METHODJIT
|
||||||
ifdef ENABLE_TRACEJIT
|
|
||||||
#check:: check-jstests
|
|
||||||
endif
|
|
||||||
endif
|
endif
|
||||||
else
|
else
|
||||||
ifndef HAVE_DTRACE
|
ifndef HAVE_DTRACE
|
||||||
@ -851,7 +801,6 @@ ifdef SOLARIS_SUNPRO_CXX
|
|||||||
ifeq ($(TARGET_CPU),sparc)
|
ifeq ($(TARGET_CPU),sparc)
|
||||||
# Sun Studio SPARC doesn't work well with gcc inline asm, use lock_SunOS_sparc*.il
|
# Sun Studio SPARC doesn't work well with gcc inline asm, use lock_SunOS_sparc*.il
|
||||||
jslock.o: jslock.cpp Makefile.in lock_sparcv8plus.il lock_sparcv9.il
|
jslock.o: jslock.cpp Makefile.in lock_sparcv8plus.il lock_sparcv9.il
|
||||||
$(REPORT_BUILD)
|
|
||||||
@$(MAKE_DEPS_AUTO_CXX)
|
@$(MAKE_DEPS_AUTO_CXX)
|
||||||
ifeq (sparcv9,$(findstring sparcv9,$(OS_TEST)))
|
ifeq (sparcv9,$(findstring sparcv9,$(OS_TEST)))
|
||||||
$(CXX) -o $@ -c $(COMPILE_CFLAGS) $(srcdir)/lock_sparcv9.il $<
|
$(CXX) -o $@ -c $(COMPILE_CFLAGS) $(srcdir)/lock_sparcv9.il $<
|
||||||
@ -865,11 +814,9 @@ endif # SOLARIS_SUNPRO_CXX
|
|||||||
# This suppresses optimization for this single compilation unit.
|
# This suppresses optimization for this single compilation unit.
|
||||||
ifeq ($(OS_ARCH),AIX)
|
ifeq ($(OS_ARCH),AIX)
|
||||||
jsatom.o: jsatom.cpp Makefile.in
|
jsatom.o: jsatom.cpp Makefile.in
|
||||||
$(REPORT_BUILD)
|
|
||||||
@$(MAKE_DEPS_AUTO_CXX)
|
@$(MAKE_DEPS_AUTO_CXX)
|
||||||
$(CXX) -o $@ -c $(filter-out $(MOZ_OPTIMIZE_FLAGS), $(COMPILE_CFLAGS)) $<
|
$(CXX) -o $@ -c $(filter-out $(MOZ_OPTIMIZE_FLAGS), $(COMPILE_CFLAGS)) $<
|
||||||
jsdtoa.o: jsdtoa.cpp Makefile.in
|
jsdtoa.o: jsdtoa.cpp Makefile.in
|
||||||
$(REPORT_BUILD)
|
|
||||||
@$(MAKE_DEPS_AUTO_CXX)
|
@$(MAKE_DEPS_AUTO_CXX)
|
||||||
$(CXX) -o $@ -c $(filter-out $(MOZ_OPTIMIZE_FLAGS), $(COMPILE_CFLAGS)) $<
|
$(CXX) -o $@ -c $(filter-out $(MOZ_OPTIMIZE_FLAGS), $(COMPILE_CFLAGS)) $<
|
||||||
endif
|
endif
|
||||||
@ -975,41 +922,6 @@ $(CURDIR)/javascript-trace.h: $(srcdir)/javascript-trace.d
|
|||||||
$(addsuffix .$(OBJ_SUFFIX),jsprobes jsinterp jsobj): $(CURDIR)/javascript-trace.h
|
$(addsuffix .$(OBJ_SUFFIX),jsprobes jsinterp jsobj): $(CURDIR)/javascript-trace.h
|
||||||
endif
|
endif
|
||||||
|
|
||||||
ifdef ENABLE_TRACEJIT
|
|
||||||
# Imacro compilation.
|
|
||||||
$(CURDIR)/imacros.c.out: $(srcdir)/imacro_asm.py $(srcdir)/imacros.jsasm jsopcode.tbl
|
|
||||||
$(PYTHON) $< $(srcdir)/imacros.jsasm $(CURDIR)/imacros.c.out
|
|
||||||
$(addsuffix .$(OBJ_SUFFIX),jstracer): $(CURDIR)/imacros.c.out
|
|
||||||
|
|
||||||
# Code for importing the nanojit subtree from its repository.
|
|
||||||
NANOJIT_CENTRAL_REV=$(shell cat $(srcdir)/nanojit-import-rev)
|
|
||||||
NANOJIT_CENTRAL_REPO=http://hg.mozilla.org/projects/nanojit-central
|
|
||||||
NANOJIT_CENTRAL_LOCAL=$(CURDIR)/nanojit-central
|
|
||||||
CUR_REPO=$(srcdir)/../..
|
|
||||||
|
|
||||||
update-nanojit:
|
|
||||||
$(RM) -r $(NANOJIT_CENTRAL_LOCAL) import-splicemap import-revmap
|
|
||||||
hg clone $(NANOJIT_CENTRAL_REPO) $(NANOJIT_CENTRAL_LOCAL)
|
|
||||||
python $(srcdir)/find-child.py \
|
|
||||||
--src=$(NANOJIT_CENTRAL_LOCAL) \
|
|
||||||
--dst=$(CUR_REPO) \
|
|
||||||
--start=$(NANOJIT_CENTRAL_REV) \
|
|
||||||
--filemap=$(srcdir)/nanojit-import-filemap \
|
|
||||||
>import-splicemap
|
|
||||||
hg convert --config convert.hg.saverev=True \
|
|
||||||
--config convert.hg.startrev=`cut -d ' ' -f 1 import-splicemap` \
|
|
||||||
--filemap=$(srcdir)/nanojit-import-filemap \
|
|
||||||
--splicemap=import-splicemap \
|
|
||||||
$(NANOJIT_CENTRAL_LOCAL) \
|
|
||||||
$(CUR_REPO) \
|
|
||||||
import-revmap
|
|
||||||
(cd $(srcdir) && hg up)
|
|
||||||
(cd $(NANOJIT_CENTRAL_LOCAL) && hg log -r tip --template "{node}\n") >$(srcdir)/nanojit-import-rev
|
|
||||||
(cd $(srcdir) && hg commit --message="Update nanojit-import-rev stamp." nanojit-import-rev)
|
|
||||||
|
|
||||||
.PHONY: update-nanojit
|
|
||||||
endif
|
|
||||||
|
|
||||||
###############################################
|
###############################################
|
||||||
# BEGIN kludges for the Nitro assembler
|
# BEGIN kludges for the Nitro assembler
|
||||||
#
|
#
|
||||||
@ -1019,7 +931,7 @@ endif
|
|||||||
# the code in js/src/assembler.
|
# the code in js/src/assembler.
|
||||||
CXXFLAGS += -DUSE_SYSTEM_MALLOC=1 -DENABLE_ASSEMBLER=1
|
CXXFLAGS += -DUSE_SYSTEM_MALLOC=1 -DENABLE_ASSEMBLER=1
|
||||||
|
|
||||||
ifneq (,$(ENABLE_YARR_JIT)$(ENABLE_TRACEJIT)$(ENABLE_METHODJIT))
|
ifneq (,$(ENABLE_YARR_JIT)$(ENABLE_METHODJIT))
|
||||||
CXXFLAGS += -DENABLE_JIT=1
|
CXXFLAGS += -DENABLE_JIT=1
|
||||||
endif
|
endif
|
||||||
|
|
||||||
|
@ -331,9 +331,7 @@ HAVE_DTRACE= @HAVE_DTRACE@
|
|||||||
VISIBILITY_FLAGS = @VISIBILITY_FLAGS@
|
VISIBILITY_FLAGS = @VISIBILITY_FLAGS@
|
||||||
WRAP_SYSTEM_INCLUDES = @WRAP_SYSTEM_INCLUDES@
|
WRAP_SYSTEM_INCLUDES = @WRAP_SYSTEM_INCLUDES@
|
||||||
|
|
||||||
ENABLE_TRACEJIT = @ENABLE_TRACEJIT@
|
|
||||||
ENABLE_METHODJIT = @ENABLE_METHODJIT@
|
ENABLE_METHODJIT = @ENABLE_METHODJIT@
|
||||||
NANOJIT_ARCH = @NANOJIT_ARCH@
|
|
||||||
HAVE_ARM_SIMD= @HAVE_ARM_SIMD@
|
HAVE_ARM_SIMD= @HAVE_ARM_SIMD@
|
||||||
|
|
||||||
JS_SHARED_LIBRARY = @JS_SHARED_LIBRARY@
|
JS_SHARED_LIBRARY = @JS_SHARED_LIBRARY@
|
||||||
|
@ -64,8 +64,6 @@ ifdef SDK_HEADERS
|
|||||||
EXPORTS += $(SDK_HEADERS)
|
EXPORTS += $(SDK_HEADERS)
|
||||||
endif
|
endif
|
||||||
|
|
||||||
REPORT_BUILD = @echo $(notdir $<)
|
|
||||||
|
|
||||||
ifeq ($(OS_ARCH),OS2)
|
ifeq ($(OS_ARCH),OS2)
|
||||||
EXEC =
|
EXEC =
|
||||||
else
|
else
|
||||||
@ -1150,32 +1148,25 @@ endif # MOZ_AUTO_DEPS
|
|||||||
|
|
||||||
# Rules for building native targets must come first because of the host_ prefix
|
# Rules for building native targets must come first because of the host_ prefix
|
||||||
host_%.$(OBJ_SUFFIX): %.c $(GLOBAL_DEPS)
|
host_%.$(OBJ_SUFFIX): %.c $(GLOBAL_DEPS)
|
||||||
$(REPORT_BUILD)
|
|
||||||
$(ELOG) $(HOST_CC) $(HOST_OUTOPTION)$@ -c $(HOST_CFLAGS) $(INCLUDES) $(NSPR_CFLAGS) $(_VPATH_SRCS)
|
$(ELOG) $(HOST_CC) $(HOST_OUTOPTION)$@ -c $(HOST_CFLAGS) $(INCLUDES) $(NSPR_CFLAGS) $(_VPATH_SRCS)
|
||||||
|
|
||||||
host_%.$(OBJ_SUFFIX): %.cpp $(GLOBAL_DEPS)
|
host_%.$(OBJ_SUFFIX): %.cpp $(GLOBAL_DEPS)
|
||||||
$(REPORT_BUILD)
|
|
||||||
$(ELOG) $(HOST_CXX) $(HOST_OUTOPTION)$@ -c $(HOST_CXXFLAGS) $(INCLUDES) $(NSPR_CFLAGS) $(_VPATH_SRCS)
|
$(ELOG) $(HOST_CXX) $(HOST_OUTOPTION)$@ -c $(HOST_CXXFLAGS) $(INCLUDES) $(NSPR_CFLAGS) $(_VPATH_SRCS)
|
||||||
|
|
||||||
host_%.$(OBJ_SUFFIX): %.cc $(GLOBAL_DEPS)
|
host_%.$(OBJ_SUFFIX): %.cc $(GLOBAL_DEPS)
|
||||||
$(REPORT_BUILD)
|
|
||||||
$(ELOG) $(HOST_CXX) $(HOST_OUTOPTION)$@ -c $(HOST_CXXFLAGS) $(INCLUDES) $(NSPR_CFLAGS) $(_VPATH_SRCS)
|
$(ELOG) $(HOST_CXX) $(HOST_OUTOPTION)$@ -c $(HOST_CXXFLAGS) $(INCLUDES) $(NSPR_CFLAGS) $(_VPATH_SRCS)
|
||||||
|
|
||||||
host_%.$(OBJ_SUFFIX): %.m $(GLOBAL_DEPS)
|
host_%.$(OBJ_SUFFIX): %.m $(GLOBAL_DEPS)
|
||||||
$(REPORT_BUILD)
|
|
||||||
$(ELOG) $(HOST_CC) $(HOST_OUTOPTION)$@ -c $(HOST_CFLAGS) $(HOST_CMFLAGS) $(INCLUDES) $(NSPR_CFLAGS) $(_VPATH_SRCS)
|
$(ELOG) $(HOST_CC) $(HOST_OUTOPTION)$@ -c $(HOST_CFLAGS) $(HOST_CMFLAGS) $(INCLUDES) $(NSPR_CFLAGS) $(_VPATH_SRCS)
|
||||||
|
|
||||||
host_%.$(OBJ_SUFFIX): %.mm $(GLOBAL_DEPS)
|
host_%.$(OBJ_SUFFIX): %.mm $(GLOBAL_DEPS)
|
||||||
$(REPORT_BUILD)
|
|
||||||
$(ELOG) $(HOST_CXX) $(HOST_OUTOPTION)$@ -c $(HOST_CXXFLAGS) $(HOST_CMMFLAGS) $(INCLUDES) $(NSPR_CFLAGS) $(_VPATH_SRCS)
|
$(ELOG) $(HOST_CXX) $(HOST_OUTOPTION)$@ -c $(HOST_CXXFLAGS) $(HOST_CMMFLAGS) $(INCLUDES) $(NSPR_CFLAGS) $(_VPATH_SRCS)
|
||||||
|
|
||||||
%:: %.c $(GLOBAL_DEPS)
|
%:: %.c $(GLOBAL_DEPS)
|
||||||
$(REPORT_BUILD)
|
|
||||||
@$(MAKE_DEPS_AUTO_CC)
|
@$(MAKE_DEPS_AUTO_CC)
|
||||||
$(ELOG) $(CC) $(CFLAGS) $(LDFLAGS) $(OUTOPTION)$@ $(_VPATH_SRCS)
|
$(ELOG) $(CC) $(CFLAGS) $(LDFLAGS) $(OUTOPTION)$@ $(_VPATH_SRCS)
|
||||||
|
|
||||||
%.$(OBJ_SUFFIX): %.c $(GLOBAL_DEPS)
|
%.$(OBJ_SUFFIX): %.c $(GLOBAL_DEPS)
|
||||||
$(REPORT_BUILD)
|
|
||||||
@$(MAKE_DEPS_AUTO_CC)
|
@$(MAKE_DEPS_AUTO_CC)
|
||||||
$(ELOG) $(CC) $(OUTOPTION)$@ -c $(COMPILE_CFLAGS) $(_VPATH_SRCS)
|
$(ELOG) $(CC) $(OUTOPTION)$@ -c $(COMPILE_CFLAGS) $(_VPATH_SRCS)
|
||||||
|
|
||||||
@ -1186,7 +1177,6 @@ moc_%.cpp: %.h $(GLOBAL_DEPS)
|
|||||||
$(MOC) $(DEFINES) $(ACDEFINES) $< $(OUTOPTION)$@
|
$(MOC) $(DEFINES) $(ACDEFINES) $< $(OUTOPTION)$@
|
||||||
|
|
||||||
moc_%.cc: %.cc $(GLOBAL_DEPS)
|
moc_%.cc: %.cc $(GLOBAL_DEPS)
|
||||||
$(REPORT_BUILD)
|
|
||||||
$(ELOG) $(MOC) $(DEFINES) $(ACDEFINES) $(_VPATH_SRCS:.cc=.h) $(OUTOPTION)$@
|
$(ELOG) $(MOC) $(DEFINES) $(ACDEFINES) $(_VPATH_SRCS:.cc=.h) $(OUTOPTION)$@
|
||||||
|
|
||||||
ifdef ASFILES
|
ifdef ASFILES
|
||||||
@ -1207,12 +1197,10 @@ endif
|
|||||||
# Please keep the next two rules in sync.
|
# Please keep the next two rules in sync.
|
||||||
#
|
#
|
||||||
%.$(OBJ_SUFFIX): %.cc $(GLOBAL_DEPS)
|
%.$(OBJ_SUFFIX): %.cc $(GLOBAL_DEPS)
|
||||||
$(REPORT_BUILD)
|
|
||||||
@$(MAKE_DEPS_AUTO_CXX)
|
@$(MAKE_DEPS_AUTO_CXX)
|
||||||
$(ELOG) $(CCC) $(OUTOPTION)$@ -c $(COMPILE_CXXFLAGS) $(_VPATH_SRCS)
|
$(ELOG) $(CCC) $(OUTOPTION)$@ -c $(COMPILE_CXXFLAGS) $(_VPATH_SRCS)
|
||||||
|
|
||||||
%.$(OBJ_SUFFIX): %.cpp $(GLOBAL_DEPS)
|
%.$(OBJ_SUFFIX): %.cpp $(GLOBAL_DEPS)
|
||||||
$(REPORT_BUILD)
|
|
||||||
@$(MAKE_DEPS_AUTO_CXX)
|
@$(MAKE_DEPS_AUTO_CXX)
|
||||||
ifdef STRICT_CPLUSPLUS_SUFFIX
|
ifdef STRICT_CPLUSPLUS_SUFFIX
|
||||||
echo "#line 1 \"$*.cpp\"" | cat - $*.cpp > t_$*.cc
|
echo "#line 1 \"$*.cpp\"" | cat - $*.cpp > t_$*.cc
|
||||||
@ -1223,12 +1211,10 @@ else
|
|||||||
endif #STRICT_CPLUSPLUS_SUFFIX
|
endif #STRICT_CPLUSPLUS_SUFFIX
|
||||||
|
|
||||||
$(OBJ_PREFIX)%.$(OBJ_SUFFIX): %.mm $(GLOBAL_DEPS)
|
$(OBJ_PREFIX)%.$(OBJ_SUFFIX): %.mm $(GLOBAL_DEPS)
|
||||||
$(REPORT_BUILD)
|
|
||||||
@$(MAKE_DEPS_AUTO_CXX)
|
@$(MAKE_DEPS_AUTO_CXX)
|
||||||
$(ELOG) $(CCC) -o $@ -c $(COMPILE_CXXFLAGS) $(COMPILE_CMMFLAGS) $(_VPATH_SRCS)
|
$(ELOG) $(CCC) -o $@ -c $(COMPILE_CXXFLAGS) $(COMPILE_CMMFLAGS) $(_VPATH_SRCS)
|
||||||
|
|
||||||
$(OBJ_PREFIX)%.$(OBJ_SUFFIX): %.m $(GLOBAL_DEPS)
|
$(OBJ_PREFIX)%.$(OBJ_SUFFIX): %.m $(GLOBAL_DEPS)
|
||||||
$(REPORT_BUILD)
|
|
||||||
@$(MAKE_DEPS_AUTO_CC)
|
@$(MAKE_DEPS_AUTO_CC)
|
||||||
$(ELOG) $(CC) -o $@ -c $(COMPILE_CFLAGS) $(COMPILE_CMFLAGS) $(_VPATH_SRCS)
|
$(ELOG) $(CC) -o $@ -c $(COMPILE_CFLAGS) $(COMPILE_CMFLAGS) $(_VPATH_SRCS)
|
||||||
|
|
||||||
@ -1478,7 +1464,6 @@ XPIDL_DEPS = \
|
|||||||
$(NULL)
|
$(NULL)
|
||||||
|
|
||||||
$(XPIDL_GEN_DIR)/%.h: %.idl $(XPIDL_DEPS) $(XPIDL_GEN_DIR)/.done
|
$(XPIDL_GEN_DIR)/%.h: %.idl $(XPIDL_DEPS) $(XPIDL_GEN_DIR)/.done
|
||||||
$(REPORT_BUILD)
|
|
||||||
$(PYTHON_PATH) \
|
$(PYTHON_PATH) \
|
||||||
-I$(topsrcdir)/other-licenses/ply \
|
-I$(topsrcdir)/other-licenses/ply \
|
||||||
-I$(topsrcdir)/xpcom/idl-parser \
|
-I$(topsrcdir)/xpcom/idl-parser \
|
||||||
@ -1490,7 +1475,6 @@ ifndef NO_GEN_XPT
|
|||||||
# generate intermediate .xpt files into $(XPIDL_GEN_DIR), then link
|
# generate intermediate .xpt files into $(XPIDL_GEN_DIR), then link
|
||||||
# into $(XPIDL_MODULE).xpt and export it to $(FINAL_TARGET)/components.
|
# into $(XPIDL_MODULE).xpt and export it to $(FINAL_TARGET)/components.
|
||||||
$(XPIDL_GEN_DIR)/%.xpt: %.idl $(XPIDL_DEPS) $(XPIDL_GEN_DIR)/.done
|
$(XPIDL_GEN_DIR)/%.xpt: %.idl $(XPIDL_DEPS) $(XPIDL_GEN_DIR)/.done
|
||||||
$(REPORT_BUILD)
|
|
||||||
$(PYTHON_PATH) \
|
$(PYTHON_PATH) \
|
||||||
-I$(topsrcdir)/other-licenses/ply \
|
-I$(topsrcdir)/other-licenses/ply \
|
||||||
-I$(topsrcdir)/xpcom/idl-parser \
|
-I$(topsrcdir)/xpcom/idl-parser \
|
||||||
@ -1779,15 +1763,12 @@ define MAKE_DEPS_NOAUTO
|
|||||||
endef
|
endef
|
||||||
|
|
||||||
$(MDDEPDIR)/%.pp: %.c
|
$(MDDEPDIR)/%.pp: %.c
|
||||||
$(REPORT_BUILD)
|
|
||||||
@$(MAKE_DEPS_NOAUTO)
|
@$(MAKE_DEPS_NOAUTO)
|
||||||
|
|
||||||
$(MDDEPDIR)/%.pp: %.cpp
|
$(MDDEPDIR)/%.pp: %.cpp
|
||||||
$(REPORT_BUILD)
|
|
||||||
@$(MAKE_DEPS_NOAUTO)
|
@$(MAKE_DEPS_NOAUTO)
|
||||||
|
|
||||||
$(MDDEPDIR)/%.pp: %.s
|
$(MDDEPDIR)/%.pp: %.s
|
||||||
$(REPORT_BUILD)
|
|
||||||
@$(MAKE_DEPS_NOAUTO)
|
@$(MAKE_DEPS_NOAUTO)
|
||||||
|
|
||||||
ifneq (,$(OBJS)$(XPIDLSRCS)$(SIMPLE_PROGRAMS))
|
ifneq (,$(OBJS)$(XPIDLSRCS)$(SIMPLE_PROGRAMS))
|
||||||
|
@ -2790,7 +2790,6 @@ dnl Configure JIT support
|
|||||||
|
|
||||||
case "$target" in
|
case "$target" in
|
||||||
i?86-*)
|
i?86-*)
|
||||||
NANOJIT_ARCH=i386
|
|
||||||
ENABLE_METHODJIT=1
|
ENABLE_METHODJIT=1
|
||||||
ENABLE_MONOIC=1
|
ENABLE_MONOIC=1
|
||||||
ENABLE_POLYIC=1
|
ENABLE_POLYIC=1
|
||||||
@ -2799,7 +2798,6 @@ i?86-*)
|
|||||||
AC_DEFINE(JS_NUNBOX32)
|
AC_DEFINE(JS_NUNBOX32)
|
||||||
;;
|
;;
|
||||||
x86_64*-*)
|
x86_64*-*)
|
||||||
NANOJIT_ARCH=X64
|
|
||||||
ENABLE_METHODJIT=1
|
ENABLE_METHODJIT=1
|
||||||
ENABLE_MONOIC=1
|
ENABLE_MONOIC=1
|
||||||
ENABLE_POLYIC=1
|
ENABLE_POLYIC=1
|
||||||
@ -2808,7 +2806,6 @@ x86_64*-*)
|
|||||||
AC_DEFINE(JS_PUNBOX64)
|
AC_DEFINE(JS_PUNBOX64)
|
||||||
;;
|
;;
|
||||||
arm*-*)
|
arm*-*)
|
||||||
NANOJIT_ARCH=ARM
|
|
||||||
ENABLE_METHODJIT=1
|
ENABLE_METHODJIT=1
|
||||||
ENABLE_MONOIC=1
|
ENABLE_MONOIC=1
|
||||||
ENABLE_POLYIC=1
|
ENABLE_POLYIC=1
|
||||||
@ -2817,7 +2814,6 @@ arm*-*)
|
|||||||
AC_DEFINE(JS_NUNBOX32)
|
AC_DEFINE(JS_NUNBOX32)
|
||||||
;;
|
;;
|
||||||
sparc*-*)
|
sparc*-*)
|
||||||
NANOJIT_ARCH=Sparc
|
|
||||||
ENABLE_METHODJIT=1
|
ENABLE_METHODJIT=1
|
||||||
ENABLE_MONOIC=1
|
ENABLE_MONOIC=1
|
||||||
ENABLE_POLYIC=1
|
ENABLE_POLYIC=1
|
||||||
@ -2840,8 +2836,8 @@ MOZ_ARG_DISABLE_BOOL(polyic,
|
|||||||
ENABLE_POLYIC= )
|
ENABLE_POLYIC= )
|
||||||
|
|
||||||
MOZ_ARG_ENABLE_BOOL(tracejit,
|
MOZ_ARG_ENABLE_BOOL(tracejit,
|
||||||
[ --enable-tracejit Enable tracing JIT support],
|
[ --enable-tracejit Deprecated, does nothing],
|
||||||
ENABLE_TRACEJIT=1,
|
ENABLE_TRACEJIT=,
|
||||||
ENABLE_TRACEJIT= )
|
ENABLE_TRACEJIT= )
|
||||||
|
|
||||||
MOZ_ARG_ENABLE_BOOL(methodjit-spew,
|
MOZ_ARG_ENABLE_BOOL(methodjit-spew,
|
||||||
@ -2871,62 +2867,6 @@ if test "$ENABLE_METHODJIT_SPEW"; then
|
|||||||
AC_DEFINE(JS_METHODJIT_SPEW)
|
AC_DEFINE(JS_METHODJIT_SPEW)
|
||||||
fi
|
fi
|
||||||
|
|
||||||
if test "$ENABLE_TRACEJIT"; then
|
|
||||||
|
|
||||||
AC_DEFINE(FEATURE_NANOJIT)
|
|
||||||
AC_DEFINE(JS_TRACER)
|
|
||||||
|
|
||||||
case "$target" in
|
|
||||||
i?86-*)
|
|
||||||
AC_DEFINE(AVMPLUS_IA32)
|
|
||||||
;;
|
|
||||||
x86_64*-*)
|
|
||||||
AC_DEFINE(AVMPLUS_AMD64)
|
|
||||||
AC_DEFINE(AVMPLUS_64BIT)
|
|
||||||
;;
|
|
||||||
arm*-*)
|
|
||||||
AC_DEFINE(AVMPLUS_ARM)
|
|
||||||
;;
|
|
||||||
sparc-*)
|
|
||||||
AC_DEFINE(AVMPLUS_SPARC)
|
|
||||||
;;
|
|
||||||
esac
|
|
||||||
|
|
||||||
case "$target" in
|
|
||||||
*-linux*|*-android*|*-linuxandroid*)
|
|
||||||
AC_DEFINE(AVMPLUS_UNIX)
|
|
||||||
AC_DEFINE(AVMPLUS_LINUX)
|
|
||||||
;;
|
|
||||||
*-darwin*)
|
|
||||||
AC_DEFINE(AVMPLUS_UNIX)
|
|
||||||
;;
|
|
||||||
*-solaris*)
|
|
||||||
AC_DEFINE(AVMPLUS_UNIX)
|
|
||||||
;;
|
|
||||||
*-freebsd*|*-kfreebsd*)
|
|
||||||
AC_DEFINE(AVMPLUS_UNIX)
|
|
||||||
;;
|
|
||||||
*-openbsd*)
|
|
||||||
AC_DEFINE(AVMPLUS_UNIX)
|
|
||||||
;;
|
|
||||||
*-gnu*)
|
|
||||||
AC_DEFINE(AVMPLUS_UNIX)
|
|
||||||
;;
|
|
||||||
*-mingw*)
|
|
||||||
AC_DEFINE(AVMPLUS_WIN32)
|
|
||||||
;;
|
|
||||||
*-os2*)
|
|
||||||
AC_DEFINE(AVMPLUS_OS2)
|
|
||||||
;;
|
|
||||||
*)
|
|
||||||
AC_MSG_ERROR([Unrecognized nanojit platform. Use --disable-tracejit to build without tracing JIT support.])
|
|
||||||
esac
|
|
||||||
|
|
||||||
fi # ENABLE_TRACEJIT
|
|
||||||
|
|
||||||
AC_SUBST(ENABLE_TRACEJIT)
|
|
||||||
AC_SUBST(NANOJIT_ARCH)
|
|
||||||
|
|
||||||
if test -z "$SKIP_COMPILER_CHECKS"; then
|
if test -z "$SKIP_COMPILER_CHECKS"; then
|
||||||
dnl Checks for typedefs, structures, and compiler characteristics.
|
dnl Checks for typedefs, structures, and compiler characteristics.
|
||||||
dnl ========================================================
|
dnl ========================================================
|
||||||
@ -4503,20 +4443,6 @@ if test -n "$MOZ_TRACE_JSCALLS"; then
|
|||||||
AC_DEFINE(MOZ_TRACE_JSCALLS)
|
AC_DEFINE(MOZ_TRACE_JSCALLS)
|
||||||
fi
|
fi
|
||||||
|
|
||||||
dnl ========================================================
|
|
||||||
dnl = Use TraceVis
|
|
||||||
dnl ========================================================
|
|
||||||
MOZ_ARG_ENABLE_BOOL(tracevis,
|
|
||||||
[ --enable-tracevis Enable TraceVis tracing tool (default=no)],
|
|
||||||
MOZ_TRACEVIS=1,
|
|
||||||
MOZ_TRACEVIS= )
|
|
||||||
if test -n "$MOZ_TRACEVIS"; then
|
|
||||||
AC_DEFINE(MOZ_TRACEVIS)
|
|
||||||
if test -z "$ENABLE_TRACEJIT"; then
|
|
||||||
AC_MSG_ERROR([--enable-tracevis is incompatible with --disable-tracejit])
|
|
||||||
fi
|
|
||||||
fi
|
|
||||||
|
|
||||||
dnl ========================================================
|
dnl ========================================================
|
||||||
dnl = Use incremental GC
|
dnl = Use incremental GC
|
||||||
dnl ========================================================
|
dnl ========================================================
|
||||||
|
@ -89,10 +89,6 @@ using namespace js;
|
|||||||
using namespace js::gc;
|
using namespace js::gc;
|
||||||
using namespace js::frontend;
|
using namespace js::frontend;
|
||||||
|
|
||||||
#ifdef JS_TRACER
|
|
||||||
extern uint8 js_opcode2extra[];
|
|
||||||
#endif
|
|
||||||
|
|
||||||
static JSBool
|
static JSBool
|
||||||
NewTryNote(JSContext *cx, BytecodeEmitter *bce, JSTryNoteKind kind, uintN stackDepth,
|
NewTryNote(JSContext *cx, BytecodeEmitter *bce, JSTryNoteKind kind, uintN stackDepth,
|
||||||
size_t start, size_t end);
|
size_t start, size_t end);
|
||||||
@ -204,21 +200,15 @@ UpdateDepth(JSContext *cx, BytecodeEmitter *bce, ptrdiff_t target)
|
|||||||
jsbytecode *pc;
|
jsbytecode *pc;
|
||||||
JSOp op;
|
JSOp op;
|
||||||
const JSCodeSpec *cs;
|
const JSCodeSpec *cs;
|
||||||
uintN extra, nuses;
|
uintN nuses;
|
||||||
intN ndefs;
|
intN ndefs;
|
||||||
|
|
||||||
pc = bce->code(target);
|
pc = bce->code(target);
|
||||||
op = (JSOp) *pc;
|
op = (JSOp) *pc;
|
||||||
cs = &js_CodeSpec[op];
|
cs = &js_CodeSpec[op];
|
||||||
#ifdef JS_TRACER
|
if ((cs->format & JOF_TMPSLOT_MASK)) {
|
||||||
extra = js_opcode2extra[op];
|
|
||||||
#else
|
|
||||||
extra = 0;
|
|
||||||
#endif
|
|
||||||
if ((cs->format & JOF_TMPSLOT_MASK) || extra) {
|
|
||||||
uintN depth = (uintN) bce->stackDepth +
|
uintN depth = (uintN) bce->stackDepth +
|
||||||
((cs->format & JOF_TMPSLOT_MASK) >> JOF_TMPSLOT_SHIFT) +
|
((cs->format & JOF_TMPSLOT_MASK) >> JOF_TMPSLOT_SHIFT);
|
||||||
extra;
|
|
||||||
if (depth > bce->maxStackDepth)
|
if (depth > bce->maxStackDepth)
|
||||||
bce->maxStackDepth = depth;
|
bce->maxStackDepth = depth;
|
||||||
}
|
}
|
||||||
|
@ -335,7 +335,7 @@ class HeapValue
|
|||||||
bool toBoolean() const { return value.toBoolean(); }
|
bool toBoolean() const { return value.toBoolean(); }
|
||||||
double toNumber() const { return value.toNumber(); }
|
double toNumber() const { return value.toNumber(); }
|
||||||
|
|
||||||
unsigned gcKind() const { return value.gcKind(); }
|
JSGCTraceKind gcKind() const { return value.gcKind(); }
|
||||||
|
|
||||||
inline void boxNonDoubleFrom(JSValueType type, uint64 *out);
|
inline void boxNonDoubleFrom(JSValueType type, uint64 *out);
|
||||||
|
|
||||||
|
@ -1,467 +0,0 @@
|
|||||||
#!/usr/bin/env python
|
|
||||||
# -*- Mode: Python; tab-width: 4; indent-tabs-mode: nil -*-
|
|
||||||
# ***** BEGIN LICENSE BLOCK *****
|
|
||||||
# Version: MPL 1.1/GPL 2.0/LGPL 2.1
|
|
||||||
#
|
|
||||||
# The contents of this file are subject to the Mozilla Public License Version
|
|
||||||
# 1.1 (the "License"); you may not use this file except in compliance with
|
|
||||||
# the License. You may obtain a copy of the License at
|
|
||||||
# http://www.mozilla.org/MPL/
|
|
||||||
#
|
|
||||||
# Software distributed under the License is distributed on an "AS IS" basis,
|
|
||||||
# WITHOUT WARRANTY OF ANY KIND, either express or implied. See the License
|
|
||||||
# for the specific language governing rights and limitations under the
|
|
||||||
# License.
|
|
||||||
#
|
|
||||||
# The Original Code is the TraceMonkey IMacro Assembler.
|
|
||||||
#
|
|
||||||
# The Initial Developer of the Original Code is
|
|
||||||
# Brendan Eich <brendan@mozilla.org>.
|
|
||||||
# Portions created by the Initial Developer are Copyright (C) 2008
|
|
||||||
# the Initial Developer. All Rights Reserved.
|
|
||||||
#
|
|
||||||
# Contributor(s):
|
|
||||||
#
|
|
||||||
# Alternatively, the contents of this file may be used under the terms of
|
|
||||||
# either the GNU General Public License Version 2 or later (the "GPL"), or
|
|
||||||
# the GNU Lesser General Public License Version 2.1 or later (the "LGPL"),
|
|
||||||
# in which case the provisions of the GPL or the LGPL are applicable instead
|
|
||||||
# of those above. If you wish to allow use of your version of this file only
|
|
||||||
# under the terms of either the GPL or the LGPL, and not to allow others to
|
|
||||||
# use your version of this file under the terms of the MPL, indicate your
|
|
||||||
# decision by deleting the provisions above and replace them with the notice
|
|
||||||
# and other provisions required by the GPL or the LGPL. If you do not delete
|
|
||||||
# the provisions above, a recipient may use your version of this file under
|
|
||||||
# the terms of any one of the MPL, the GPL or the LGPL.
|
|
||||||
#
|
|
||||||
# ***** END LICENSE BLOCK *****
|
|
||||||
|
|
||||||
# An imacro (interpreter-macro) assembler in Python.
|
|
||||||
#
|
|
||||||
# Filename suffix conventions, used by Makefile.in rules:
|
|
||||||
# .jsasm SpiderMonkey JS assembly source, which could be input to other
|
|
||||||
# assemblers than imacro_asm.js, hence the generic suffix!
|
|
||||||
# .c.out C source output by imacro_asm.js
|
|
||||||
|
|
||||||
import re
|
|
||||||
import os
|
|
||||||
|
|
||||||
class Op:
|
|
||||||
def __init__(self, jsop, opcode, opname, opsrc, oplen, pops, pushes, precedence, flags):
|
|
||||||
self.jsop = jsop
|
|
||||||
self.opcode = opcode
|
|
||||||
self.opname = opname
|
|
||||||
self.opsrc = opsrc
|
|
||||||
self.oplen = oplen
|
|
||||||
self.pops = pops
|
|
||||||
self.pushes = pushes
|
|
||||||
self.precedence = precedence
|
|
||||||
self.flags = flags
|
|
||||||
|
|
||||||
def readFileLines(filename):
|
|
||||||
f = open(filename)
|
|
||||||
try:
|
|
||||||
return f.readlines()
|
|
||||||
finally:
|
|
||||||
f.close()
|
|
||||||
|
|
||||||
def load_ops(filename):
|
|
||||||
opdef_regexp = re.compile(r'''(?x)
|
|
||||||
^ OPDEF \( (JSOP_\w+), \s* # op
|
|
||||||
([0-9]+), \s* # val
|
|
||||||
("[^"]+" | [\w_]+), \s* # name
|
|
||||||
("[^"]+" | [\w_]+), \s* # image
|
|
||||||
(-1|[0-9]+), \s* # len
|
|
||||||
(-1|[0-9]+), \s* # uses
|
|
||||||
(-1|[0-9]+), \s* # defs
|
|
||||||
([0-9]+), \s* # prec
|
|
||||||
([\w_| ]+) \s* # format
|
|
||||||
\) \s* $''')
|
|
||||||
|
|
||||||
def decode_string_expr(expr):
|
|
||||||
if expr == 'NULL':
|
|
||||||
return None
|
|
||||||
if expr[0] == '"':
|
|
||||||
assert expr[-1] == '"'
|
|
||||||
return expr[1:-1]
|
|
||||||
assert expr.startswith('js_') and expr.endswith('_str')
|
|
||||||
return expr[3:-4]
|
|
||||||
|
|
||||||
opinfo = []
|
|
||||||
for lineno, line in enumerate(readFileLines(filename)):
|
|
||||||
if line.startswith('OPDEF'):
|
|
||||||
m = opdef_regexp.match(line)
|
|
||||||
if m is None:
|
|
||||||
raise ValueError("OPDEF line of wrong format in jsopcode.tbl at line %d" % (lineno + 1))
|
|
||||||
jsop, opcode, opname, opsrc, oplen, pops, pushes, precedence, flags = m.groups()
|
|
||||||
assert int(opcode) == len(opinfo)
|
|
||||||
opinfo.append(Op(jsop, int(opcode), decode_string_expr(opname),
|
|
||||||
decode_string_expr(opsrc), int(oplen), int(pops), int(pushes),
|
|
||||||
int(precedence), flags.replace(' ', '').split('|')))
|
|
||||||
return opinfo
|
|
||||||
|
|
||||||
opinfo = load_ops(os.path.join(os.path.dirname(__file__), "jsopcode.tbl"))
|
|
||||||
opname2info = dict((info.opname, info) for info in opinfo)
|
|
||||||
jsop2opcode = dict((info.jsop, info.opcode) for info in opinfo)
|
|
||||||
|
|
||||||
def to_uint8(s):
|
|
||||||
try:
|
|
||||||
n = int(s)
|
|
||||||
except ValueError:
|
|
||||||
n = -1
|
|
||||||
if 0 <= n < (1<<8):
|
|
||||||
return n
|
|
||||||
raise ValueError("invalid 8-bit operand: " + s)
|
|
||||||
|
|
||||||
def to_uint16(s):
|
|
||||||
try:
|
|
||||||
n = int(s)
|
|
||||||
except ValueError:
|
|
||||||
n = -1
|
|
||||||
if 0 <= n < (1<<16):
|
|
||||||
return n
|
|
||||||
raise ValueError("invalid 16-bit operand: " + s)
|
|
||||||
|
|
||||||
def immediate(op):
|
|
||||||
info = op.info
|
|
||||||
imm1Expr = op.imm1.startswith('(')
|
|
||||||
if 'JOF_ATOM' in info.flags:
|
|
||||||
if op.imm1 in ('void', 'object', 'function', 'string', 'number', 'boolean'):
|
|
||||||
return "0, COMMON_TYPE_ATOM_INDEX(JSTYPE_%s)" % op.imm1.upper()
|
|
||||||
return "0, COMMON_ATOM_INDEX(%s)" % op.imm1
|
|
||||||
if 'JOF_JUMP' in info.flags:
|
|
||||||
assert not imm1Expr
|
|
||||||
return "%d, %d" % ((op.target >> 8) & 0xff, op.target & 0xff)
|
|
||||||
if 'JOF_UINT8' in info.flags or 'JOF_INT8' in info.flags:
|
|
||||||
if imm1Expr:
|
|
||||||
return op.imm1
|
|
||||||
return str(to_uint8(op.imm1))
|
|
||||||
if 'JOF_UINT16' in info.flags:
|
|
||||||
if imm1Expr:
|
|
||||||
return '(%s & 0xff00) >> 8, (%s & 0xff)' % (op.imm1, op.imm1)
|
|
||||||
v = to_uint16(op.imm1)
|
|
||||||
return "%d, %d" % ((v & 0xff00) >> 8, v & 0xff)
|
|
||||||
raise NotImplementedError(info.jsop + " format not yet implemented")
|
|
||||||
|
|
||||||
def simulate_cfg(igroup, imacro, depth, i):
|
|
||||||
any_group_opcode = None
|
|
||||||
expected_depth = None
|
|
||||||
for opcode in igroup.ops:
|
|
||||||
opi = opinfo[opcode]
|
|
||||||
if any_group_opcode is None:
|
|
||||||
any_group_opcode = opcode
|
|
||||||
if opi.pops < 0:
|
|
||||||
expected_depth = None
|
|
||||||
else:
|
|
||||||
expected_depth = opi.pushes - opi.pops
|
|
||||||
elif expected_depth is None:
|
|
||||||
if opi.pops >= 0:
|
|
||||||
raise ValueError("imacro shared by constant- and variable-stack-defs/uses instructions")
|
|
||||||
else:
|
|
||||||
if opi.pops < 0:
|
|
||||||
raise ValueError("imacro shared by constant- and variable-stack-defs/uses instructions")
|
|
||||||
if opi.pushes - opi.pops != expected_depth:
|
|
||||||
raise ValueError("imacro shared by instructions with different stack depths")
|
|
||||||
|
|
||||||
for i in range(i, len(imacro.code)):
|
|
||||||
op = imacro.code[i]
|
|
||||||
opi = op.info
|
|
||||||
if opi.opname == 'imacop':
|
|
||||||
opi = opinfo[any_group_opcode]
|
|
||||||
|
|
||||||
if opi.pops < 0:
|
|
||||||
depth -= 2 + int(op.imm1)
|
|
||||||
else:
|
|
||||||
depth -= opi.pops
|
|
||||||
depth += opi.pushes
|
|
||||||
|
|
||||||
if i in imacro.depths and imacro.depths[i] != depth:
|
|
||||||
raise ValueError("Mismatched depth at %s:%d" % (imacro.filename, op.line))
|
|
||||||
|
|
||||||
# Underflowing depth isn't necessarily fatal; most of the imacros
|
|
||||||
# assume they are called with N>0 args so some assume it's ok to go
|
|
||||||
# to some depth <N. We simulate starting from 0, as we've no idea
|
|
||||||
# what else to do.
|
|
||||||
#
|
|
||||||
# if depth < 0:
|
|
||||||
# raise ValueError("Negative static-stack depth at %s:%d" % (imacro.filename, op.line))
|
|
||||||
if depth > imacro.maxdepth:
|
|
||||||
imacro.maxdepth = depth
|
|
||||||
imacro.depths[i] = depth
|
|
||||||
|
|
||||||
if hasattr(op, "target_index"):
|
|
||||||
if op.target_index <= i:
|
|
||||||
raise ValueError("Backward jump at %s:%d" % (imacro.filename, op.line))
|
|
||||||
simulate_cfg(igroup, imacro, depth, op.target_index)
|
|
||||||
if op.info.opname in ('goto', 'gotox'):
|
|
||||||
return
|
|
||||||
|
|
||||||
if expected_depth is not None and depth != expected_depth:
|
|
||||||
raise ValueError("Expected depth %d, got %d" % (expected_depth, depth))
|
|
||||||
|
|
||||||
|
|
||||||
# Syntax (spaces are significant only to delimit tokens):
|
|
||||||
#
|
|
||||||
# Assembly ::= (Directive? '\n')*
|
|
||||||
# Directive ::= (name ':')? Operation
|
|
||||||
# Operation ::= opname Operands?
|
|
||||||
# Operands ::= Operand (',' Operand)*
|
|
||||||
# Operand ::= name | number | '(' Expr ')'
|
|
||||||
# Expr ::= a constant-expression in the C++ language
|
|
||||||
# containing no parentheses
|
|
||||||
#
|
|
||||||
# We simplify given line structure and the maximum of one immediate operand,
|
|
||||||
# by parsing using split and regexps. For ease of parsing, parentheses are
|
|
||||||
# banned in an Expr for now, even in quotes or a C++ comment.
|
|
||||||
#
|
|
||||||
# Pseudo-ops start with . and include .igroup and .imacro, terminated by .end.
|
|
||||||
# .imacro must nest in .igroup, neither nests in itself. See imacros.jsasm for
|
|
||||||
# examples.
|
|
||||||
#
|
|
||||||
line_regexp = re.compile(r'''(?x)
|
|
||||||
^
|
|
||||||
(?: (\w+): )? # optional label at start of line
|
|
||||||
\s* (\.?\w+) # optional spaces, (pseudo-)opcode
|
|
||||||
(?: \s+ ([+-]?\w+ | \([^)]*\)) )? # optional first immediate operand
|
|
||||||
(?: \s+ ([\w,-]+ | \([^)]*\)) )? # optional second immediate operand
|
|
||||||
(?: \s* (?:\#.*) )? # optional spaces and comment
|
|
||||||
$''')
|
|
||||||
|
|
||||||
oprange_regexp = re.compile(r'^\w+(?:-\w+)?(?:,\w+(?:-\w+)?)*$')
|
|
||||||
|
|
||||||
class IGroup(object):
|
|
||||||
def __init__(self, name, ops):
|
|
||||||
self.name = name
|
|
||||||
self.ops = ops
|
|
||||||
self.imacros = []
|
|
||||||
|
|
||||||
class IMacro(object):
|
|
||||||
def __init__(self, name, filename):
|
|
||||||
self.name = name
|
|
||||||
self.offset = 0
|
|
||||||
self.code = []
|
|
||||||
self.labeldefs = {}
|
|
||||||
self.labeldef_indexes = {}
|
|
||||||
self.labelrefs = {}
|
|
||||||
self.filename = filename
|
|
||||||
self.depths = {}
|
|
||||||
self.initdepth = 0
|
|
||||||
|
|
||||||
class Instruction(object):
|
|
||||||
def __init__(self, offset, info, imm1, imm2, lineno):
|
|
||||||
self.offset = offset
|
|
||||||
self.info = info
|
|
||||||
self.imm1 = imm1
|
|
||||||
self.imm2 = imm2
|
|
||||||
self.lineno = lineno
|
|
||||||
|
|
||||||
def assemble(filename, outfile):
|
|
||||||
write = outfile.write
|
|
||||||
igroup = None
|
|
||||||
imacro = None
|
|
||||||
opcode2extra = {}
|
|
||||||
igroups = []
|
|
||||||
|
|
||||||
write("/* GENERATED BY imacro_asm.js -- DO NOT EDIT!!! */\n")
|
|
||||||
|
|
||||||
def fail(msg, *args):
|
|
||||||
raise ValueError("%s at %s:%d" % (msg % args, filename, lineno + 1))
|
|
||||||
|
|
||||||
for lineno, line in enumerate(readFileLines(filename)):
|
|
||||||
# strip comments
|
|
||||||
line = re.sub(r'#.*', '', line).rstrip()
|
|
||||||
if line == "":
|
|
||||||
continue
|
|
||||||
m = line_regexp.match(line)
|
|
||||||
if m is None:
|
|
||||||
fail(line)
|
|
||||||
|
|
||||||
label, opname, imm1, imm2 = m.groups()
|
|
||||||
|
|
||||||
if opname.startswith('.'):
|
|
||||||
if label is not None:
|
|
||||||
fail("invalid label %s before %s" % (label, opname))
|
|
||||||
|
|
||||||
if opname == '.igroup':
|
|
||||||
if imm1 is None:
|
|
||||||
fail("missing .igroup name")
|
|
||||||
if igroup is not None:
|
|
||||||
fail("nested .igroup " + imm1)
|
|
||||||
if oprange_regexp.match(imm2) is None:
|
|
||||||
fail("invalid igroup operator range " + imm2)
|
|
||||||
|
|
||||||
ops = set()
|
|
||||||
for current in imm2.split(","):
|
|
||||||
split = current.split('-')
|
|
||||||
opcode = jsop2opcode[split[0]]
|
|
||||||
if len(split) == 1:
|
|
||||||
lastopcode = opcode
|
|
||||||
else:
|
|
||||||
assert len(split) == 2
|
|
||||||
lastopcode = jsop2opcode[split[1]]
|
|
||||||
if opcode >= lastopcode:
|
|
||||||
fail("invalid opcode range: " + current)
|
|
||||||
|
|
||||||
for opcode in range(opcode, lastopcode + 1):
|
|
||||||
if opcode in ops:
|
|
||||||
fail("repeated opcode " + opinfo[opcode].jsop)
|
|
||||||
ops.add(opcode)
|
|
||||||
|
|
||||||
igroup = IGroup(imm1, ops)
|
|
||||||
|
|
||||||
elif opname == '.imacro':
|
|
||||||
if igroup is None:
|
|
||||||
fail(".imacro outside of .igroup")
|
|
||||||
if imm1 is None:
|
|
||||||
fail("missing .imacro name")
|
|
||||||
if imacro:
|
|
||||||
fail("nested .imacro " + imm1)
|
|
||||||
imacro = IMacro(imm1, filename)
|
|
||||||
|
|
||||||
elif opname == '.fixup':
|
|
||||||
if imacro is None:
|
|
||||||
fail(".fixup outside of .imacro")
|
|
||||||
if len(imacro.code) != 0:
|
|
||||||
fail(".fixup must be first item in .imacro")
|
|
||||||
if imm1 is None:
|
|
||||||
fail("missing .fixup argument")
|
|
||||||
try:
|
|
||||||
fixup = int(imm1)
|
|
||||||
except ValueError:
|
|
||||||
fail(".fixup argument must be a nonzero integer")
|
|
||||||
if fixup == 0:
|
|
||||||
fail(".fixup argument must be a nonzero integer")
|
|
||||||
if imacro.initdepth != 0:
|
|
||||||
fail("more than one .fixup in .imacro")
|
|
||||||
imacro.initdepth = fixup
|
|
||||||
|
|
||||||
elif opname == '.end':
|
|
||||||
if imacro is None:
|
|
||||||
if igroup is None:
|
|
||||||
fail(".end without prior .igroup or .imacro")
|
|
||||||
if imm1 is not None and (imm1 != igroup.name or imm2 is not None):
|
|
||||||
fail(".igroup/.end name mismatch")
|
|
||||||
|
|
||||||
maxdepth = 0
|
|
||||||
|
|
||||||
write("static struct {\n")
|
|
||||||
for imacro in igroup.imacros:
|
|
||||||
write(" jsbytecode %s[%d];\n" % (imacro.name, imacro.offset))
|
|
||||||
write("} %s_imacros = {\n" % igroup.name)
|
|
||||||
|
|
||||||
for imacro in igroup.imacros:
|
|
||||||
depth = 0
|
|
||||||
write(" {\n")
|
|
||||||
for op in imacro.code:
|
|
||||||
operand = ""
|
|
||||||
if op.imm1 is not None:
|
|
||||||
operand = ", " + immediate(op)
|
|
||||||
write("/*%2d*/ %s%s,\n" % (op.offset, op.info.jsop, operand))
|
|
||||||
|
|
||||||
imacro.maxdepth = imacro.initdepth
|
|
||||||
simulate_cfg(igroup, imacro, imacro.initdepth, 0)
|
|
||||||
if imacro.maxdepth > maxdepth:
|
|
||||||
maxdepth = imacro.maxdepth
|
|
||||||
|
|
||||||
write(" },\n")
|
|
||||||
write("};\n")
|
|
||||||
|
|
||||||
for opcode in igroup.ops:
|
|
||||||
opcode2extra[opcode] = maxdepth
|
|
||||||
igroups.append(igroup)
|
|
||||||
igroup = None
|
|
||||||
else:
|
|
||||||
assert igroup is not None
|
|
||||||
|
|
||||||
if imm1 is not None and imm1 != imacro.name:
|
|
||||||
fail(".imacro/.end name mismatch")
|
|
||||||
|
|
||||||
# Backpatch the forward references to labels that must now be defined.
|
|
||||||
for label in imacro.labelrefs:
|
|
||||||
if label not in imacro.labeldefs:
|
|
||||||
fail("label " + label + " used but not defined")
|
|
||||||
link = imacro.labelrefs[label]
|
|
||||||
assert link >= 0
|
|
||||||
while True:
|
|
||||||
op = imacro.code[link]
|
|
||||||
next = op.target
|
|
||||||
op.target = imacro.labeldefs[label] - op.offset
|
|
||||||
op.target_index = imacro.labeldef_indexes[label]
|
|
||||||
if next < 0:
|
|
||||||
break
|
|
||||||
link = next
|
|
||||||
|
|
||||||
igroup.imacros.append(imacro)
|
|
||||||
imacro = None
|
|
||||||
|
|
||||||
else:
|
|
||||||
fail("unknown pseudo-op " + opname)
|
|
||||||
continue
|
|
||||||
|
|
||||||
if opname not in opname2info:
|
|
||||||
fail("unknown opcode " + opname)
|
|
||||||
|
|
||||||
info = opname2info[opname]
|
|
||||||
if info.oplen == -1:
|
|
||||||
fail("unimplemented opcode " + opname)
|
|
||||||
|
|
||||||
if imacro is None:
|
|
||||||
fail("opcode %s outside of .imacro", opname)
|
|
||||||
|
|
||||||
# Blacklist ops that may or must use an atomized double immediate.
|
|
||||||
if info.opname in ('double', 'lookupswitch', 'lookupswitchx'):
|
|
||||||
fail(op.opname + " opcode not yet supported")
|
|
||||||
|
|
||||||
if label:
|
|
||||||
imacro.labeldefs[label] = imacro.offset
|
|
||||||
imacro.labeldef_indexes[label] = len(imacro.code)
|
|
||||||
|
|
||||||
op = Instruction(imacro.offset, info, imm1, imm2, lineno + 1)
|
|
||||||
if 'JOF_JUMP' in info.flags:
|
|
||||||
if imm1 in imacro.labeldefs:
|
|
||||||
# Backward reference can be resolved right away, no backpatching needed.
|
|
||||||
op.target = imacro.labeldefs[imm1] - op.offset
|
|
||||||
op.target_index = imacro.labeldef_indexes[imm1]
|
|
||||||
else:
|
|
||||||
# Link op into the .target-linked backpatch chain at labelrefs[imm1].
|
|
||||||
# The linked list terminates with a -1 sentinel.
|
|
||||||
if imm1 in imacro.labelrefs:
|
|
||||||
op.target = imacro.labelrefs[imm1]
|
|
||||||
else:
|
|
||||||
op.target = -1
|
|
||||||
imacro.labelrefs[imm1] = len(imacro.code)
|
|
||||||
|
|
||||||
imacro.code.append(op)
|
|
||||||
imacro.offset += info.oplen
|
|
||||||
|
|
||||||
write("uint8 js_opcode2extra[JSOP_LIMIT] = {\n")
|
|
||||||
for i in range(len(opinfo)):
|
|
||||||
write(" %d, /* %s */\n" % (opcode2extra.get(i, 0), opinfo[i].jsop))
|
|
||||||
write("};\n")
|
|
||||||
|
|
||||||
write("#define JSOP_IS_IMACOP(x) (0 \\\n")
|
|
||||||
for i in sorted(opcode2extra):
|
|
||||||
write(" || x == %s \\\n" % opinfo[i].jsop)
|
|
||||||
write(")\n")
|
|
||||||
|
|
||||||
write("jsbytecode*\njs_GetImacroStart(jsbytecode* pc) {\n")
|
|
||||||
for g in igroups:
|
|
||||||
for m in g.imacros:
|
|
||||||
start = g.name + "_imacros." + m.name
|
|
||||||
write(" if (size_t(pc - %s) < %d) return %s;\n" % (start, m.offset, start))
|
|
||||||
|
|
||||||
write(" return NULL;\n")
|
|
||||||
write("}\n")
|
|
||||||
|
|
||||||
if __name__ == '__main__':
|
|
||||||
import sys
|
|
||||||
if len(sys.argv) != 3:
|
|
||||||
print "usage: python imacro_asm.py infile.jsasm outfile.c.out"
|
|
||||||
sys.exit(1)
|
|
||||||
|
|
||||||
f = open(sys.argv[2], 'w')
|
|
||||||
try:
|
|
||||||
assemble(sys.argv[1], f)
|
|
||||||
finally:
|
|
||||||
f.close()
|
|
||||||
|
|
@ -1,697 +0,0 @@
|
|||||||
# -*- indent-tabs-mode: nil; -*-
|
|
||||||
# vim: set sw=4 ts=8 et tw=78 ft=asm:
|
|
||||||
# ***** BEGIN LICENSE BLOCK *****
|
|
||||||
# Version: MPL 1.1/GPL 2.0/LGPL 2.1
|
|
||||||
#
|
|
||||||
# The contents of this file are subject to the Mozilla Public License Version
|
|
||||||
# 1.1 (the "License"); you may not use this file except in compliance with
|
|
||||||
# the License. You may obtain a copy of the License at
|
|
||||||
# http://www.mozilla.org/MPL/
|
|
||||||
#
|
|
||||||
# Software distributed under the License is distributed on an "AS IS" basis,
|
|
||||||
# WITHOUT WARRANTY OF ANY KIND, either express or implied. See the License
|
|
||||||
# for the specific language governing rights and limitations under the
|
|
||||||
# License.
|
|
||||||
#
|
|
||||||
# The Original Code is the TraceMonkey IMacro Assembler.
|
|
||||||
#
|
|
||||||
# The Initial Developer of the Original Code is
|
|
||||||
# Brendan Eich <brendan@mozilla.org>.
|
|
||||||
# Portions created by the Initial Developer are Copyright (C) 2008
|
|
||||||
# the Initial Developer. All Rights Reserved.
|
|
||||||
#
|
|
||||||
# Contributor(s):
|
|
||||||
#
|
|
||||||
# Alternatively, the contents of this file may be used under the terms of
|
|
||||||
# either the GNU General Public License Version 2 or later (the "GPL"), or
|
|
||||||
# the GNU Lesser General Public License Version 2.1 or later (the "LGPL"),
|
|
||||||
# in which case the provisions of the GPL or the LGPL are applicable instead
|
|
||||||
# of those above. If you wish to allow use of your version of this file only
|
|
||||||
# under the terms of either the GPL or the LGPL, and not to allow others to
|
|
||||||
# use your version of this file under the terms of the MPL, indicate your
|
|
||||||
# decision by deleting the provisions above and replace them with the notice
|
|
||||||
# and other provisions required by the GPL or the LGPL. If you do not delete
|
|
||||||
# the provisions above, a recipient may use your version of this file under
|
|
||||||
# the terms of any one of the MPL, the GPL or the LGPL.
|
|
||||||
#
|
|
||||||
# ***** END LICENSE BLOCK *****
|
|
||||||
|
|
||||||
.igroup equality JSOP_EQ-JSOP_NE
|
|
||||||
|
|
||||||
.imacro any_obj # any obj
|
|
||||||
dup # any obj obj
|
|
||||||
dup # any obj obj obj
|
|
||||||
getprop valueOf # any obj obj valueOf
|
|
||||||
ifcantcalltop 1 # any obj obj valueOf
|
|
||||||
swap # any obj valueOf obj
|
|
||||||
call 0 # any obj rval
|
|
||||||
ifcantcalltop 3 # any obj rval
|
|
||||||
pop # any obj
|
|
||||||
dup # any obj obj
|
|
||||||
goto 2
|
|
||||||
1: pop # any obj obj
|
|
||||||
2: callprop toString # any obj toString obj
|
|
||||||
call 0 # any obj rval
|
|
||||||
primtop (JSTYPE_NUMBER) # any obj rval
|
|
||||||
3: swap # any rval obj
|
|
||||||
pop # any rval
|
|
||||||
imacop # eqval
|
|
||||||
stop
|
|
||||||
.end
|
|
||||||
|
|
||||||
.imacro obj_any # obj any
|
|
||||||
swap # any obj
|
|
||||||
dup # any obj obj
|
|
||||||
dup # any obj obj obj
|
|
||||||
getprop valueOf # any obj obj valueOf
|
|
||||||
ifcantcalltop 1 # any obj obj valueOf
|
|
||||||
swap # any obj valueOf obj
|
|
||||||
call 0 # any obj lval
|
|
||||||
ifcantcalltop 3 # any obj lval
|
|
||||||
pop # any obj
|
|
||||||
dup # any obj obj
|
|
||||||
goto 2
|
|
||||||
1: pop # any obj obj
|
|
||||||
2: callprop toString # any obj toString obj
|
|
||||||
call 0 # any obj lval
|
|
||||||
primtop (JSTYPE_NUMBER) # any obj rval
|
|
||||||
3: swap # any lval obj
|
|
||||||
pop # any lval
|
|
||||||
swap # lval any
|
|
||||||
imacop # eqval
|
|
||||||
stop
|
|
||||||
.end
|
|
||||||
|
|
||||||
.end equality
|
|
||||||
|
|
||||||
# A single range, split up like so to test groups over multiple ranges of ops
|
|
||||||
.igroup binary JSOP_BITOR-JSOP_BITAND,JSOP_EQ-JSOP_DIV,JSOP_MOD
|
|
||||||
|
|
||||||
.imacro any_obj # any obj
|
|
||||||
dup # any obj obj
|
|
||||||
dup # any obj obj obj
|
|
||||||
getprop valueOf # any obj obj valueOf
|
|
||||||
ifcantcalltop 1 # any obj obj valueOf
|
|
||||||
swap # any obj valueOf obj
|
|
||||||
call 0 # any obj rval
|
|
||||||
ifcantcalltop 3 # any obj rval
|
|
||||||
pop # any obj
|
|
||||||
dup # any obj obj
|
|
||||||
goto 2
|
|
||||||
1: pop # any obj obj
|
|
||||||
2: callprop toString # any obj toString obj
|
|
||||||
call 0 # any obj rval
|
|
||||||
primtop (JSTYPE_NUMBER) # any obj rval
|
|
||||||
3: swap # any rval obj
|
|
||||||
pop # any rval
|
|
||||||
imacop # bval
|
|
||||||
stop
|
|
||||||
.end
|
|
||||||
|
|
||||||
.imacro obj_any # obj any
|
|
||||||
swap # any obj
|
|
||||||
dup # any obj obj
|
|
||||||
dup # any obj obj obj
|
|
||||||
getprop valueOf # any obj obj valueOf
|
|
||||||
ifcantcalltop 1 # any obj obj valueOf
|
|
||||||
swap # any obj valueOf obj
|
|
||||||
call 0 # any obj lval
|
|
||||||
ifcantcalltop 3 # any obj lval
|
|
||||||
pop # any obj
|
|
||||||
dup # any obj obj
|
|
||||||
goto 2
|
|
||||||
1: pop # any obj obj
|
|
||||||
2: callprop toString # any obj toString obj
|
|
||||||
call 0 # any obj lval
|
|
||||||
primtop (JSTYPE_NUMBER) # any obj lval
|
|
||||||
3: swap # any lval obj
|
|
||||||
pop # any lval
|
|
||||||
swap # lval any
|
|
||||||
imacop # bval
|
|
||||||
stop
|
|
||||||
.end
|
|
||||||
|
|
||||||
.imacro obj_obj # obj1 obj2
|
|
||||||
swap # obj2 obj1
|
|
||||||
dup # obj2 obj1 obj1
|
|
||||||
dup # obj2 obj1 obj1 obj1
|
|
||||||
getprop valueOf # obj2 obj1 obj1 valueOf
|
|
||||||
ifcantcalltop 1 # obj2 obj1 obj1 valueOf
|
|
||||||
swap # obj2 obj1 valueOf obj1
|
|
||||||
call 0 # obj2 obj1 lval
|
|
||||||
ifcantcalltop 3 # obj2 obj1 lval
|
|
||||||
pop # obj2 obj1
|
|
||||||
dup # obj2 obj1 obj1
|
|
||||||
goto 2
|
|
||||||
1: pop # obj2 obj1 obj1
|
|
||||||
2: callprop toString # obj2 obj1 toString obj1
|
|
||||||
call 0 # obj2 obj1 lval
|
|
||||||
primtop (JSTYPE_NUMBER) # obj2 obj1 lval
|
|
||||||
3: swap # obj2 lval obj1
|
|
||||||
pop # obj2 lval
|
|
||||||
swap # lval obj2
|
|
||||||
dup # lval obj1 obj1
|
|
||||||
dup # lval obj obj obj
|
|
||||||
getprop valueOf # lval obj obj valueOf
|
|
||||||
ifcantcalltop 4 # lval obj obj valueOf
|
|
||||||
swap # lval obj valueOf obj
|
|
||||||
call 0 # lval obj rval
|
|
||||||
ifcantcalltop 6 # lval obj rval
|
|
||||||
pop # lval obj
|
|
||||||
dup # lval obj obj
|
|
||||||
goto 5
|
|
||||||
4: pop # lval obj obj
|
|
||||||
5: callprop toString # lval obj toString obj
|
|
||||||
call 0 # lval obj rval
|
|
||||||
primtop (JSTYPE_NUMBER) # lval obj rval
|
|
||||||
6: swap # lval rval obj
|
|
||||||
pop # lval rval
|
|
||||||
imacop # bval
|
|
||||||
stop
|
|
||||||
.end
|
|
||||||
|
|
||||||
.end binary
|
|
||||||
|
|
||||||
.igroup add JSOP_ADD
|
|
||||||
|
|
||||||
.imacro any_obj # any obj
|
|
||||||
dup # any obj obj
|
|
||||||
dup # any obj obj obj
|
|
||||||
getprop valueOf # any obj obj valueOf
|
|
||||||
ifcantcalltop 1 # any obj obj valueOf
|
|
||||||
swap # any obj valueOf obj
|
|
||||||
call 0 # any obj rval
|
|
||||||
ifcantcalltop 3 # any obj rval
|
|
||||||
pop # any obj
|
|
||||||
dup # any obj obj
|
|
||||||
goto 2
|
|
||||||
1: pop # any obj obj
|
|
||||||
2: callprop toString # any obj toString obj
|
|
||||||
call 0 # any obj rval
|
|
||||||
primtop (JSTYPE_VOID) # any obj rval
|
|
||||||
3: swap # any rval obj
|
|
||||||
pop # any rval
|
|
||||||
add # aval
|
|
||||||
stop
|
|
||||||
.end
|
|
||||||
|
|
||||||
.imacro obj_any # obj any
|
|
||||||
swap # any obj
|
|
||||||
dup # any obj obj
|
|
||||||
dup # any obj obj obj
|
|
||||||
getprop valueOf # any obj obj valueOf
|
|
||||||
ifcantcalltop 1 # any obj obj valueOf
|
|
||||||
swap # any obj valueOf obj
|
|
||||||
call 0 # any obj lval
|
|
||||||
ifcantcalltop 3 # any obj lval
|
|
||||||
pop # any obj
|
|
||||||
dup # any obj obj
|
|
||||||
goto 2
|
|
||||||
1: pop # any obj obj
|
|
||||||
2: callprop toString # any obj toString obj
|
|
||||||
call 0 # any obj lval
|
|
||||||
primtop (JSTYPE_VOID) # any obj lval
|
|
||||||
3: swap # any lval obj
|
|
||||||
pop # any lval
|
|
||||||
swap # lval any
|
|
||||||
add # aval
|
|
||||||
stop
|
|
||||||
.end
|
|
||||||
|
|
||||||
.imacro obj_obj # obj1 obj2
|
|
||||||
swap # obj2 obj1
|
|
||||||
dup # obj2 obj1 obj1
|
|
||||||
dup # obj2 obj1 obj1 obj1
|
|
||||||
getprop valueOf # obj2 obj1 obj1 valueOf
|
|
||||||
ifcantcalltop 1 # obj2 obj1 obj1 valueOf
|
|
||||||
swap # obj2 obj1 valueOf obj1
|
|
||||||
call 0 # obj2 obj1 lval
|
|
||||||
ifcantcalltop 3 # obj2 obj1 lval
|
|
||||||
pop # obj2 obj1
|
|
||||||
dup # obj2 obj1 obj1
|
|
||||||
goto 2
|
|
||||||
1: pop # obj2 obj1 obj1
|
|
||||||
2: callprop toString # obj2 obj1 toString obj1
|
|
||||||
call 0 # obj2 obj1 lval
|
|
||||||
primtop (JSTYPE_VOID) # obj2 obj1 lval
|
|
||||||
3: swap # obj2 lval obj1
|
|
||||||
pop # obj2 lval
|
|
||||||
swap # lval obj2
|
|
||||||
dup # lval obj obj
|
|
||||||
dup # lval obj obj obj
|
|
||||||
getprop valueOf # lval obj obj valueOf
|
|
||||||
ifcantcalltop 4 # lval obj obj valueOf
|
|
||||||
swap # lval obj valueOf obj
|
|
||||||
call 0 # lval obj rval
|
|
||||||
ifcantcalltop 6 # lval obj rval
|
|
||||||
pop # lval obj
|
|
||||||
dup # lval obj obj
|
|
||||||
goto 5
|
|
||||||
4: pop # lval obj obj
|
|
||||||
5: callprop toString # lval obj toString obj
|
|
||||||
call 0 # lval obj rval
|
|
||||||
primtop (JSTYPE_VOID) # lval obj rval
|
|
||||||
6: swap # lval rval obj
|
|
||||||
pop # lval rval
|
|
||||||
add # aval
|
|
||||||
stop
|
|
||||||
.end
|
|
||||||
|
|
||||||
.end add
|
|
||||||
|
|
||||||
.igroup unary JSOP_NEG-JSOP_POS
|
|
||||||
|
|
||||||
.imacro sign # obj
|
|
||||||
dup # obj obj
|
|
||||||
dup # obj obj obj
|
|
||||||
getprop valueOf # obj obj valueOf
|
|
||||||
ifcantcalltop 2 # obj obj valueOf
|
|
||||||
swap # obj valueOf obj
|
|
||||||
call 0 # obj lval
|
|
||||||
ifcantcalltop 1 # obj lval
|
|
||||||
pop # obj
|
|
||||||
dup # obj obj
|
|
||||||
goto 3
|
|
||||||
1: swap # lval obj
|
|
||||||
pop # lval
|
|
||||||
goto 4
|
|
||||||
2: pop # obj obj
|
|
||||||
3: callprop toString # obj toString obj
|
|
||||||
call 0 # obj lval
|
|
||||||
primtop (JSTYPE_NUMBER) # obj lval
|
|
||||||
swap # lval obj
|
|
||||||
pop # lval
|
|
||||||
4: imacop # aval
|
|
||||||
stop
|
|
||||||
.end
|
|
||||||
|
|
||||||
.end unary
|
|
||||||
|
|
||||||
.igroup incelem JSOP_INCELEM,JSOP_ELEMINC
|
|
||||||
.imacro incelem # obj id
|
|
||||||
dup2 # obj id obj id
|
|
||||||
getelem # obj id val
|
|
||||||
pos # obj id n
|
|
||||||
one # obj id n 1
|
|
||||||
add # obj id m
|
|
||||||
setelem # m
|
|
||||||
stop
|
|
||||||
.end
|
|
||||||
|
|
||||||
.imacro eleminc # obj id
|
|
||||||
dup2 # obj id obj id
|
|
||||||
getelem # obj id val
|
|
||||||
pos # obj id n
|
|
||||||
dup # obj id n n
|
|
||||||
one # obj id n n 1
|
|
||||||
add # obj id n m
|
|
||||||
pick 3 # id n m obj
|
|
||||||
pick 3 # n m obj id
|
|
||||||
pick 2 # n obj id m
|
|
||||||
setelem # n m
|
|
||||||
pop # n
|
|
||||||
stop
|
|
||||||
.end
|
|
||||||
.end incelem
|
|
||||||
|
|
||||||
.igroup decelem JSOP_DECELEM,JSOP_ELEMDEC
|
|
||||||
.imacro decelem # obj id
|
|
||||||
dup2 # obj id obj id
|
|
||||||
getelem # obj id val
|
|
||||||
pos # obj id n
|
|
||||||
one # obj id n 1
|
|
||||||
sub # obj id m
|
|
||||||
setelem # m
|
|
||||||
stop
|
|
||||||
.end
|
|
||||||
|
|
||||||
.imacro elemdec # obj id
|
|
||||||
dup2 # obj id obj id
|
|
||||||
getelem # obj id val
|
|
||||||
pos # obj id n
|
|
||||||
dup # obj id n n
|
|
||||||
one # obj id n n 1
|
|
||||||
sub # obj id n m
|
|
||||||
pick 3 # id n m obj
|
|
||||||
pick 3 # n m obj id
|
|
||||||
pick 2 # n obj id m
|
|
||||||
setelem # n m
|
|
||||||
pop # n
|
|
||||||
stop
|
|
||||||
.end
|
|
||||||
.end decelem
|
|
||||||
|
|
||||||
.igroup call JSOP_CALL
|
|
||||||
|
|
||||||
.imacro String # String this obj
|
|
||||||
dup # String this obj obj
|
|
||||||
dup # String this obj obj obj
|
|
||||||
getprop toString # String this obj obj toString
|
|
||||||
ifcantcalltop 1 # String this obj obj toString
|
|
||||||
swap # String this obj toString obj
|
|
||||||
call 0 # String this obj rval
|
|
||||||
ifcantcalltop 3 # String this obj rval
|
|
||||||
pop # String this obj
|
|
||||||
dup # String this obj obj
|
|
||||||
goto 2
|
|
||||||
1: pop # String this obj obj
|
|
||||||
2: callprop valueOf # String this obj valueOf obj
|
|
||||||
call 0 # String this obj rval
|
|
||||||
primtop (JSTYPE_STRING) # String this obj rval
|
|
||||||
3: swap # String this rval obj
|
|
||||||
pop # String this rval
|
|
||||||
call 1 # str
|
|
||||||
stop # str
|
|
||||||
.end
|
|
||||||
|
|
||||||
.end call
|
|
||||||
|
|
||||||
.igroup new JSOP_NEW
|
|
||||||
|
|
||||||
.imacro String # String this obj
|
|
||||||
dup # String this obj obj
|
|
||||||
dup # String this obj obj obj
|
|
||||||
getprop toString # String this obj obj toString
|
|
||||||
ifcantcalltop 1 # String this obj obj toString
|
|
||||||
swap # String this obj toString obj
|
|
||||||
call 0 # String this obj rval
|
|
||||||
ifcantcalltop 3 # String this obj rval
|
|
||||||
pop # String this obj
|
|
||||||
dup # String this obj obj
|
|
||||||
goto 2
|
|
||||||
1: pop # String this obj obj
|
|
||||||
2: callprop valueOf # String this obj valueOf obj
|
|
||||||
call 0 # String this obj rval
|
|
||||||
primtop (JSTYPE_STRING) # String this obj rval
|
|
||||||
3: swap # String this rval obj
|
|
||||||
pop # String this rval
|
|
||||||
new 1 # strobj
|
|
||||||
stop # strobj
|
|
||||||
.end
|
|
||||||
|
|
||||||
.end new
|
|
||||||
|
|
||||||
.igroup funapply JSOP_FUNAPPLY
|
|
||||||
|
|
||||||
.imacro apply0 # apply fun this arr
|
|
||||||
pick 3 # fun this arr apply
|
|
||||||
pop # fun this arr
|
|
||||||
pop # fun this
|
|
||||||
call 0 #
|
|
||||||
stop #
|
|
||||||
.end #
|
|
||||||
|
|
||||||
.imacro apply1 # apply fun this arr
|
|
||||||
pick 3 # fun this arr apply
|
|
||||||
pop # fun this arr
|
|
||||||
dup # fun this arr arr
|
|
||||||
zero # fun this arr arr 0
|
|
||||||
getelem # fun this arr arg0
|
|
||||||
swap # fun this arg0 arr
|
|
||||||
pop # fun this arg0
|
|
||||||
call 1 #
|
|
||||||
stop #
|
|
||||||
.end #
|
|
||||||
|
|
||||||
.imacro apply2 # apply fun this arr
|
|
||||||
pick 3 # fun this arr apply
|
|
||||||
pop # fun this arr
|
|
||||||
dup # fun this arr arr
|
|
||||||
zero # fun this arr arr 0
|
|
||||||
getelem # fun this arr arg0
|
|
||||||
swap # fun this arg0 arr
|
|
||||||
dup # fun this arg0 arr arr
|
|
||||||
one # fun this arg0 arr arr 1
|
|
||||||
getelem # fun this arg0 arr arg1
|
|
||||||
swap # fun this arg0 arg1 arr
|
|
||||||
pop # fun this arg0 arg1
|
|
||||||
call 2 #
|
|
||||||
stop #
|
|
||||||
.end #
|
|
||||||
|
|
||||||
.imacro apply3 # apply fun this arr
|
|
||||||
pick 3 # fun this arr apply
|
|
||||||
pop # fun this arr
|
|
||||||
dup # fun this arr arr
|
|
||||||
zero # fun this arr arr 0
|
|
||||||
getelem # fun this arr arg0
|
|
||||||
swap # fun this arg0 arr
|
|
||||||
dup # fun this arg0 arr arr
|
|
||||||
one # fun this arg0 arr arr 1
|
|
||||||
getelem # fun this arg0 arr arg1
|
|
||||||
swap # fun this arg0 arg1 arr
|
|
||||||
dup # fun this arg0 arg1 arr arr
|
|
||||||
int8 2 # fun this arg0 arg1 arr arr 2
|
|
||||||
getelem # fun this arg0 arg1 arr arg2
|
|
||||||
swap # fun this arg0 arg1 arg2 arr
|
|
||||||
pop # fun this arg0 arg1 arg2
|
|
||||||
call 3 #
|
|
||||||
stop #
|
|
||||||
.end #
|
|
||||||
|
|
||||||
.imacro apply4 # apply fun this arr
|
|
||||||
pick 3 # fun this arr apply
|
|
||||||
pop # fun this arr
|
|
||||||
dup # fun this arr arr
|
|
||||||
zero # fun this arr arr 0
|
|
||||||
getelem # fun this arr arg0
|
|
||||||
swap # fun this arg0 arr
|
|
||||||
dup # fun this arg0 arr arr
|
|
||||||
one # fun this arg0 arr arr 1
|
|
||||||
getelem # fun this arg0 arr arg1
|
|
||||||
swap # fun this arg0 arg1 arr
|
|
||||||
dup # fun this arg0 arg1 arr arr
|
|
||||||
int8 2 # fun this arg0 arg1 arr arr 2
|
|
||||||
getelem # fun this arg0 arg1 arr arg2
|
|
||||||
swap # fun this arg0 arg1 arg2 arr
|
|
||||||
dup # fun this arg0 arg1 arg2 arr arr
|
|
||||||
int8 3 # fun this arg0 arg1 arg2 arr arr 3
|
|
||||||
getelem # fun this arg0 arg1 arg2 arr arg3
|
|
||||||
swap # fun this arg0 arg1 arg2 arg3 arr
|
|
||||||
pop # fun this arg0 arg1 arg2 arg3
|
|
||||||
call 4 #
|
|
||||||
stop #
|
|
||||||
.end #
|
|
||||||
|
|
||||||
.imacro apply5 # apply fun this arr
|
|
||||||
pick 3 # fun this arr apply
|
|
||||||
pop # fun this arr
|
|
||||||
dup # fun this arr arr
|
|
||||||
zero # fun this arr arr 0
|
|
||||||
getelem # fun this arr arg0
|
|
||||||
swap # fun this arg0 arr
|
|
||||||
dup # fun this arg0 arr arr
|
|
||||||
one # fun this arg0 arr arr 1
|
|
||||||
getelem # fun this arg0 arr arg1
|
|
||||||
swap # fun this arg0 arg1 arr
|
|
||||||
dup # fun this arg0 arg1 arr arr
|
|
||||||
int8 2 # fun this arg0 arg1 arr arr 2
|
|
||||||
getelem # fun this arg0 arg1 arr arg2
|
|
||||||
swap # fun this arg0 arg1 arg2 arr
|
|
||||||
dup # fun this arg0 arg1 arg2 arr arr
|
|
||||||
int8 3 # fun this arg0 arg1 arg2 arr arr 3
|
|
||||||
getelem # fun this arg0 arg1 arg2 arr arg3
|
|
||||||
swap # fun this arg0 arg1 arg2 arg3 arr
|
|
||||||
dup # fun this arg0 arg1 arg2 arg3 arr arr
|
|
||||||
int8 4 # fun this arg0 arg1 arg2 arg3 arr arr 4
|
|
||||||
getelem # fun this arg0 arg1 arg2 arg3 arr arg4
|
|
||||||
swap # fun this arg0 arg1 arg2 arg3 arg4 arr
|
|
||||||
pop # fun this arg0 arg1 arg2 arg3 arg4
|
|
||||||
call 5 #
|
|
||||||
stop #
|
|
||||||
.end #
|
|
||||||
|
|
||||||
.imacro apply6 # apply fun this arr
|
|
||||||
pick 3 # fun this arr apply
|
|
||||||
pop # fun this arr
|
|
||||||
dup # fun this arr arr
|
|
||||||
zero # fun this arr arr 0
|
|
||||||
getelem # fun this arr arg0
|
|
||||||
swap # fun this arg0 arr
|
|
||||||
dup # fun this arg0 arr arr
|
|
||||||
one # fun this arg0 arr arr 1
|
|
||||||
getelem # fun this arg0 arr arg1
|
|
||||||
swap # fun this arg0 arg1 arr
|
|
||||||
dup # fun this arg0 arg1 arr arr
|
|
||||||
int8 2 # fun this arg0 arg1 arr arr 2
|
|
||||||
getelem # fun this arg0 arg1 arr arg2
|
|
||||||
swap # fun this arg0 arg1 arg2 arr
|
|
||||||
dup # fun this arg0 arg1 arg2 arr arr
|
|
||||||
int8 3 # fun this arg0 arg1 arg2 arr arr 3
|
|
||||||
getelem # fun this arg0 arg1 arg2 arr arg3
|
|
||||||
swap # fun this arg0 arg1 arg2 arg3 arr
|
|
||||||
dup # fun this arg0 arg1 arg2 arg3 arr arr
|
|
||||||
int8 4 # fun this arg0 arg1 arg2 arg3 arr arr 4
|
|
||||||
getelem # fun this arg0 arg1 arg2 arg3 arr arg4
|
|
||||||
swap # fun this arg0 arg1 arg2 arg3 arg4 arr
|
|
||||||
dup # fun this arg0 arg1 arg2 arg3 arg4 arr arr
|
|
||||||
int8 5 # fun this arg0 arg1 arg2 arg3 arg4 arr arr 5
|
|
||||||
getelem # fun this arg0 arg1 arg2 arg3 arg4 arr arg5
|
|
||||||
swap # fun this arg0 arg1 arg2 arg3 arg4 arg5 arr
|
|
||||||
pop # fun this arg0 arg1 arg2 arg3 arg4 arg5
|
|
||||||
call 6 #
|
|
||||||
stop #
|
|
||||||
.end #
|
|
||||||
|
|
||||||
.imacro apply7 # apply fun this arr
|
|
||||||
pick 3 # fun this arr apply
|
|
||||||
pop # fun this arr
|
|
||||||
dup # fun this arr arr
|
|
||||||
zero # fun this arr arr 0
|
|
||||||
getelem # fun this arr arg0
|
|
||||||
swap # fun this arg0 arr
|
|
||||||
dup # fun this arg0 arr arr
|
|
||||||
one # fun this arg0 arr arr 1
|
|
||||||
getelem # fun this arg0 arr arg1
|
|
||||||
swap # fun this arg0 arg1 arr
|
|
||||||
dup # fun this arg0 arg1 arr arr
|
|
||||||
int8 2 # fun this arg0 arg1 arr arr 2
|
|
||||||
getelem # fun this arg0 arg1 arr arg2
|
|
||||||
swap # fun this arg0 arg1 arg2 arr
|
|
||||||
dup # fun this arg0 arg1 arg2 arr arr
|
|
||||||
int8 3 # fun this arg0 arg1 arg2 arr arr 3
|
|
||||||
getelem # fun this arg0 arg1 arg2 arr arg3
|
|
||||||
swap # fun this arg0 arg1 arg2 arg3 arr
|
|
||||||
dup # fun this arg0 arg1 arg2 arg3 arr arr
|
|
||||||
int8 4 # fun this arg0 arg1 arg2 arg3 arr arr 4
|
|
||||||
getelem # fun this arg0 arg1 arg2 arg3 arr arg4
|
|
||||||
swap # fun this arg0 arg1 arg2 arg3 arg4 arr
|
|
||||||
dup # fun this arg0 arg1 arg2 arg3 arg4 arr arr
|
|
||||||
int8 5 # fun this arg0 arg1 arg2 arg3 arg4 arr arr 5
|
|
||||||
getelem # fun this arg0 arg1 arg2 arg3 arg4 arr arg5
|
|
||||||
swap # fun this arg0 arg1 arg2 arg3 arg4 arg5 arr
|
|
||||||
dup # fun this arg0 arg1 arg2 arg3 arg4 arg5 arr arr
|
|
||||||
int8 6 # fun this arg0 arg1 arg2 arg3 arg4 arg5 arr arr 6
|
|
||||||
getelem # fun this arg0 arg1 arg2 arg3 arg4 arg5 arr arg6
|
|
||||||
swap # fun this arg0 arg1 arg2 arg3 arg4 arg5 arg6 arr
|
|
||||||
pop # fun this arg0 arg1 arg2 arg3 arg4 arg5 arg6
|
|
||||||
call 7 #
|
|
||||||
stop #
|
|
||||||
.end #
|
|
||||||
|
|
||||||
.imacro apply8 # apply fun this arr
|
|
||||||
pick 3 # fun this arr apply
|
|
||||||
pop # fun this arr
|
|
||||||
dup # fun this arr arr
|
|
||||||
zero # fun this arr arr 0
|
|
||||||
getelem # fun this arr arg0
|
|
||||||
swap # fun this arg0 arr
|
|
||||||
dup # fun this arg0 arr arr
|
|
||||||
one # fun this arg0 arr arr 1
|
|
||||||
getelem # fun this arg0 arr arg1
|
|
||||||
swap # fun this arg0 arg1 arr
|
|
||||||
dup # fun this arg0 arg1 arr arr
|
|
||||||
int8 2 # fun this arg0 arg1 arr arr 2
|
|
||||||
getelem # fun this arg0 arg1 arr arg2
|
|
||||||
swap # fun this arg0 arg1 arg2 arr
|
|
||||||
dup # fun this arg0 arg1 arg2 arr arr
|
|
||||||
int8 3 # fun this arg0 arg1 arg2 arr arr 3
|
|
||||||
getelem # fun this arg0 arg1 arg2 arr arg3
|
|
||||||
swap # fun this arg0 arg1 arg2 arg3 arr
|
|
||||||
dup # fun this arg0 arg1 arg2 arg3 arr arr
|
|
||||||
int8 4 # fun this arg0 arg1 arg2 arg3 arr arr 4
|
|
||||||
getelem # fun this arg0 arg1 arg2 arg3 arr arg4
|
|
||||||
swap # fun this arg0 arg1 arg2 arg3 arg4 arr
|
|
||||||
dup # fun this arg0 arg1 arg2 arg3 arg4 arr arr
|
|
||||||
int8 5 # fun this arg0 arg1 arg2 arg3 arg4 arr arr 5
|
|
||||||
getelem # fun this arg0 arg1 arg2 arg3 arg4 arr arg5
|
|
||||||
swap # fun this arg0 arg1 arg2 arg3 arg4 arg5 arr
|
|
||||||
dup # fun this arg0 arg1 arg2 arg3 arg4 arg5 arr arr
|
|
||||||
int8 6 # fun this arg0 arg1 arg2 arg3 arg4 arg5 arr arr 6
|
|
||||||
getelem # fun this arg0 arg1 arg2 arg3 arg4 arg5 arr arg6
|
|
||||||
swap # fun this arg0 arg1 arg2 arg3 arg4 arg5 arg6 arr
|
|
||||||
dup # fun this arg0 arg1 arg2 arg3 arg4 arg5 arg6 arr arr
|
|
||||||
int8 7 # fun this arg0 arg1 arg2 arg3 arg4 arg5 arg6 arr arr 7
|
|
||||||
getelem # fun this arg0 arg1 arg2 arg3 arg4 arg5 arg6 arr arg7
|
|
||||||
swap # fun this arg0 arg1 arg2 arg3 arg4 arg5 arg6 arg7 arr
|
|
||||||
pop # fun this arg0 arg1 arg2 arg3 arg4 arg5 arg6 arg7
|
|
||||||
call 8 #
|
|
||||||
stop #
|
|
||||||
.end #
|
|
||||||
|
|
||||||
.end funapply
|
|
||||||
|
|
||||||
.igroup funcall JSOP_FUNCALL
|
|
||||||
|
|
||||||
.imacro call0 # call fun
|
|
||||||
swap # fun call
|
|
||||||
pop # fun
|
|
||||||
null # fun this
|
|
||||||
call 0 #
|
|
||||||
stop #
|
|
||||||
.end #
|
|
||||||
|
|
||||||
.imacro call1 # call fun this
|
|
||||||
pick 2 # fun this call
|
|
||||||
pop # fun this
|
|
||||||
call 0 #
|
|
||||||
stop #
|
|
||||||
.end #
|
|
||||||
|
|
||||||
.imacro call2 # call fun this arg0
|
|
||||||
pick 3 # fun this arg0 call
|
|
||||||
pop # fun this arg0
|
|
||||||
call 1 #
|
|
||||||
stop #
|
|
||||||
.end #
|
|
||||||
|
|
||||||
.imacro call3 # call fun this arg0 arg1
|
|
||||||
pick 4 # fun this arg0 arg1 call
|
|
||||||
pop # fun this arg0 arg1
|
|
||||||
call 2 #
|
|
||||||
stop #
|
|
||||||
.end #
|
|
||||||
|
|
||||||
.imacro call4 # call fun this arg0 arg1 arg2
|
|
||||||
pick 5 # fun this arg0 arg1 arg2 call
|
|
||||||
pop # fun this arg0 arg1 arg2
|
|
||||||
call 3 #
|
|
||||||
stop #
|
|
||||||
.end #
|
|
||||||
|
|
||||||
.imacro call5 # call fun this arg0 arg1 arg2 arg3
|
|
||||||
pick 6 # fun this arg0 arg1 arg2 arg3 call
|
|
||||||
pop # fun this arg0 arg1 arg2 arg3
|
|
||||||
call 4 #
|
|
||||||
stop #
|
|
||||||
.end #
|
|
||||||
|
|
||||||
.imacro call6 # call fun this arg0 arg1 arg2 arg3 arg4
|
|
||||||
pick 7 # fun this arg0 arg1 arg2 arg3 arg4 call
|
|
||||||
pop # fun this arg0 arg1 arg2 arg3 arg4
|
|
||||||
call 5 #
|
|
||||||
stop #
|
|
||||||
.end #
|
|
||||||
|
|
||||||
.imacro call7 # call fun this arg0 arg1 arg2 arg3 arg4 arg5
|
|
||||||
pick 8 # fun this arg0 arg1 arg2 arg3 arg4 arg5 call
|
|
||||||
pop # fun this arg0 arg1 arg2 arg3 arg4 arg5
|
|
||||||
call 6 #
|
|
||||||
stop #
|
|
||||||
.end #
|
|
||||||
|
|
||||||
.imacro call8 # call fun this arg0 arg1 arg2 arg3 arg4 arg5 arg6
|
|
||||||
pick 9 # fun this arg0 arg1 arg2 arg3 arg4 arg5 arg6 call
|
|
||||||
pop # fun this arg0 arg1 arg2 arg3 arg4 arg5 arg6
|
|
||||||
call 7 #
|
|
||||||
stop #
|
|
||||||
.end #
|
|
||||||
|
|
||||||
.end funcall
|
|
||||||
|
|
||||||
.igroup getprop JSOP_GETPROP
|
|
||||||
.imacro scriptgetter # obj
|
|
||||||
.fixup +1 # getter obj
|
|
||||||
call 0 # val
|
|
||||||
stop
|
|
||||||
.end
|
|
||||||
.end getprop
|
|
||||||
|
|
||||||
.igroup callprop JSOP_CALLPROP
|
|
||||||
.imacro scriptgetter # obj
|
|
||||||
.fixup +2 # obj getter obj
|
|
||||||
call 0 # obj method
|
|
||||||
swap # method obj
|
|
||||||
stop
|
|
||||||
.end
|
|
||||||
.end callprop
|
|
@ -356,7 +356,7 @@ def parse_jitflags():
|
|||||||
for flags in OPTIONS.jitflags.split(',') ]
|
for flags in OPTIONS.jitflags.split(',') ]
|
||||||
for flags in jitflags:
|
for flags in jitflags:
|
||||||
for flag in flags:
|
for flag in flags:
|
||||||
if flag not in ('-j', '-m', '-a', '-p', '-d', '-n'):
|
if flag not in ('-m', '-a', '-p', '-d', '-n'):
|
||||||
print('Invalid jit flag: "%s"'%flag)
|
print('Invalid jit flag: "%s"'%flag)
|
||||||
sys.exit(1)
|
sys.exit(1)
|
||||||
return jitflags
|
return jitflags
|
||||||
@ -420,8 +420,8 @@ def main(argv):
|
|||||||
help='Enable the |valgrind| flag, if valgrind is in $PATH.')
|
help='Enable the |valgrind| flag, if valgrind is in $PATH.')
|
||||||
op.add_option('--valgrind-all', dest='valgrind_all', action='store_true',
|
op.add_option('--valgrind-all', dest='valgrind_all', action='store_true',
|
||||||
help='Run all tests with valgrind, if valgrind is in $PATH.')
|
help='Run all tests with valgrind, if valgrind is in $PATH.')
|
||||||
op.add_option('--jitflags', dest='jitflags', default='mjp',
|
op.add_option('--jitflags', dest='jitflags', default='m,mn',
|
||||||
help='Example: --jitflags=j,mj,mjp to run each test with -j, -m -j, -m -j -p [default=%default]')
|
help='Example: --jitflags=m,mn to run each test with -m, -m -n [default=%default]')
|
||||||
op.add_option('--avoid-stdio', dest='avoid_stdio', action='store_true',
|
op.add_option('--avoid-stdio', dest='avoid_stdio', action='store_true',
|
||||||
help='Use js-shell file indirection instead of piping stdio.')
|
help='Use js-shell file indirection instead of piping stdio.')
|
||||||
op.add_option('--write-failure-output', dest='write_failure_output', action='store_true',
|
op.add_option('--write-failure-output', dest='write_failure_output', action='store_true',
|
||||||
|
@ -91,9 +91,8 @@
|
|||||||
#undef JS_INTPTR_TYPE
|
#undef JS_INTPTR_TYPE
|
||||||
#undef JS_BYTES_PER_WORD
|
#undef JS_BYTES_PER_WORD
|
||||||
|
|
||||||
/* Some mozilla code uses JS-friend APIs that depend on JS_TRACER and
|
/* Some mozilla code uses JS-friend APIs that depend on JS_METHODJIT being
|
||||||
JS_METHODJIT being correct. */
|
correct. */
|
||||||
#undef JS_TRACER
|
|
||||||
#undef JS_METHODJIT
|
#undef JS_METHODJIT
|
||||||
|
|
||||||
#endif /* js_config_h___ */
|
#endif /* js_config_h___ */
|
||||||
|
@ -2,8 +2,6 @@
|
|||||||
#include "jsfun.h"
|
#include "jsfun.h"
|
||||||
#include "jscntxt.h"
|
#include "jscntxt.h"
|
||||||
|
|
||||||
// For TRACING_ENABLED
|
|
||||||
#include "jstracer.h"
|
|
||||||
#include "jsobjinlines.h"
|
#include "jsobjinlines.h"
|
||||||
|
|
||||||
#ifdef MOZ_TRACE_JSCALLS
|
#ifdef MOZ_TRACE_JSCALLS
|
||||||
@ -103,15 +101,6 @@ BEGIN_TEST(testFuncCallback_bug507012)
|
|||||||
CHECK_EQUAL(leaves, 1+50);
|
CHECK_EQUAL(leaves, 1+50);
|
||||||
CHECK_EQUAL(depth, 0);
|
CHECK_EQUAL(depth, 0);
|
||||||
|
|
||||||
// If this fails, it means that the code was interpreted rather
|
|
||||||
// than trace-JITted, and so is not testing what it's supposed to
|
|
||||||
// be testing. Which doesn't necessarily imply that the
|
|
||||||
// functionality is broken.
|
|
||||||
#ifdef JS_TRACER
|
|
||||||
if (TRACING_ENABLED(cx))
|
|
||||||
CHECK(interpreted < enters);
|
|
||||||
#endif
|
|
||||||
|
|
||||||
// Test nesting callbacks via JS_GetFunctionCallback()
|
// Test nesting callbacks via JS_GetFunctionCallback()
|
||||||
JS_SetFunctionCallback(cx, funcTransition);
|
JS_SetFunctionCallback(cx, funcTransition);
|
||||||
innerCallback = JS_GetFunctionCallback(cx);
|
innerCallback = JS_GetFunctionCallback(cx);
|
||||||
|
@ -56,7 +56,6 @@
|
|||||||
#include "jsarray.h"
|
#include "jsarray.h"
|
||||||
#include "jsatom.h"
|
#include "jsatom.h"
|
||||||
#include "jsbool.h"
|
#include "jsbool.h"
|
||||||
#include "jsbuiltins.h"
|
|
||||||
#include "jsclone.h"
|
#include "jsclone.h"
|
||||||
#include "jscntxt.h"
|
#include "jscntxt.h"
|
||||||
#include "jsversion.h"
|
#include "jsversion.h"
|
||||||
@ -78,7 +77,6 @@
|
|||||||
#include "jsscope.h"
|
#include "jsscope.h"
|
||||||
#include "jsscript.h"
|
#include "jsscript.h"
|
||||||
#include "jsstr.h"
|
#include "jsstr.h"
|
||||||
#include "jstracer.h"
|
|
||||||
#include "prmjtime.h"
|
#include "prmjtime.h"
|
||||||
#include "jsweakmap.h"
|
#include "jsweakmap.h"
|
||||||
#include "jswrapper.h"
|
#include "jswrapper.h"
|
||||||
@ -657,6 +655,7 @@ JSRuntime::JSRuntime()
|
|||||||
gcMaxBytes(0),
|
gcMaxBytes(0),
|
||||||
gcMaxMallocBytes(0),
|
gcMaxMallocBytes(0),
|
||||||
gcEmptyArenaPoolLifespan(0),
|
gcEmptyArenaPoolLifespan(0),
|
||||||
|
gcNumFreeArenas(0),
|
||||||
gcNumber(0),
|
gcNumber(0),
|
||||||
gcIncrementalTracer(NULL),
|
gcIncrementalTracer(NULL),
|
||||||
gcVerifyData(NULL),
|
gcVerifyData(NULL),
|
||||||
@ -751,10 +750,6 @@ JSRuntime::init(uint32 maxbytes)
|
|||||||
JMCheckLogging();
|
JMCheckLogging();
|
||||||
#endif
|
#endif
|
||||||
|
|
||||||
#ifdef JS_TRACER
|
|
||||||
InitJIT();
|
|
||||||
#endif
|
|
||||||
|
|
||||||
if (!js_InitGC(this, maxbytes))
|
if (!js_InitGC(this, maxbytes))
|
||||||
return false;
|
return false;
|
||||||
|
|
||||||
@ -813,10 +808,6 @@ JSRuntime::~JSRuntime()
|
|||||||
}
|
}
|
||||||
#endif
|
#endif
|
||||||
|
|
||||||
#ifdef JS_TRACER
|
|
||||||
FinishJIT();
|
|
||||||
#endif
|
|
||||||
|
|
||||||
FinishRuntimeNumberState(this);
|
FinishRuntimeNumberState(this);
|
||||||
js_FinishThreads(this);
|
js_FinishThreads(this);
|
||||||
js_FinishAtomState(this);
|
js_FinishAtomState(this);
|
||||||
@ -917,10 +908,6 @@ JS_ShutDown(void)
|
|||||||
{
|
{
|
||||||
Probes::shutdown();
|
Probes::shutdown();
|
||||||
|
|
||||||
#ifdef MOZ_TRACEVIS
|
|
||||||
StopTraceVis();
|
|
||||||
#endif
|
|
||||||
|
|
||||||
#ifdef JS_THREADSAFE
|
#ifdef JS_THREADSAFE
|
||||||
js_CleanupLocks();
|
js_CleanupLocks();
|
||||||
#endif
|
#endif
|
||||||
@ -983,8 +970,6 @@ StopRequest(JSContext *cx)
|
|||||||
if (t->data.requestDepth != 1) {
|
if (t->data.requestDepth != 1) {
|
||||||
t->data.requestDepth--;
|
t->data.requestDepth--;
|
||||||
} else {
|
} else {
|
||||||
LeaveTrace(cx); /* for GC safety */
|
|
||||||
|
|
||||||
t->data.conservativeGC.updateForRequestEnd(t->suspendCount);
|
t->data.conservativeGC.updateForRequestEnd(t->suspendCount);
|
||||||
|
|
||||||
/* Lock before clearing to interlock with ClaimScope, in jslock.c. */
|
/* Lock before clearing to interlock with ClaimScope, in jslock.c. */
|
||||||
@ -2747,8 +2732,6 @@ JS_CompartmentGC(JSContext *cx, JSCompartment *comp)
|
|||||||
/* We cannot GC the atoms compartment alone; use a full GC instead. */
|
/* We cannot GC the atoms compartment alone; use a full GC instead. */
|
||||||
JS_ASSERT(comp != cx->runtime->atomsCompartment);
|
JS_ASSERT(comp != cx->runtime->atomsCompartment);
|
||||||
|
|
||||||
LeaveTrace(cx);
|
|
||||||
|
|
||||||
js::gc::VerifyBarriers(cx, true);
|
js::gc::VerifyBarriers(cx, true);
|
||||||
js_GC(cx, comp, GC_NORMAL, gcstats::PUBLIC_API);
|
js_GC(cx, comp, GC_NORMAL, gcstats::PUBLIC_API);
|
||||||
}
|
}
|
||||||
@ -2762,8 +2745,6 @@ JS_GC(JSContext *cx)
|
|||||||
JS_PUBLIC_API(void)
|
JS_PUBLIC_API(void)
|
||||||
JS_MaybeGC(JSContext *cx)
|
JS_MaybeGC(JSContext *cx)
|
||||||
{
|
{
|
||||||
LeaveTrace(cx);
|
|
||||||
|
|
||||||
MaybeGC(cx);
|
MaybeGC(cx);
|
||||||
}
|
}
|
||||||
|
|
||||||
@ -2842,29 +2823,18 @@ JS_PUBLIC_API(void)
|
|||||||
JS_SetGCParameterForThread(JSContext *cx, JSGCParamKey key, uint32 value)
|
JS_SetGCParameterForThread(JSContext *cx, JSGCParamKey key, uint32 value)
|
||||||
{
|
{
|
||||||
JS_ASSERT(key == JSGC_MAX_CODE_CACHE_BYTES);
|
JS_ASSERT(key == JSGC_MAX_CODE_CACHE_BYTES);
|
||||||
#ifdef JS_TRACER
|
|
||||||
SetMaxCodeCacheBytes(cx, value);
|
|
||||||
#endif
|
|
||||||
}
|
}
|
||||||
|
|
||||||
JS_PUBLIC_API(uint32)
|
JS_PUBLIC_API(uint32)
|
||||||
JS_GetGCParameterForThread(JSContext *cx, JSGCParamKey key)
|
JS_GetGCParameterForThread(JSContext *cx, JSGCParamKey key)
|
||||||
{
|
{
|
||||||
JS_ASSERT(key == JSGC_MAX_CODE_CACHE_BYTES);
|
JS_ASSERT(key == JSGC_MAX_CODE_CACHE_BYTES);
|
||||||
#ifdef JS_TRACER
|
|
||||||
return JS_THREAD_DATA(cx)->maxCodeCacheBytes;
|
|
||||||
#else
|
|
||||||
return 0;
|
return 0;
|
||||||
#endif
|
|
||||||
}
|
}
|
||||||
|
|
||||||
JS_PUBLIC_API(void)
|
JS_PUBLIC_API(void)
|
||||||
JS_FlushCaches(JSContext *cx)
|
JS_FlushCaches(JSContext *cx)
|
||||||
{
|
{
|
||||||
#ifdef JS_TRACER
|
|
||||||
if (cx->compartment->hasTraceMonitor())
|
|
||||||
FlushJITCache(cx, cx->compartment->traceMonitor());
|
|
||||||
#endif
|
|
||||||
}
|
}
|
||||||
|
|
||||||
JS_PUBLIC_API(intN)
|
JS_PUBLIC_API(intN)
|
||||||
@ -4527,14 +4497,7 @@ js_generic_native_method_dispatcher(JSContext *cx, uintN argc, Value *vp)
|
|||||||
/* Clear the last parameter in case too few arguments were passed. */
|
/* Clear the last parameter in case too few arguments were passed. */
|
||||||
vp[2 + --argc].setUndefined();
|
vp[2 + --argc].setUndefined();
|
||||||
|
|
||||||
Native native =
|
return fs->call(cx, argc, vp);
|
||||||
#ifdef JS_TRACER
|
|
||||||
(fs->flags & JSFUN_TRCINFO)
|
|
||||||
? JS_FUNC_TO_DATA_PTR(JSNativeTraceInfo *, fs->call)->native
|
|
||||||
:
|
|
||||||
#endif
|
|
||||||
fs->call;
|
|
||||||
return native(cx, argc, vp);
|
|
||||||
}
|
}
|
||||||
|
|
||||||
JS_PUBLIC_API(JSBool)
|
JS_PUBLIC_API(JSBool)
|
||||||
@ -4570,7 +4533,7 @@ JS_DefineFunctions(JSContext *cx, JSObject *obj, JSFunctionSpec *fs)
|
|||||||
fun = js_DefineFunction(cx, ctor, ATOM_TO_JSID(atom),
|
fun = js_DefineFunction(cx, ctor, ATOM_TO_JSID(atom),
|
||||||
js_generic_native_method_dispatcher,
|
js_generic_native_method_dispatcher,
|
||||||
fs->nargs + 1,
|
fs->nargs + 1,
|
||||||
flags & ~JSFUN_TRCINFO);
|
flags);
|
||||||
if (!fun)
|
if (!fun)
|
||||||
return JS_FALSE;
|
return JS_FALSE;
|
||||||
|
|
||||||
@ -5325,10 +5288,6 @@ JS_IsRunning(JSContext *cx)
|
|||||||
return false;
|
return false;
|
||||||
#endif
|
#endif
|
||||||
|
|
||||||
#ifdef JS_TRACER
|
|
||||||
JS_ASSERT_IF(JS_ON_TRACE(cx) && JS_TRACE_MONITOR_ON_TRACE(cx)->tracecx == cx, cx->hasfp());
|
|
||||||
#endif
|
|
||||||
|
|
||||||
StackFrame *fp = cx->maybefp();
|
StackFrame *fp = cx->maybefp();
|
||||||
while (fp && fp->isDummyFrame())
|
while (fp && fp->isDummyFrame())
|
||||||
fp = fp->prev();
|
fp = fp->prev();
|
||||||
@ -5339,7 +5298,6 @@ JS_PUBLIC_API(JSBool)
|
|||||||
JS_SaveFrameChain(JSContext *cx)
|
JS_SaveFrameChain(JSContext *cx)
|
||||||
{
|
{
|
||||||
CHECK_REQUEST(cx);
|
CHECK_REQUEST(cx);
|
||||||
LeaveTrace(cx);
|
|
||||||
return cx->stack.saveFrameChain();
|
return cx->stack.saveFrameChain();
|
||||||
}
|
}
|
||||||
|
|
||||||
@ -5347,7 +5305,6 @@ JS_PUBLIC_API(void)
|
|||||||
JS_RestoreFrameChain(JSContext *cx)
|
JS_RestoreFrameChain(JSContext *cx)
|
||||||
{
|
{
|
||||||
CHECK_REQUEST(cx);
|
CHECK_REQUEST(cx);
|
||||||
JS_ASSERT_NOT_ON_TRACE(cx);
|
|
||||||
cx->stack.restoreFrameChain();
|
cx->stack.restoreFrameChain();
|
||||||
}
|
}
|
||||||
|
|
||||||
|
@ -2157,7 +2157,7 @@ JS_StringToVersion(const char *string);
|
|||||||
of the input string */
|
of the input string */
|
||||||
/* JS_BIT(10) is currently unused. */
|
/* JS_BIT(10) is currently unused. */
|
||||||
|
|
||||||
#define JSOPTION_JIT JS_BIT(11) /* Enable JIT compilation. */
|
#define JSOPTION_JIT JS_BIT(11) /* Deprecated; does nothing */
|
||||||
|
|
||||||
#define JSOPTION_NO_SCRIPT_RVAL JS_BIT(12) /* A promise to the compiler
|
#define JSOPTION_NO_SCRIPT_RVAL JS_BIT(12) /* A promise to the compiler
|
||||||
that a null rval out-param
|
that a null rval out-param
|
||||||
|
@ -110,7 +110,6 @@
|
|||||||
#include "jsarray.h"
|
#include "jsarray.h"
|
||||||
#include "jsatom.h"
|
#include "jsatom.h"
|
||||||
#include "jsbool.h"
|
#include "jsbool.h"
|
||||||
#include "jsbuiltins.h"
|
|
||||||
#include "jscntxt.h"
|
#include "jscntxt.h"
|
||||||
#include "jsversion.h"
|
#include "jsversion.h"
|
||||||
#include "jsfun.h"
|
#include "jsfun.h"
|
||||||
@ -123,7 +122,6 @@
|
|||||||
#include "jsobj.h"
|
#include "jsobj.h"
|
||||||
#include "jsscope.h"
|
#include "jsscope.h"
|
||||||
#include "jsstr.h"
|
#include "jsstr.h"
|
||||||
#include "jstracer.h"
|
|
||||||
#include "jswrapper.h"
|
#include "jswrapper.h"
|
||||||
#include "methodjit/MethodJIT.h"
|
#include "methodjit/MethodJIT.h"
|
||||||
#include "methodjit/StubCalls.h"
|
#include "methodjit/StubCalls.h"
|
||||||
@ -507,25 +505,6 @@ SetArrayElement(JSContext *cx, JSObject *obj, jsdouble index, const Value &v)
|
|||||||
return obj->setGeneric(cx, idr.id(), &tmp, true);
|
return obj->setGeneric(cx, idr.id(), &tmp, true);
|
||||||
}
|
}
|
||||||
|
|
||||||
#ifdef JS_TRACER
|
|
||||||
JSBool JS_FASTCALL
|
|
||||||
js_EnsureDenseArrayCapacity(JSContext *cx, JSObject *obj, jsint i)
|
|
||||||
{
|
|
||||||
#ifdef DEBUG
|
|
||||||
Class *origObjClasp = obj->getClass();
|
|
||||||
#endif
|
|
||||||
jsuint u = jsuint(i);
|
|
||||||
JSBool ret = (obj->ensureDenseArrayElements(cx, u, 1) == JSObject::ED_OK);
|
|
||||||
|
|
||||||
/* Partially check the CallInfo's storeAccSet is correct. */
|
|
||||||
JS_ASSERT(obj->getClass() == origObjClasp);
|
|
||||||
return ret;
|
|
||||||
}
|
|
||||||
/* This function and its callees do not touch any object's .clasp field. */
|
|
||||||
JS_DEFINE_CALLINFO_3(extern, BOOL, js_EnsureDenseArrayCapacity, CONTEXT, OBJECT, INT32,
|
|
||||||
0, nanojit::ACCSET_STORE_ANY & ~tjit::ACCSET_OBJ_CLASP)
|
|
||||||
#endif
|
|
||||||
|
|
||||||
/*
|
/*
|
||||||
* Delete the element |index| from |obj|. If |strict|, do a strict
|
* Delete the element |index| from |obj|. If |strict|, do a strict
|
||||||
* deletion: throw if the property is not configurable.
|
* deletion: throw if the property is not configurable.
|
||||||
@ -1718,7 +1697,6 @@ array_toString(JSContext *cx, uintN argc, Value *vp)
|
|||||||
return true;
|
return true;
|
||||||
}
|
}
|
||||||
|
|
||||||
LeaveTrace(cx);
|
|
||||||
InvokeArgsGuard ag;
|
InvokeArgsGuard ag;
|
||||||
if (!cx->stack.pushInvokeArgs(cx, 0, &ag))
|
if (!cx->stack.pushInvokeArgs(cx, 0, &ag))
|
||||||
return false;
|
return false;
|
||||||
@ -1770,16 +1748,22 @@ InitArrayTypes(JSContext *cx, TypeObject *type, const Value *vector, unsigned co
|
|||||||
return true;
|
return true;
|
||||||
}
|
}
|
||||||
|
|
||||||
static JSBool
|
enum ShouldUpdateTypes
|
||||||
InitArrayElements(JSContext *cx, JSObject *obj, jsuint start, jsuint count, const Value *vector, bool updateTypes)
|
{
|
||||||
|
UpdateTypes = true,
|
||||||
|
DontUpdateTypes = false
|
||||||
|
};
|
||||||
|
|
||||||
|
static bool
|
||||||
|
InitArrayElements(JSContext *cx, JSObject *obj, uint32 start, uint32 count, const Value *vector, ShouldUpdateTypes updateTypes)
|
||||||
{
|
{
|
||||||
JS_ASSERT(count <= MAX_ARRAY_INDEX);
|
JS_ASSERT(count <= MAX_ARRAY_INDEX);
|
||||||
|
|
||||||
if (count == 0)
|
if (count == 0)
|
||||||
return JS_TRUE;
|
return true;
|
||||||
|
|
||||||
if (updateTypes && !InitArrayTypes(cx, obj->getType(cx), vector, count))
|
if (updateTypes && !InitArrayTypes(cx, obj->getType(cx), vector, count))
|
||||||
return JS_FALSE;
|
return false;
|
||||||
|
|
||||||
/*
|
/*
|
||||||
* Optimize for dense arrays so long as adding the given set of elements
|
* Optimize for dense arrays so long as adding the given set of elements
|
||||||
@ -1812,16 +1796,16 @@ InitArrayElements(JSContext *cx, JSObject *obj, jsuint start, jsuint count, cons
|
|||||||
while (vector < end && start <= MAX_ARRAY_INDEX) {
|
while (vector < end && start <= MAX_ARRAY_INDEX) {
|
||||||
if (!JS_CHECK_OPERATION_LIMIT(cx) ||
|
if (!JS_CHECK_OPERATION_LIMIT(cx) ||
|
||||||
!SetArrayElement(cx, obj, start++, *vector++)) {
|
!SetArrayElement(cx, obj, start++, *vector++)) {
|
||||||
return JS_FALSE;
|
return false;
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
if (vector == end)
|
if (vector == end)
|
||||||
return JS_TRUE;
|
return true;
|
||||||
|
|
||||||
/* Finish out any remaining elements past the max array index. */
|
/* Finish out any remaining elements past the max array index. */
|
||||||
if (obj->isDenseArray() && !obj->makeDenseArraySlow(cx))
|
if (obj->isDenseArray() && !obj->makeDenseArraySlow(cx))
|
||||||
return JS_FALSE;
|
return false;
|
||||||
|
|
||||||
JS_ASSERT(start == MAX_ARRAY_INDEX + 1);
|
JS_ASSERT(start == MAX_ARRAY_INDEX + 1);
|
||||||
AutoValueRooter tvr(cx);
|
AutoValueRooter tvr(cx);
|
||||||
@ -1831,12 +1815,12 @@ InitArrayElements(JSContext *cx, JSObject *obj, jsuint start, jsuint count, cons
|
|||||||
*tvr.addr() = *vector++;
|
*tvr.addr() = *vector++;
|
||||||
if (!js_ValueToStringId(cx, idval, idr.addr()) ||
|
if (!js_ValueToStringId(cx, idval, idr.addr()) ||
|
||||||
!obj->setGeneric(cx, idr.id(), tvr.addr(), true)) {
|
!obj->setGeneric(cx, idr.id(), tvr.addr(), true)) {
|
||||||
return JS_FALSE;
|
return false;
|
||||||
}
|
}
|
||||||
idval.getDoubleRef() += 1;
|
idval.getDoubleRef() += 1;
|
||||||
} while (vector != end);
|
} while (vector != end);
|
||||||
|
|
||||||
return JS_TRUE;
|
return true;
|
||||||
}
|
}
|
||||||
|
|
||||||
#if 0
|
#if 0
|
||||||
@ -2240,7 +2224,7 @@ js::array_sort(JSContext *cx, uintN argc, Value *vp)
|
|||||||
* InitArrayElements easier.
|
* InitArrayElements easier.
|
||||||
*/
|
*/
|
||||||
vec.resize(n);
|
vec.resize(n);
|
||||||
if (!InitArrayElements(cx, obj, 0, jsuint(n), vec.begin(), false))
|
if (!InitArrayElements(cx, obj, 0, jsuint(n), vec.begin(), DontUpdateTypes))
|
||||||
return false;
|
return false;
|
||||||
}
|
}
|
||||||
|
|
||||||
@ -2270,7 +2254,7 @@ array_push_slowly(JSContext *cx, JSObject *obj, CallArgs &args)
|
|||||||
|
|
||||||
if (!js_GetLengthProperty(cx, obj, &length))
|
if (!js_GetLengthProperty(cx, obj, &length))
|
||||||
return false;
|
return false;
|
||||||
if (!InitArrayElements(cx, obj, length, args.length(), args.array(), true))
|
if (!InitArrayElements(cx, obj, length, args.length(), args.array(), UpdateTypes))
|
||||||
return false;
|
return false;
|
||||||
|
|
||||||
/* Per ECMA-262, return the new array length. */
|
/* Per ECMA-262, return the new array length. */
|
||||||
@ -2333,23 +2317,6 @@ js_NewbornArrayPush(JSContext *cx, JSObject *obj, const Value &vp)
|
|||||||
return NewbornArrayPushImpl(cx, obj, vp);
|
return NewbornArrayPushImpl(cx, obj, vp);
|
||||||
}
|
}
|
||||||
|
|
||||||
#ifdef JS_TRACER
|
|
||||||
JSBool JS_FASTCALL
|
|
||||||
js_NewbornArrayPush_tn(JSContext *cx, JSObject *obj, ValueArgType v)
|
|
||||||
{
|
|
||||||
TraceMonitor *tm = JS_TRACE_MONITOR_ON_TRACE(cx);
|
|
||||||
|
|
||||||
if (!NewbornArrayPushImpl(cx, obj, ValueArgToConstRef(v))) {
|
|
||||||
SetBuiltinError(tm);
|
|
||||||
return JS_FALSE;
|
|
||||||
}
|
|
||||||
|
|
||||||
return WasBuiltinSuccessful(tm);
|
|
||||||
}
|
|
||||||
JS_DEFINE_CALLINFO_3(extern, BOOL_FAIL, js_NewbornArrayPush_tn, CONTEXT, OBJECT,
|
|
||||||
VALUE, 0, nanojit::ACCSET_STORE_ANY)
|
|
||||||
#endif
|
|
||||||
|
|
||||||
JSBool
|
JSBool
|
||||||
js::array_push(JSContext *cx, uintN argc, Value *vp)
|
js::array_push(JSContext *cx, uintN argc, Value *vp)
|
||||||
{
|
{
|
||||||
@ -2436,7 +2403,6 @@ mjit::stubs::ArrayShift(VMFrame &f)
|
|||||||
{
|
{
|
||||||
JSObject *obj = &f.regs.sp[-1].toObject();
|
JSObject *obj = &f.regs.sp[-1].toObject();
|
||||||
JS_ASSERT(obj->isDenseArray());
|
JS_ASSERT(obj->isDenseArray());
|
||||||
JS_ASSERT(!js_PrototypeHasIndexedProperties(f.cx, obj));
|
|
||||||
|
|
||||||
/*
|
/*
|
||||||
* At this point the length and initialized length have already been
|
* At this point the length and initialized length have already been
|
||||||
@ -2555,7 +2521,7 @@ array_unshift(JSContext *cx, uintN argc, Value *vp)
|
|||||||
}
|
}
|
||||||
|
|
||||||
/* Copy from args to the bottom of the array. */
|
/* Copy from args to the bottom of the array. */
|
||||||
if (!InitArrayElements(cx, obj, 0, args.length(), args.array(), true))
|
if (!InitArrayElements(cx, obj, 0, args.length(), args.array(), UpdateTypes))
|
||||||
return JS_FALSE;
|
return JS_FALSE;
|
||||||
|
|
||||||
newlen += args.length();
|
newlen += args.length();
|
||||||
@ -3753,19 +3719,6 @@ NewDenseCopiedArray(JSContext *cx, uint32 length, const Value *vp, JSObject *pro
|
|||||||
return obj;
|
return obj;
|
||||||
}
|
}
|
||||||
|
|
||||||
#ifdef JS_TRACER
|
|
||||||
JS_DEFINE_CALLINFO_2(extern, OBJECT, NewDenseEmptyArray, CONTEXT, OBJECT, 0,
|
|
||||||
nanojit::ACCSET_STORE_ANY)
|
|
||||||
JS_DEFINE_CALLINFO_3(extern, OBJECT, NewDenseAllocatedArray, CONTEXT, UINT32, OBJECT, 0,
|
|
||||||
nanojit::ACCSET_STORE_ANY)
|
|
||||||
JS_DEFINE_CALLINFO_3(extern, OBJECT, NewDenseAllocatedEmptyArray, CONTEXT, UINT32, OBJECT, 0,
|
|
||||||
nanojit::ACCSET_STORE_ANY)
|
|
||||||
JS_DEFINE_CALLINFO_3(extern, OBJECT, NewDenseUnallocatedArray, CONTEXT, UINT32, OBJECT, 0,
|
|
||||||
nanojit::ACCSET_STORE_ANY)
|
|
||||||
#endif
|
|
||||||
|
|
||||||
|
|
||||||
|
|
||||||
JSObject *
|
JSObject *
|
||||||
NewSlowEmptyArray(JSContext *cx)
|
NewSlowEmptyArray(JSContext *cx)
|
||||||
{
|
{
|
||||||
|
@ -1,330 +0,0 @@
|
|||||||
/* -*- Mode: C++; tab-width: 8; indent-tabs-mode: nil; c-basic-offset: 4; -*-
|
|
||||||
* vim: set ts=4 sw=4 et tw=99:
|
|
||||||
*
|
|
||||||
* ***** BEGIN LICENSE BLOCK *****
|
|
||||||
* Version: MPL 1.1/GPL 2.0/LGPL 2.1
|
|
||||||
*
|
|
||||||
* The contents of this file are subject to the Mozilla Public License Version
|
|
||||||
* 1.1 (the "License"); you may not use this file except in compliance with
|
|
||||||
* the License. You may obtain a copy of the License at
|
|
||||||
* http://www.mozilla.org/MPL/
|
|
||||||
*
|
|
||||||
* Software distributed under the License is distributed on an "AS IS" basis,
|
|
||||||
* WITHOUT WARRANTY OF ANY KIND, either express or implied. See the License
|
|
||||||
* for the specific language governing rights and limitations under the
|
|
||||||
* License.
|
|
||||||
*
|
|
||||||
* The Original Code is Mozilla SpiderMonkey JavaScript 1.9 code, released
|
|
||||||
* May 28, 2008.
|
|
||||||
*
|
|
||||||
* The Initial Developer of the Original Code is
|
|
||||||
* Andreas Gal <gal@mozilla.com>
|
|
||||||
*
|
|
||||||
* Contributor(s):
|
|
||||||
* Brendan Eich <brendan@mozilla.org>
|
|
||||||
* Mike Shaver <shaver@mozilla.org>
|
|
||||||
* David Anderson <danderson@mozilla.com>
|
|
||||||
*
|
|
||||||
* Alternatively, the contents of this file may be used under the terms of
|
|
||||||
* either of the GNU General Public License Version 2 or later (the "GPL"),
|
|
||||||
* or the GNU Lesser General Public License Version 2.1 or later (the "LGPL"),
|
|
||||||
* in which case the provisions of the GPL or the LGPL are applicable instead
|
|
||||||
* of those above. If you wish to allow use of your version of this file only
|
|
||||||
* under the terms of either the GPL or the LGPL, and not to allow others to
|
|
||||||
* use your version of this file under the terms of the MPL, indicate your
|
|
||||||
* decision by deleting the provisions above and replace them with the notice
|
|
||||||
* and other provisions required by the GPL or the LGPL. If you do not delete
|
|
||||||
* the provisions above, a recipient may use your version of this file under
|
|
||||||
* the terms of any one of the MPL, the GPL or the LGPL.
|
|
||||||
*
|
|
||||||
* ***** END LICENSE BLOCK ***** */
|
|
||||||
|
|
||||||
#include <math.h>
|
|
||||||
|
|
||||||
#include "jsapi.h"
|
|
||||||
#include "jsstdint.h"
|
|
||||||
#include "jsarray.h"
|
|
||||||
#include "jsbool.h"
|
|
||||||
#include "jscntxt.h"
|
|
||||||
#include "jsgc.h"
|
|
||||||
#include "jsiter.h"
|
|
||||||
#include "jsnum.h"
|
|
||||||
#include "jslibmath.h"
|
|
||||||
#include "jsmath.h"
|
|
||||||
#include "jsnum.h"
|
|
||||||
#include "prmjtime.h"
|
|
||||||
#include "jsdate.h"
|
|
||||||
#include "jsscope.h"
|
|
||||||
#include "jsstr.h"
|
|
||||||
#include "jsbuiltins.h"
|
|
||||||
#include "jstracer.h"
|
|
||||||
|
|
||||||
#include "jsatominlines.h"
|
|
||||||
#include "jscntxtinlines.h"
|
|
||||||
#include "jsnuminlines.h"
|
|
||||||
#include "jsobjinlines.h"
|
|
||||||
#include "jsscopeinlines.h"
|
|
||||||
|
|
||||||
using namespace avmplus;
|
|
||||||
using namespace nanojit;
|
|
||||||
using namespace js;
|
|
||||||
|
|
||||||
JS_FRIEND_API(void)
|
|
||||||
js_SetTraceableNativeFailed(JSContext *cx)
|
|
||||||
{
|
|
||||||
/*
|
|
||||||
* We might not be on trace (we might have deep bailed) so we hope
|
|
||||||
* cx->compartment is correct.
|
|
||||||
*/
|
|
||||||
SetBuiltinError(JS_TRACE_MONITOR_FROM_CONTEXT(cx));
|
|
||||||
}
|
|
||||||
|
|
||||||
/*
|
|
||||||
* NB: bool FASTCALL is not compatible with Nanojit's calling convention usage.
|
|
||||||
* Do not use bool FASTCALL, use JSBool only!
|
|
||||||
*/
|
|
||||||
|
|
||||||
jsdouble FASTCALL
|
|
||||||
js_dmod(jsdouble a, jsdouble b)
|
|
||||||
{
|
|
||||||
if (b == 0.0) {
|
|
||||||
jsdpun u;
|
|
||||||
u.s.hi = JSDOUBLE_HI32_NAN;
|
|
||||||
u.s.lo = JSDOUBLE_LO32_NAN;
|
|
||||||
return u.d;
|
|
||||||
}
|
|
||||||
return js_fmod(a, b);
|
|
||||||
}
|
|
||||||
JS_DEFINE_CALLINFO_2(extern, DOUBLE, js_dmod, DOUBLE, DOUBLE, 1, ACCSET_NONE)
|
|
||||||
|
|
||||||
int32 FASTCALL
|
|
||||||
js_imod(int32 a, int32 b)
|
|
||||||
{
|
|
||||||
if (a < 0 || b <= 0)
|
|
||||||
return -1;
|
|
||||||
int r = a % b;
|
|
||||||
return r;
|
|
||||||
}
|
|
||||||
JS_DEFINE_CALLINFO_2(extern, INT32, js_imod, INT32, INT32, 1, ACCSET_NONE)
|
|
||||||
|
|
||||||
#if JS_BITS_PER_WORD == 32
|
|
||||||
|
|
||||||
jsdouble FASTCALL
|
|
||||||
js_UnboxNumberAsDouble(uint32 tag, uint32 payload)
|
|
||||||
{
|
|
||||||
if (tag == JSVAL_TAG_INT32)
|
|
||||||
return (double)(int32)payload;
|
|
||||||
|
|
||||||
JS_ASSERT(tag <= JSVAL_TAG_CLEAR);
|
|
||||||
jsval_layout l;
|
|
||||||
l.s.tag = (JSValueTag)tag;
|
|
||||||
l.s.payload.u32 = payload;
|
|
||||||
return l.asDouble;
|
|
||||||
}
|
|
||||||
JS_DEFINE_CALLINFO_2(extern, DOUBLE, js_UnboxNumberAsDouble, UINT32, UINT32, 1, ACCSET_NONE)
|
|
||||||
|
|
||||||
int32 FASTCALL
|
|
||||||
js_UnboxNumberAsInt32(uint32 tag, uint32 payload)
|
|
||||||
{
|
|
||||||
if (tag == JSVAL_TAG_INT32)
|
|
||||||
return (int32)payload;
|
|
||||||
|
|
||||||
JS_ASSERT(tag <= JSVAL_TAG_CLEAR);
|
|
||||||
jsval_layout l;
|
|
||||||
l.s.tag = (JSValueTag)tag;
|
|
||||||
l.s.payload.u32 = payload;
|
|
||||||
return js_DoubleToECMAInt32(l.asDouble);
|
|
||||||
}
|
|
||||||
JS_DEFINE_CALLINFO_2(extern, INT32, js_UnboxNumberAsInt32, UINT32, UINT32, 1, ACCSET_NONE)
|
|
||||||
|
|
||||||
#elif JS_BITS_PER_WORD == 64
|
|
||||||
|
|
||||||
jsdouble FASTCALL
|
|
||||||
js_UnboxNumberAsDouble(Value v)
|
|
||||||
{
|
|
||||||
if (v.isInt32())
|
|
||||||
return (jsdouble)v.toInt32();
|
|
||||||
JS_ASSERT(v.isDouble());
|
|
||||||
return v.toDouble();
|
|
||||||
}
|
|
||||||
JS_DEFINE_CALLINFO_1(extern, DOUBLE, js_UnboxNumberAsDouble, JSVAL, 1, ACCSET_NONE)
|
|
||||||
|
|
||||||
int32 FASTCALL
|
|
||||||
js_UnboxNumberAsInt32(Value v)
|
|
||||||
{
|
|
||||||
if (v.isInt32())
|
|
||||||
return v.toInt32();
|
|
||||||
JS_ASSERT(v.isDouble());
|
|
||||||
return js_DoubleToECMAInt32(v.toDouble());
|
|
||||||
}
|
|
||||||
JS_DEFINE_CALLINFO_1(extern, INT32, js_UnboxNumberAsInt32, VALUE, 1, ACCSET_NONE)
|
|
||||||
|
|
||||||
#endif
|
|
||||||
|
|
||||||
int32 FASTCALL
|
|
||||||
js_DoubleToInt32(jsdouble d)
|
|
||||||
{
|
|
||||||
return js_DoubleToECMAInt32(d);
|
|
||||||
}
|
|
||||||
JS_DEFINE_CALLINFO_1(extern, INT32, js_DoubleToInt32, DOUBLE, 1, ACCSET_NONE)
|
|
||||||
|
|
||||||
uint32 FASTCALL
|
|
||||||
js_DoubleToUint32(jsdouble d)
|
|
||||||
{
|
|
||||||
return js_DoubleToECMAUint32(d);
|
|
||||||
}
|
|
||||||
JS_DEFINE_CALLINFO_1(extern, UINT32, js_DoubleToUint32, DOUBLE, 1, ACCSET_NONE)
|
|
||||||
|
|
||||||
/*
|
|
||||||
* js_StringToNumber and js_StringToInt32 store into their second argument, so
|
|
||||||
* they need to be annotated accordingly. To be future-proof, we use
|
|
||||||
* ACCSET_STORE_ANY so that new callers don't have to remember to update the
|
|
||||||
* annotation.
|
|
||||||
*/
|
|
||||||
jsdouble FASTCALL
|
|
||||||
js_StringToNumber(JSContext* cx, JSString* str, JSBool *ok)
|
|
||||||
{
|
|
||||||
double out = 0; /* silence warnings. */
|
|
||||||
*ok = StringToNumberType<jsdouble>(cx, str, &out);
|
|
||||||
return out;
|
|
||||||
}
|
|
||||||
JS_DEFINE_CALLINFO_3(extern, DOUBLE, js_StringToNumber, CONTEXT, STRING, BOOLPTR,
|
|
||||||
0, ACCSET_STORE_ANY)
|
|
||||||
|
|
||||||
int32 FASTCALL
|
|
||||||
js_StringToInt32(JSContext* cx, JSString* str, JSBool *ok)
|
|
||||||
{
|
|
||||||
int32 out = 0; /* silence warnings. */
|
|
||||||
*ok = StringToNumberType<int32>(cx, str, &out);
|
|
||||||
return out;
|
|
||||||
}
|
|
||||||
JS_DEFINE_CALLINFO_3(extern, INT32, js_StringToInt32, CONTEXT, STRING, BOOLPTR,
|
|
||||||
0, ACCSET_STORE_ANY)
|
|
||||||
|
|
||||||
/* Nb: it's always safe to set isDefinitelyAtom to false if you're unsure or don't know. */
|
|
||||||
static inline JSBool
|
|
||||||
AddPropertyHelper(JSContext* cx, JSObject* obj, Shape* shape, bool isDefinitelyAtom)
|
|
||||||
{
|
|
||||||
JS_ASSERT(shape->previous() == obj->lastProperty());
|
|
||||||
|
|
||||||
if (obj->nativeEmpty()) {
|
|
||||||
if (!obj->ensureClassReservedSlotsForEmptyObject(cx))
|
|
||||||
return false;
|
|
||||||
}
|
|
||||||
|
|
||||||
uint32 slot;
|
|
||||||
slot = shape->slot;
|
|
||||||
JS_ASSERT(slot == obj->slotSpan());
|
|
||||||
|
|
||||||
if (slot < obj->numSlots()) {
|
|
||||||
JS_ASSERT(obj->getSlot(slot).isUndefined());
|
|
||||||
} else {
|
|
||||||
if (!obj->allocSlot(cx, &slot))
|
|
||||||
return false;
|
|
||||||
JS_ASSERT(slot == shape->slot);
|
|
||||||
}
|
|
||||||
|
|
||||||
obj->extend(cx, shape, isDefinitelyAtom);
|
|
||||||
return !js_IsPropertyCacheDisabled(cx);
|
|
||||||
}
|
|
||||||
|
|
||||||
JSBool FASTCALL
|
|
||||||
js_AddProperty(JSContext* cx, JSObject* obj, Shape* shape)
|
|
||||||
{
|
|
||||||
return AddPropertyHelper(cx, obj, shape, /* isDefinitelyAtom = */false);
|
|
||||||
}
|
|
||||||
JS_DEFINE_CALLINFO_3(extern, BOOL, js_AddProperty, CONTEXT, OBJECT, SHAPE, 0, ACCSET_STORE_ANY)
|
|
||||||
|
|
||||||
JSBool FASTCALL
|
|
||||||
js_AddAtomProperty(JSContext* cx, JSObject* obj, Shape* shape)
|
|
||||||
{
|
|
||||||
return AddPropertyHelper(cx, obj, shape, /* isDefinitelyAtom = */true);
|
|
||||||
}
|
|
||||||
JS_DEFINE_CALLINFO_3(extern, BOOL, js_AddAtomProperty, CONTEXT, OBJECT, SHAPE, 0, ACCSET_STORE_ANY)
|
|
||||||
|
|
||||||
static JSBool
|
|
||||||
HasProperty(JSContext* cx, JSObject* obj, jsid id)
|
|
||||||
{
|
|
||||||
// Check that we know how the lookup op will behave.
|
|
||||||
for (JSObject* pobj = obj; pobj; pobj = pobj->getProto()) {
|
|
||||||
if (pobj->getOps()->lookupProperty)
|
|
||||||
return JS_NEITHER;
|
|
||||||
Class* clasp = pobj->getClass();
|
|
||||||
if (clasp->resolve != JS_ResolveStub && clasp != &StringClass)
|
|
||||||
return JS_NEITHER;
|
|
||||||
}
|
|
||||||
|
|
||||||
JSObject* obj2;
|
|
||||||
JSProperty* prop;
|
|
||||||
if (!LookupPropertyWithFlags(cx, obj, id, JSRESOLVE_QUALIFIED, &obj2, &prop))
|
|
||||||
return JS_NEITHER;
|
|
||||||
return prop != NULL;
|
|
||||||
}
|
|
||||||
|
|
||||||
JSBool FASTCALL
|
|
||||||
js_HasNamedProperty(JSContext* cx, JSObject* obj, JSString* idstr)
|
|
||||||
{
|
|
||||||
JSAtom *atom = js_AtomizeString(cx, idstr);
|
|
||||||
if (!atom)
|
|
||||||
return JS_NEITHER;
|
|
||||||
|
|
||||||
return HasProperty(cx, obj, ATOM_TO_JSID(atom));
|
|
||||||
}
|
|
||||||
JS_DEFINE_CALLINFO_3(extern, BOOL, js_HasNamedProperty, CONTEXT, OBJECT, STRING,
|
|
||||||
0, ACCSET_STORE_ANY)
|
|
||||||
|
|
||||||
JSBool FASTCALL
|
|
||||||
js_HasNamedPropertyInt32(JSContext* cx, JSObject* obj, int32 index)
|
|
||||||
{
|
|
||||||
jsid id;
|
|
||||||
if (!js_Int32ToId(cx, index, &id))
|
|
||||||
return JS_NEITHER;
|
|
||||||
|
|
||||||
return HasProperty(cx, obj, id);
|
|
||||||
}
|
|
||||||
JS_DEFINE_CALLINFO_3(extern, BOOL, js_HasNamedPropertyInt32, CONTEXT, OBJECT, INT32,
|
|
||||||
0, ACCSET_STORE_ANY)
|
|
||||||
|
|
||||||
JSString* FASTCALL
|
|
||||||
js_TypeOfObject(JSContext* cx, JSObject* obj)
|
|
||||||
{
|
|
||||||
JS_ASSERT(obj);
|
|
||||||
return cx->runtime->atomState.typeAtoms[obj->typeOf(cx)];
|
|
||||||
}
|
|
||||||
JS_DEFINE_CALLINFO_2(extern, STRING, js_TypeOfObject, CONTEXT, OBJECT, 1, ACCSET_NONE)
|
|
||||||
|
|
||||||
JSString* FASTCALL
|
|
||||||
js_BooleanIntToString(JSContext *cx, int32 unboxed)
|
|
||||||
{
|
|
||||||
JS_ASSERT(uint32(unboxed) <= 1);
|
|
||||||
return cx->runtime->atomState.booleanAtoms[unboxed];
|
|
||||||
}
|
|
||||||
JS_DEFINE_CALLINFO_2(extern, STRING, js_BooleanIntToString, CONTEXT, INT32, 1, ACCSET_NONE)
|
|
||||||
|
|
||||||
JSObject* FASTCALL
|
|
||||||
js_NewNullClosure(JSContext* cx, JSObject* funobj, JSObject* proto, JSObject* parent)
|
|
||||||
{
|
|
||||||
JS_ASSERT(funobj->isFunction());
|
|
||||||
JS_ASSERT(proto->isFunction());
|
|
||||||
JS_ASSERT(JS_ON_TRACE(cx));
|
|
||||||
|
|
||||||
JSFunction *fun = (JSFunction*) funobj;
|
|
||||||
JS_ASSERT(funobj->getFunctionPrivate() == fun);
|
|
||||||
|
|
||||||
types::TypeObject *type = proto->getNewType(cx);
|
|
||||||
if (!type)
|
|
||||||
return NULL;
|
|
||||||
|
|
||||||
JSObject* closure = js_NewGCObject(cx, gc::FINALIZE_OBJECT2);
|
|
||||||
if (!closure)
|
|
||||||
return NULL;
|
|
||||||
|
|
||||||
if (!closure->initSharingEmptyShape(cx, &FunctionClass, type, parent,
|
|
||||||
fun, gc::FINALIZE_OBJECT2)) {
|
|
||||||
return NULL;
|
|
||||||
}
|
|
||||||
return closure;
|
|
||||||
}
|
|
||||||
JS_DEFINE_CALLINFO_4(extern, OBJECT, js_NewNullClosure, CONTEXT, OBJECT, OBJECT, OBJECT,
|
|
||||||
0, ACCSET_STORE_ANY)
|
|
||||||
|
|
@ -1,653 +0,0 @@
|
|||||||
/* -*- Mode: C++; tab-width: 8; indent-tabs-mode: nil; c-basic-offset: 4 -*-
|
|
||||||
* vim: set ts=8 sw=4 et tw=99:
|
|
||||||
*
|
|
||||||
* ***** BEGIN LICENSE BLOCK *****
|
|
||||||
* Version: MPL 1.1/GPL 2.0/LGPL 2.1
|
|
||||||
*
|
|
||||||
* The contents of this file are subject to the Mozilla Public License Version
|
|
||||||
* 1.1 (the "License"); you may not use this file except in compliance with
|
|
||||||
* the License. You may obtain a copy of the License at
|
|
||||||
* http://www.mozilla.org/MPL/
|
|
||||||
*
|
|
||||||
* Software distributed under the License is distributed on an "AS IS" basis,
|
|
||||||
* WITHOUT WARRANTY OF ANY KIND, either express or implied. See the License
|
|
||||||
* for the specific language governing rights and limitations under the
|
|
||||||
* License.
|
|
||||||
*
|
|
||||||
* The Original Code is Mozilla SpiderMonkey JavaScript 1.9 code, released
|
|
||||||
* May 28, 2008.
|
|
||||||
*
|
|
||||||
* The Initial Developer of the Original Code is
|
|
||||||
* Mozilla Corporation.
|
|
||||||
*
|
|
||||||
* Contributor(s):
|
|
||||||
* Jason Orendorff <jorendorff@mozilla.com>
|
|
||||||
*
|
|
||||||
* Alternatively, the contents of this file may be used under the terms of
|
|
||||||
* either of the GNU General Public License Version 2 or later (the "GPL"),
|
|
||||||
* or the GNU Lesser General Public License Version 2.1 or later (the "LGPL"),
|
|
||||||
* in which case the provisions of the GPL or the LGPL are applicable instead
|
|
||||||
* of those above. If you wish to allow use of your version of this file only
|
|
||||||
* under the terms of either the GPL or the LGPL, and not to allow others to
|
|
||||||
* use your version of this file under the terms of the MPL, indicate your
|
|
||||||
* decision by deleting the provisions above and replace them with the notice
|
|
||||||
* and other provisions required by the GPL or the LGPL. If you do not delete
|
|
||||||
* the provisions above, a recipient may use your version of this file under
|
|
||||||
* the terms of any one of the MPL, the GPL or the LGPL.
|
|
||||||
*
|
|
||||||
* ***** END LICENSE BLOCK ***** */
|
|
||||||
|
|
||||||
#ifndef jsbuiltins_h___
|
|
||||||
#define jsbuiltins_h___
|
|
||||||
|
|
||||||
#ifdef JS_TRACER
|
|
||||||
|
|
||||||
// nanojit.h includes windows.h, so undo the obnoxious #defines, if needed
|
|
||||||
#include "nanojit/nanojit.h"
|
|
||||||
#include "jswin.h"
|
|
||||||
#include "jsprvtd.h"
|
|
||||||
|
|
||||||
enum JSTNErrType { INFALLIBLE, FAIL_STATUS, FAIL_NULL, FAIL_NEG, FAIL_NEITHER };
|
|
||||||
enum {
|
|
||||||
JSTN_ERRTYPE_MASK = 0x07,
|
|
||||||
JSTN_UNBOX_AFTER = 0x08,
|
|
||||||
JSTN_MORE = 0x10,
|
|
||||||
JSTN_CONSTRUCTOR = 0x20,
|
|
||||||
JSTN_RETURN_NULLABLE_STR = 0x40,
|
|
||||||
JSTN_RETURN_NULLABLE_OBJ = 0x80
|
|
||||||
};
|
|
||||||
|
|
||||||
#define JSTN_ERRTYPE(jstn) ((jstn)->flags & JSTN_ERRTYPE_MASK)
|
|
||||||
|
|
||||||
/*
|
|
||||||
* Type describing a type specialization of a js::Native.
|
|
||||||
*
|
|
||||||
* |prefix| and |argtypes| declare what arguments should be passed to the
|
|
||||||
* native function. |prefix| can contain the following characters:
|
|
||||||
*
|
|
||||||
* 'C': a JSContext* argument
|
|
||||||
* 'T': |this| as a JSObject* argument (bails if |this| is not an object)
|
|
||||||
* 'S': |this| as a JSString* argument (bails if |this| is not a string)
|
|
||||||
* 'R': a JSRuntime* argument
|
|
||||||
* 'P': the pc as a jsbytecode*
|
|
||||||
* 'D': |this| as a number (jsdouble)
|
|
||||||
* 'f': the function being called, as a JSObject*
|
|
||||||
* 'p': the .prototype of the function, as a JSObject*
|
|
||||||
*
|
|
||||||
* The corresponding things will get passed as arguments to the builtin in
|
|
||||||
* reverse order (so TC means JSContext* as the first arg, and the
|
|
||||||
* JSObject* for |this| as the second arg).
|
|
||||||
*
|
|
||||||
* |argtypes| can contain the following characters:
|
|
||||||
* 'd': a number (double) argument
|
|
||||||
* 'i': an integer argument
|
|
||||||
* 's': a JSString* argument
|
|
||||||
* 'o': a JSObject* argument
|
|
||||||
* 'r': a JSObject* argument that is of class RegExpClass
|
|
||||||
* 'f': a JSObject* argument that is of class FunctionClass
|
|
||||||
* 'v': a value argument: on 32-bit, a Value*, on 64-bit, a jsval
|
|
||||||
*/
|
|
||||||
struct JSSpecializedNative {
|
|
||||||
const nanojit::CallInfo *builtin;
|
|
||||||
const char *prefix;
|
|
||||||
const char *argtypes;
|
|
||||||
uintN flags; /* JSTNErrType | JSTN_UNBOX_AFTER | JSTN_MORE |
|
|
||||||
JSTN_CONSTRUCTOR */
|
|
||||||
};
|
|
||||||
|
|
||||||
/*
|
|
||||||
* Type holding extra trace-specific information about a fast native.
|
|
||||||
*
|
|
||||||
* 'specializations' points to a static array of available specializations
|
|
||||||
* terminated by the lack of having the JSTN_MORE flag set.
|
|
||||||
*/
|
|
||||||
struct JSNativeTraceInfo {
|
|
||||||
js::Native native;
|
|
||||||
JSSpecializedNative *specializations;
|
|
||||||
};
|
|
||||||
|
|
||||||
/* Macros used by JS_DEFINE_CALLINFOn. */
|
|
||||||
#ifdef DEBUG
|
|
||||||
#define _JS_CI_NAME(op) ,#op
|
|
||||||
#else
|
|
||||||
#define _JS_CI_NAME(op)
|
|
||||||
#endif
|
|
||||||
|
|
||||||
#define _JS_I32_ARGTYPE nanojit::ARGTYPE_I
|
|
||||||
#define _JS_I32_RETTYPE nanojit::ARGTYPE_I
|
|
||||||
#define _JS_U64_ARGTYPE nanojit::ARGTYPE_Q
|
|
||||||
#define _JS_U64_RETTYPE nanojit::ARGTYPE_Q
|
|
||||||
#define _JS_F64_ARGTYPE nanojit::ARGTYPE_D
|
|
||||||
#define _JS_F64_RETTYPE nanojit::ARGTYPE_D
|
|
||||||
#define _JS_PTR_ARGTYPE nanojit::ARGTYPE_P
|
|
||||||
#define _JS_PTR_RETTYPE nanojit::ARGTYPE_P
|
|
||||||
|
|
||||||
struct ClosureVarInfo;
|
|
||||||
|
|
||||||
/*
|
|
||||||
* Supported types for builtin functions.
|
|
||||||
*
|
|
||||||
* Types with -- for the two string fields are not permitted as argument types
|
|
||||||
* in JS_DEFINE_TRCINFO.
|
|
||||||
*
|
|
||||||
* There are three kinds of traceable-native error handling.
|
|
||||||
*
|
|
||||||
* - If a traceable native's return type ends with _FAIL, it always runs to
|
|
||||||
* completion. It can either succeed or fail with an error or exception;
|
|
||||||
* on success, it may or may not stay on trace. There may be side effects
|
|
||||||
* in any case. If the call succeeds but bails off trace, we resume in the
|
|
||||||
* interpreter at the next opcode.
|
|
||||||
*
|
|
||||||
* _FAIL builtins indicate failure or bailing off trace by setting bits in
|
|
||||||
* cx->interpState->builtinStatus.
|
|
||||||
*
|
|
||||||
* - If a traceable native's return type contains _RETRY, it can either
|
|
||||||
* succeed, fail with a JS exception, or tell the caller to bail off trace
|
|
||||||
* and retry the call from the interpreter. The last case happens if the
|
|
||||||
* builtin discovers that it can't do its job without examining the JS
|
|
||||||
* stack, reentering the interpreter, accessing properties of the global
|
|
||||||
* object, etc.
|
|
||||||
*
|
|
||||||
* The builtin must detect the need to retry before committing any side
|
|
||||||
* effects. If a builtin can't do this, it must use a _FAIL return type
|
|
||||||
* instead of _RETRY.
|
|
||||||
*
|
|
||||||
* _RETRY builtins indicate failure with a special return value that
|
|
||||||
* depends on the return type:
|
|
||||||
*
|
|
||||||
* BOOL_RETRY: JS_NEITHER
|
|
||||||
* INT32_RETRY: any negative value
|
|
||||||
* STRING_RETRY: NULL
|
|
||||||
* OBJECT_RETRY_NULL: NULL
|
|
||||||
*
|
|
||||||
* _RETRY function calls are faster than _FAIL calls. Each _RETRY call
|
|
||||||
* saves two writes to tm->bailExit and a read from state->builtinStatus.
|
|
||||||
*
|
|
||||||
* - All other traceable natives are infallible (e.g. Date.now, Math.log).
|
|
||||||
*
|
|
||||||
* Special builtins known to the tracer can have their own idiosyncratic
|
|
||||||
* error codes.
|
|
||||||
*
|
|
||||||
* When a traceable native returns a value indicating failure, we fall off
|
|
||||||
* trace. If an exception is pending, it is thrown; otherwise, we assume the
|
|
||||||
* builtin had no side effects and retry the current bytecode in the
|
|
||||||
* interpreter.
|
|
||||||
*
|
|
||||||
* So a builtin must not return a value indicating failure after causing side
|
|
||||||
* effects (such as reporting an error), without setting an exception pending.
|
|
||||||
* The operation would be retried, despite the first attempt's observable
|
|
||||||
* effects.
|
|
||||||
*/
|
|
||||||
#define _JS_CTYPE(ctype, size, pch, ach, flags) (ctype, size, pch, ach, flags)
|
|
||||||
|
|
||||||
#define _JS_CTYPE_CONTEXT _JS_CTYPE(JSContext *, _JS_PTR,"C", "", INFALLIBLE)
|
|
||||||
#define _JS_CTYPE_RUNTIME _JS_CTYPE(JSRuntime *, _JS_PTR,"R", "", INFALLIBLE)
|
|
||||||
#define _JS_CTYPE_MATHCACHE _JS_CTYPE(js::MathCache *, _JS_PTR,"M", "", INFALLIBLE)
|
|
||||||
#define _JS_CTYPE_THIS _JS_CTYPE(JSObject *, _JS_PTR,"T", "", INFALLIBLE)
|
|
||||||
#define _JS_CTYPE_THIS_DOUBLE _JS_CTYPE(jsdouble, _JS_F64,"D", "", INFALLIBLE)
|
|
||||||
#define _JS_CTYPE_THIS_STRING _JS_CTYPE(JSString *, _JS_PTR,"S", "", INFALLIBLE)
|
|
||||||
#define _JS_CTYPE_CALLEE _JS_CTYPE(JSObject *, _JS_PTR,"f", "", INFALLIBLE)
|
|
||||||
#define _JS_CTYPE_CALLEE_PROTOTYPE _JS_CTYPE(JSObject *, _JS_PTR,"p", "", INFALLIBLE)
|
|
||||||
#define _JS_CTYPE_FUNCTION _JS_CTYPE(JSFunction *, _JS_PTR, --, --, INFALLIBLE)
|
|
||||||
#define _JS_CTYPE_PC _JS_CTYPE(jsbytecode *, _JS_PTR,"P", "", INFALLIBLE)
|
|
||||||
#define _JS_CTYPE_VALUEPTR _JS_CTYPE(js::Value *, _JS_PTR, --, --, INFALLIBLE)
|
|
||||||
#define _JS_CTYPE_CVALUEPTR _JS_CTYPE(const js::Value *, _JS_PTR, --, --, INFALLIBLE)
|
|
||||||
#define _JS_CTYPE_JSID _JS_CTYPE(jsid, _JS_PTR, --, --, INFALLIBLE)
|
|
||||||
#define _JS_CTYPE_JSVAL _JS_CTYPE(js::Value, _JS_U64, --, --, INFALLIBLE)
|
|
||||||
#define _JS_CTYPE_BOOL _JS_CTYPE(JSBool, _JS_I32, "","i", INFALLIBLE)
|
|
||||||
#define _JS_CTYPE_BOOL_RETRY _JS_CTYPE(JSBool, _JS_I32, --, --, FAIL_NEITHER)
|
|
||||||
#define _JS_CTYPE_BOOL_FAIL _JS_CTYPE(JSBool, _JS_I32, --, --, FAIL_STATUS)
|
|
||||||
#define _JS_CTYPE_BOOLPTR _JS_CTYPE(JSBool *, _JS_PTR, --, --, INFALLIBLE)
|
|
||||||
#define _JS_CTYPE_INT32 _JS_CTYPE(int32, _JS_I32, "","i", INFALLIBLE)
|
|
||||||
#define _JS_CTYPE_INT32_RETRY _JS_CTYPE(int32, _JS_I32, --, --, FAIL_NEG)
|
|
||||||
#define _JS_CTYPE_INT32_FAIL _JS_CTYPE(int32, _JS_I32, --, --, FAIL_STATUS)
|
|
||||||
#define _JS_CTYPE_INT32PTR _JS_CTYPE(int32 *, _JS_PTR, --, --, INFALLIBLE)
|
|
||||||
#define _JS_CTYPE_UINT32 _JS_CTYPE(uint32, _JS_I32, "","i", INFALLIBLE)
|
|
||||||
#define _JS_CTYPE_UINT32_RETRY _JS_CTYPE(uint32, _JS_I32, --, --, FAIL_NEG)
|
|
||||||
#define _JS_CTYPE_UINT32_FAIL _JS_CTYPE(uint32, _JS_I32, --, --, FAIL_STATUS)
|
|
||||||
#define _JS_CTYPE_DOUBLE _JS_CTYPE(jsdouble, _JS_F64, "","d", INFALLIBLE)
|
|
||||||
#define _JS_CTYPE_DOUBLE_FAIL _JS_CTYPE(jsdouble, _JS_F64, --, --, FAIL_STATUS)
|
|
||||||
#define _JS_CTYPE_STRING _JS_CTYPE(JSString *, _JS_PTR, "","s", INFALLIBLE)
|
|
||||||
#define _JS_CTYPE_STRING_RETRY _JS_CTYPE(JSString *, _JS_PTR, --, --, FAIL_NULL)
|
|
||||||
#define _JS_CTYPE_STRING_FAIL _JS_CTYPE(JSString *, _JS_PTR, --, --, FAIL_STATUS)
|
|
||||||
#define _JS_CTYPE_STRING_OR_NULL_FAIL _JS_CTYPE(JSString *, _JS_PTR, --, --, FAIL_STATUS | \
|
|
||||||
JSTN_RETURN_NULLABLE_STR)
|
|
||||||
#define _JS_CTYPE_STRINGPTR _JS_CTYPE(JSString **, _JS_PTR, --, --, INFALLIBLE)
|
|
||||||
#define _JS_CTYPE_OBJECT _JS_CTYPE(JSObject *, _JS_PTR, "","o", INFALLIBLE)
|
|
||||||
#define _JS_CTYPE_OBJECT_RETRY _JS_CTYPE(JSObject *, _JS_PTR, --, --, FAIL_NULL)
|
|
||||||
#define _JS_CTYPE_OBJECT_FAIL _JS_CTYPE(JSObject *, _JS_PTR, --, --, FAIL_STATUS)
|
|
||||||
#define _JS_CTYPE_OBJECT_OR_NULL_FAIL _JS_CTYPE(JSObject *, _JS_PTR, --, --, FAIL_STATUS | \
|
|
||||||
JSTN_RETURN_NULLABLE_OBJ)
|
|
||||||
#define _JS_CTYPE_OBJECTPTR _JS_CTYPE(JSObject **, _JS_PTR, --, --, INFALLIBLE)
|
|
||||||
#define _JS_CTYPE_CONSTRUCTOR_RETRY _JS_CTYPE(JSObject *, _JS_PTR, --, --, FAIL_NULL | \
|
|
||||||
JSTN_CONSTRUCTOR)
|
|
||||||
#define _JS_CTYPE_REGEXP _JS_CTYPE(JSObject *, _JS_PTR, "","r", INFALLIBLE)
|
|
||||||
#define _JS_CTYPE_SHAPE _JS_CTYPE(js::Shape *, _JS_PTR, --, --, INFALLIBLE)
|
|
||||||
#define _JS_CTYPE_TRACERSTATE _JS_CTYPE(TracerState *, _JS_PTR, --, --, INFALLIBLE)
|
|
||||||
#define _JS_CTYPE_FRAGMENT _JS_CTYPE(nanojit::Fragment *, _JS_PTR, --, --, INFALLIBLE)
|
|
||||||
#define _JS_CTYPE_CLASS _JS_CTYPE(js::Class *, _JS_PTR, --, --, INFALLIBLE)
|
|
||||||
#define _JS_CTYPE_DOUBLEPTR _JS_CTYPE(double *, _JS_PTR, --, --, INFALLIBLE)
|
|
||||||
#define _JS_CTYPE_CHARPTR _JS_CTYPE(char *, _JS_PTR, --, --, INFALLIBLE)
|
|
||||||
#define _JS_CTYPE_CVIPTR _JS_CTYPE(const ClosureVarInfo *, _JS_PTR, --, --, INFALLIBLE)
|
|
||||||
#define _JS_CTYPE_FRAMEINFO _JS_CTYPE(FrameInfo *, _JS_PTR, --, --, INFALLIBLE)
|
|
||||||
#define _JS_CTYPE_UINTN _JS_CTYPE(uintN, _JS_PTR, --, --, INFALLIBLE)
|
|
||||||
|
|
||||||
/*
|
|
||||||
* The "VALUE" type is used to indicate that a native takes a js::Value
|
|
||||||
* parameter by value. Unfortunately, for technical reasons, we can't simply
|
|
||||||
* have the parameter type be js::Value. Furthermore, the right thing to pass
|
|
||||||
* differs based on word size. Thus, a native that declares a parameter of type
|
|
||||||
* VALUE should have the corresponding argument type be:
|
|
||||||
* - on 32-bit: const Value*
|
|
||||||
* - on 64-bit: jsval (which is a uint64)
|
|
||||||
*
|
|
||||||
* To write code that just does the right thing, use the pattern:
|
|
||||||
* void foo(js::ValueArgType arg) {
|
|
||||||
* const js::Value &v = js::ValueArgToConstRef(arg);
|
|
||||||
*/
|
|
||||||
#if JS_BITS_PER_WORD == 32
|
|
||||||
# define _JS_CTYPE_VALUE _JS_CTYPE(js::ValueArgType, _JS_PTR, "","v", INFALLIBLE)
|
|
||||||
#elif JS_BITS_PER_WORD == 64
|
|
||||||
# define _JS_CTYPE_VALUE _JS_CTYPE(js::ValueArgType, _JS_U64, "","v", INFALLIBLE)
|
|
||||||
#endif
|
|
||||||
|
|
||||||
namespace js {
|
|
||||||
#if JS_BITS_PER_WORD == 32
|
|
||||||
typedef const js::Value *ValueArgType;
|
|
||||||
|
|
||||||
static JS_ALWAYS_INLINE const js::Value &
|
|
||||||
ValueArgToConstRef(const js::Value *arg)
|
|
||||||
{
|
|
||||||
return *arg;
|
|
||||||
}
|
|
||||||
#elif JS_BITS_PER_WORD == 64
|
|
||||||
typedef js::Value ValueArgType;
|
|
||||||
|
|
||||||
static JS_ALWAYS_INLINE const Value &
|
|
||||||
ValueArgToConstRef(const Value &v)
|
|
||||||
{
|
|
||||||
return v;
|
|
||||||
}
|
|
||||||
#endif
|
|
||||||
} /* namespace js */
|
|
||||||
|
|
||||||
#define _JS_EXPAND(tokens) tokens
|
|
||||||
|
|
||||||
#define _JS_CTYPE_TYPE2(t,s,p,a,f) t
|
|
||||||
#define _JS_CTYPE_TYPE(tyname) _JS_EXPAND(_JS_CTYPE_TYPE2 _JS_CTYPE_##tyname)
|
|
||||||
#define _JS_CTYPE_RETTYPE2(t,s,p,a,f) s##_RETTYPE
|
|
||||||
#define _JS_CTYPE_RETTYPE(tyname) _JS_EXPAND(_JS_CTYPE_RETTYPE2 _JS_CTYPE_##tyname)
|
|
||||||
#define _JS_CTYPE_ARGTYPE2(t,s,p,a,f) s##_ARGTYPE
|
|
||||||
#define _JS_CTYPE_ARGTYPE(tyname) _JS_EXPAND(_JS_CTYPE_ARGTYPE2 _JS_CTYPE_##tyname)
|
|
||||||
#define _JS_CTYPE_PCH2(t,s,p,a,f) p
|
|
||||||
#define _JS_CTYPE_PCH(tyname) _JS_EXPAND(_JS_CTYPE_PCH2 _JS_CTYPE_##tyname)
|
|
||||||
#define _JS_CTYPE_ACH2(t,s,p,a,f) a
|
|
||||||
#define _JS_CTYPE_ACH(tyname) _JS_EXPAND(_JS_CTYPE_ACH2 _JS_CTYPE_##tyname)
|
|
||||||
#define _JS_CTYPE_FLAGS2(t,s,p,a,f) f
|
|
||||||
#define _JS_CTYPE_FLAGS(tyname) _JS_EXPAND(_JS_CTYPE_FLAGS2 _JS_CTYPE_##tyname)
|
|
||||||
|
|
||||||
#define _JS_static_TN(t) static t
|
|
||||||
#define _JS_static_CI static
|
|
||||||
#define _JS_extern_TN(t) extern t
|
|
||||||
#define _JS_extern_CI
|
|
||||||
#define _JS_FRIEND_TN(t) extern JS_FRIEND_API(t)
|
|
||||||
#define _JS_FRIEND_CI
|
|
||||||
#define _JS_TN_LINKAGE(linkage, t) _JS_##linkage##_TN(t)
|
|
||||||
#define _JS_CI_LINKAGE(linkage) _JS_##linkage##_CI
|
|
||||||
|
|
||||||
#define _JS_CALLINFO(name) name##_ci
|
|
||||||
|
|
||||||
#if defined(JS_NO_FASTCALL) && defined(NANOJIT_IA32)
|
|
||||||
#define _JS_DEFINE_CALLINFO(linkage, name, crtype, cargtypes, argtypes, isPure, storeAccSet) \
|
|
||||||
_JS_TN_LINKAGE(linkage, crtype) name cargtypes; \
|
|
||||||
_JS_CI_LINKAGE(linkage) const nanojit::CallInfo _JS_CALLINFO(name) = \
|
|
||||||
{ (intptr_t) &name, argtypes, nanojit::ABI_CDECL, isPure, storeAccSet _JS_CI_NAME(name) };\
|
|
||||||
JS_STATIC_ASSERT_IF(isPure, (storeAccSet) == nanojit::ACCSET_NONE);
|
|
||||||
|
|
||||||
#else
|
|
||||||
#define _JS_DEFINE_CALLINFO(linkage, name, crtype, cargtypes, argtypes, isPure, storeAccSet) \
|
|
||||||
_JS_TN_LINKAGE(linkage, crtype) FASTCALL name cargtypes; \
|
|
||||||
_JS_CI_LINKAGE(linkage) const nanojit::CallInfo _JS_CALLINFO(name) = \
|
|
||||||
{ (uintptr_t) &name, argtypes, nanojit::ABI_FASTCALL, isPure, storeAccSet _JS_CI_NAME(name) }; \
|
|
||||||
JS_STATIC_ASSERT_IF(isPure, (storeAccSet) == nanojit::ACCSET_NONE);
|
|
||||||
#endif
|
|
||||||
|
|
||||||
/*
|
|
||||||
* This macro is used for builtin functions that can be called from JITted
|
|
||||||
* code. It declares a C function named <op> and a CallInfo struct named
|
|
||||||
* <op>_ci so the tracer can call it. The <N> in JS_DEFINE_CALLINFO_<N> is
|
|
||||||
* the number of arguments the builtin takes. Builtins with no arguments
|
|
||||||
* are not supported. Using a macro is clunky but ensures that the types
|
|
||||||
* for each C function matches those for the corresponding CallInfo struct;
|
|
||||||
* mismatched types can cause subtle problems.
|
|
||||||
*
|
|
||||||
* The macro arguments are:
|
|
||||||
*
|
|
||||||
* - The linkage for the function and the associated CallInfo global. It
|
|
||||||
* can be extern, static, or FRIEND, which specifies JS_FRIEND_API linkage
|
|
||||||
* for the function.
|
|
||||||
*
|
|
||||||
* - The return type. This identifier must name one of the _JS_TYPEINFO_*
|
|
||||||
* macros defined in jsbuiltins.h.
|
|
||||||
*
|
|
||||||
* - The builtin name.
|
|
||||||
*
|
|
||||||
* - The parameter types.
|
|
||||||
*
|
|
||||||
* - The isPure flag. Set to 1 if:
|
|
||||||
* (a) the function's return value is determined solely by its arguments
|
|
||||||
* (ie. no hidden state, no implicit inputs used such as global
|
|
||||||
* variables or the result of an I/O operation); and
|
|
||||||
* (b) the function causes no observable side-effects (ie. no writes to
|
|
||||||
* global variables, no I/O output).
|
|
||||||
* Multiple calls to a pure function can be merged during CSE.
|
|
||||||
*
|
|
||||||
* - The storeAccSet. This indicates which memory access regions the function
|
|
||||||
* accesses. It must be ACCSET_NONE if the function is pure; use
|
|
||||||
* ACCSET_STORE_ANY if you're not sure. Used to determine if each call site
|
|
||||||
* of the function aliases any loads.
|
|
||||||
*/
|
|
||||||
#define JS_DEFINE_CALLINFO_1(linkage, rt, op, at0, isPure, storeAccSet) \
|
|
||||||
_JS_DEFINE_CALLINFO(linkage, op, \
|
|
||||||
_JS_CTYPE_TYPE(rt), \
|
|
||||||
(_JS_CTYPE_TYPE(at0)), \
|
|
||||||
nanojit::CallInfo::typeSig1(_JS_CTYPE_RETTYPE(rt), \
|
|
||||||
_JS_CTYPE_ARGTYPE(at0)), \
|
|
||||||
isPure, storeAccSet)
|
|
||||||
#define JS_DEFINE_CALLINFO_2(linkage, rt, op, at0, at1, isPure, storeAccSet) \
|
|
||||||
_JS_DEFINE_CALLINFO(linkage, op, \
|
|
||||||
_JS_CTYPE_TYPE(rt), \
|
|
||||||
(_JS_CTYPE_TYPE(at0), \
|
|
||||||
_JS_CTYPE_TYPE(at1)), \
|
|
||||||
nanojit::CallInfo::typeSig2(_JS_CTYPE_RETTYPE(rt), \
|
|
||||||
_JS_CTYPE_ARGTYPE(at0), \
|
|
||||||
_JS_CTYPE_ARGTYPE(at1)), \
|
|
||||||
isPure, storeAccSet)
|
|
||||||
#define JS_DEFINE_CALLINFO_3(linkage, rt, op, at0, at1, at2, isPure, storeAccSet) \
|
|
||||||
_JS_DEFINE_CALLINFO(linkage, op, \
|
|
||||||
_JS_CTYPE_TYPE(rt), \
|
|
||||||
(_JS_CTYPE_TYPE(at0), \
|
|
||||||
_JS_CTYPE_TYPE(at1), \
|
|
||||||
_JS_CTYPE_TYPE(at2)), \
|
|
||||||
nanojit::CallInfo::typeSig3(_JS_CTYPE_RETTYPE(rt), \
|
|
||||||
_JS_CTYPE_ARGTYPE(at0), \
|
|
||||||
_JS_CTYPE_ARGTYPE(at1), \
|
|
||||||
_JS_CTYPE_ARGTYPE(at2)), \
|
|
||||||
isPure, storeAccSet)
|
|
||||||
#define JS_DEFINE_CALLINFO_4(linkage, rt, op, at0, at1, at2, at3, isPure, storeAccSet) \
|
|
||||||
_JS_DEFINE_CALLINFO(linkage, op, \
|
|
||||||
_JS_CTYPE_TYPE(rt), \
|
|
||||||
(_JS_CTYPE_TYPE(at0), \
|
|
||||||
_JS_CTYPE_TYPE(at1), \
|
|
||||||
_JS_CTYPE_TYPE(at2), \
|
|
||||||
_JS_CTYPE_TYPE(at3)), \
|
|
||||||
nanojit::CallInfo::typeSig4(_JS_CTYPE_RETTYPE(rt), \
|
|
||||||
_JS_CTYPE_ARGTYPE(at0), \
|
|
||||||
_JS_CTYPE_ARGTYPE(at1), \
|
|
||||||
_JS_CTYPE_ARGTYPE(at2), \
|
|
||||||
_JS_CTYPE_ARGTYPE(at3)), \
|
|
||||||
isPure, storeAccSet)
|
|
||||||
#define JS_DEFINE_CALLINFO_5(linkage, rt, op, at0, at1, at2, at3, at4, isPure, storeAccSet) \
|
|
||||||
_JS_DEFINE_CALLINFO(linkage, op, \
|
|
||||||
_JS_CTYPE_TYPE(rt), \
|
|
||||||
(_JS_CTYPE_TYPE(at0), \
|
|
||||||
_JS_CTYPE_TYPE(at1), \
|
|
||||||
_JS_CTYPE_TYPE(at2), \
|
|
||||||
_JS_CTYPE_TYPE(at3), \
|
|
||||||
_JS_CTYPE_TYPE(at4)), \
|
|
||||||
nanojit::CallInfo::typeSig5(_JS_CTYPE_RETTYPE(rt), \
|
|
||||||
_JS_CTYPE_ARGTYPE(at0), \
|
|
||||||
_JS_CTYPE_ARGTYPE(at1), \
|
|
||||||
_JS_CTYPE_ARGTYPE(at2), \
|
|
||||||
_JS_CTYPE_ARGTYPE(at3), \
|
|
||||||
_JS_CTYPE_ARGTYPE(at4)), \
|
|
||||||
isPure, storeAccSet)
|
|
||||||
#define JS_DEFINE_CALLINFO_6(linkage, rt, op, at0, at1, at2, at3, at4, at5, isPure, storeAccSet) \
|
|
||||||
_JS_DEFINE_CALLINFO(linkage, op, \
|
|
||||||
_JS_CTYPE_TYPE(rt), \
|
|
||||||
(_JS_CTYPE_TYPE(at0), \
|
|
||||||
_JS_CTYPE_TYPE(at1), \
|
|
||||||
_JS_CTYPE_TYPE(at2), \
|
|
||||||
_JS_CTYPE_TYPE(at3), \
|
|
||||||
_JS_CTYPE_TYPE(at4), \
|
|
||||||
_JS_CTYPE_TYPE(at5)), \
|
|
||||||
nanojit::CallInfo::typeSig6(_JS_CTYPE_RETTYPE(rt), \
|
|
||||||
_JS_CTYPE_ARGTYPE(at0), \
|
|
||||||
_JS_CTYPE_ARGTYPE(at1), \
|
|
||||||
_JS_CTYPE_ARGTYPE(at2), \
|
|
||||||
_JS_CTYPE_ARGTYPE(at3), \
|
|
||||||
_JS_CTYPE_ARGTYPE(at4), \
|
|
||||||
_JS_CTYPE_ARGTYPE(at5)), \
|
|
||||||
isPure, storeAccSet)
|
|
||||||
#define JS_DEFINE_CALLINFO_7(linkage, rt, op, at0, at1, at2, at3, at4, at5, at6, isPure, \
|
|
||||||
storeAccSet) \
|
|
||||||
_JS_DEFINE_CALLINFO(linkage, op, \
|
|
||||||
_JS_CTYPE_TYPE(rt), \
|
|
||||||
(_JS_CTYPE_TYPE(at0), \
|
|
||||||
_JS_CTYPE_TYPE(at1), \
|
|
||||||
_JS_CTYPE_TYPE(at2), \
|
|
||||||
_JS_CTYPE_TYPE(at3), \
|
|
||||||
_JS_CTYPE_TYPE(at4), \
|
|
||||||
_JS_CTYPE_TYPE(at5), \
|
|
||||||
_JS_CTYPE_TYPE(at6)), \
|
|
||||||
nanojit::CallInfo::typeSig7(_JS_CTYPE_RETTYPE(rt), \
|
|
||||||
_JS_CTYPE_ARGTYPE(at0), \
|
|
||||||
_JS_CTYPE_ARGTYPE(at1), \
|
|
||||||
_JS_CTYPE_ARGTYPE(at2), \
|
|
||||||
_JS_CTYPE_ARGTYPE(at3), \
|
|
||||||
_JS_CTYPE_ARGTYPE(at4), \
|
|
||||||
_JS_CTYPE_ARGTYPE(at5), \
|
|
||||||
_JS_CTYPE_ARGTYPE(at6)), \
|
|
||||||
isPure, storeAccSet)
|
|
||||||
#define JS_DEFINE_CALLINFO_8(linkage, rt, op, at0, at1, at2, at3, at4, at5, at6, at7, isPure, \
|
|
||||||
storeAccSet) \
|
|
||||||
_JS_DEFINE_CALLINFO(linkage, op, \
|
|
||||||
_JS_CTYPE_TYPE(rt), \
|
|
||||||
(_JS_CTYPE_TYPE(at0), \
|
|
||||||
_JS_CTYPE_TYPE(at1), \
|
|
||||||
_JS_CTYPE_TYPE(at2), \
|
|
||||||
_JS_CTYPE_TYPE(at3), \
|
|
||||||
_JS_CTYPE_TYPE(at4), \
|
|
||||||
_JS_CTYPE_TYPE(at5), \
|
|
||||||
_JS_CTYPE_TYPE(at6), \
|
|
||||||
_JS_CTYPE_TYPE(at7)), \
|
|
||||||
nanojit::CallInfo::typeSig8(_JS_CTYPE_RETTYPE(rt), \
|
|
||||||
_JS_CTYPE_ARGTYPE(at0), \
|
|
||||||
_JS_CTYPE_ARGTYPE(at1), \
|
|
||||||
_JS_CTYPE_ARGTYPE(at2), \
|
|
||||||
_JS_CTYPE_ARGTYPE(at3), \
|
|
||||||
_JS_CTYPE_ARGTYPE(at4), \
|
|
||||||
_JS_CTYPE_ARGTYPE(at5), \
|
|
||||||
_JS_CTYPE_ARGTYPE(at6), \
|
|
||||||
_JS_CTYPE_ARGTYPE(at7)), \
|
|
||||||
isPure, storeAccSet)
|
|
||||||
|
|
||||||
#define JS_DECLARE_CALLINFO(name) extern const nanojit::CallInfo _JS_CALLINFO(name);
|
|
||||||
|
|
||||||
#define _JS_TN_INIT_HELPER_n(n, args) _JS_TN_INIT_HELPER_##n args
|
|
||||||
|
|
||||||
#define _JS_TN_INIT_HELPER_1(linkage, rt, op, at0, isPure, storeAccSet) \
|
|
||||||
&_JS_CALLINFO(op), \
|
|
||||||
_JS_CTYPE_PCH(at0), \
|
|
||||||
_JS_CTYPE_ACH(at0), \
|
|
||||||
_JS_CTYPE_FLAGS(rt)
|
|
||||||
|
|
||||||
#define _JS_TN_INIT_HELPER_2(linkage, rt, op, at0, at1, isPure, storeAccSet) \
|
|
||||||
&_JS_CALLINFO(op), \
|
|
||||||
_JS_CTYPE_PCH(at1) _JS_CTYPE_PCH(at0), \
|
|
||||||
_JS_CTYPE_ACH(at1) _JS_CTYPE_ACH(at0), \
|
|
||||||
_JS_CTYPE_FLAGS(rt)
|
|
||||||
|
|
||||||
#define _JS_TN_INIT_HELPER_3(linkage, rt, op, at0, at1, at2, isPure, storeAccSet) \
|
|
||||||
&_JS_CALLINFO(op), \
|
|
||||||
_JS_CTYPE_PCH(at2) _JS_CTYPE_PCH(at1) _JS_CTYPE_PCH(at0), \
|
|
||||||
_JS_CTYPE_ACH(at2) _JS_CTYPE_ACH(at1) _JS_CTYPE_ACH(at0), \
|
|
||||||
_JS_CTYPE_FLAGS(rt)
|
|
||||||
|
|
||||||
#define _JS_TN_INIT_HELPER_4(linkage, rt, op, at0, at1, at2, at3, isPure, storeAccSet) \
|
|
||||||
&_JS_CALLINFO(op), \
|
|
||||||
_JS_CTYPE_PCH(at3) _JS_CTYPE_PCH(at2) _JS_CTYPE_PCH(at1) _JS_CTYPE_PCH(at0), \
|
|
||||||
_JS_CTYPE_ACH(at3) _JS_CTYPE_ACH(at2) _JS_CTYPE_ACH(at1) _JS_CTYPE_ACH(at0), \
|
|
||||||
_JS_CTYPE_FLAGS(rt)
|
|
||||||
|
|
||||||
#define _JS_TN_INIT_HELPER_5(linkage, rt, op, at0, at1, at2, at3, at4, isPure, storeAccSet) \
|
|
||||||
&_JS_CALLINFO(op), \
|
|
||||||
_JS_CTYPE_PCH(at4) _JS_CTYPE_PCH(at3) _JS_CTYPE_PCH(at2) _JS_CTYPE_PCH(at1) \
|
|
||||||
_JS_CTYPE_PCH(at0), \
|
|
||||||
_JS_CTYPE_ACH(at4) _JS_CTYPE_ACH(at3) _JS_CTYPE_ACH(at2) _JS_CTYPE_ACH(at1) \
|
|
||||||
_JS_CTYPE_ACH(at0), \
|
|
||||||
_JS_CTYPE_FLAGS(rt)
|
|
||||||
|
|
||||||
#define _JS_TN_INIT_HELPER_6(linkage, rt, op, at0, at1, at2, at3, at4, at5, isPure, storeAccSet) \
|
|
||||||
&_JS_CALLINFO(op), \
|
|
||||||
_JS_CTYPE_PCH(at5) _JS_CTYPE_PCH(at4) _JS_CTYPE_PCH(at3) _JS_CTYPE_PCH(at2) \
|
|
||||||
_JS_CTYPE_PCH(at1) _JS_CTYPE_PCH(at0), \
|
|
||||||
_JS_CTYPE_ACH(at5) _JS_CTYPE_ACH(at4) _JS_CTYPE_ACH(at3) _JS_CTYPE_ACH(at2) \
|
|
||||||
_JS_CTYPE_ACH(at1) _JS_CTYPE_ACH(at0), \
|
|
||||||
_JS_CTYPE_FLAGS(rt)
|
|
||||||
|
|
||||||
#define _JS_TN_INIT_HELPER_7(linkage, rt, op, at0, at1, at2, at3, at4, at5, at6, isPure, storeAccSet) \
|
|
||||||
&_JS_CALLINFO(op), \
|
|
||||||
_JS_CTYPE_PCH(at6) _JS_CTYPE_PCH(at5) _JS_CTYPE_PCH(at4) _JS_CTYPE_PCH(at3) \
|
|
||||||
_JS_CTYPE_PCH(at2) _JS_CTYPE_PCH(at1) _JS_CTYPE_PCH(at0), \
|
|
||||||
_JS_CTYPE_ACH(at6) _JS_CTYPE_ACH(at5) _JS_CTYPE_ACH(at4) _JS_CTYPE_ACH(at3) \
|
|
||||||
_JS_CTYPE_ACH(at2) _JS_CTYPE_ACH(at1) _JS_CTYPE_ACH(at0), \
|
|
||||||
_JS_CTYPE_FLAGS(rt)
|
|
||||||
|
|
||||||
#define _JS_TN_INIT_HELPER_8(linkage, rt, op, at0, at1, at2, at3, at4, at5, at6, at7, isPure, storeAccSet) \
|
|
||||||
&_JS_CALLINFO(op), \
|
|
||||||
_JS_CTYPE_PCH(at7) _JS_CTYPE_PCH(at6) _JS_CTYPE_PCH(at5) _JS_CTYPE_PCH(at4) \
|
|
||||||
_JS_CTYPE_PCH(at3) _JS_CTYPE_PCH(at2) _JS_CTYPE_PCH(at1) _JS_CTYPE_PCH(at0), \
|
|
||||||
_JS_CTYPE_ACH(at7) _JS_CTYPE_ACH(at6) _JS_CTYPE_ACH(at5) _JS_CTYPE_ACH(at4) \
|
|
||||||
_JS_CTYPE_ACH(at3) _JS_CTYPE_ACH(at2) _JS_CTYPE_ACH(at1) _JS_CTYPE_ACH(at0), \
|
|
||||||
_JS_CTYPE_FLAGS(rt)
|
|
||||||
|
|
||||||
#define JS_DEFINE_TRCINFO_1(name, tn0) \
|
|
||||||
_JS_DEFINE_CALLINFO_n tn0 \
|
|
||||||
JSSpecializedNative name##_sns[] = { \
|
|
||||||
{ _JS_TN_INIT_HELPER_n tn0 } \
|
|
||||||
}; \
|
|
||||||
JSNativeTraceInfo name##_trcinfo = { name, name##_sns };
|
|
||||||
|
|
||||||
#define JS_DEFINE_TRCINFO_2(name, tn0, tn1) \
|
|
||||||
_JS_DEFINE_CALLINFO_n tn0 \
|
|
||||||
_JS_DEFINE_CALLINFO_n tn1 \
|
|
||||||
JSSpecializedNative name##_sns[] = { \
|
|
||||||
{ _JS_TN_INIT_HELPER_n tn0 | JSTN_MORE }, \
|
|
||||||
{ _JS_TN_INIT_HELPER_n tn1 } \
|
|
||||||
}; \
|
|
||||||
JSNativeTraceInfo name##_trcinfo = { name, name##_sns };
|
|
||||||
|
|
||||||
#define JS_DEFINE_TRCINFO_3(name, tn0, tn1, tn2) \
|
|
||||||
_JS_DEFINE_CALLINFO_n tn0 \
|
|
||||||
_JS_DEFINE_CALLINFO_n tn1 \
|
|
||||||
_JS_DEFINE_CALLINFO_n tn2 \
|
|
||||||
JSSpecializedNative name##_sns[] = { \
|
|
||||||
{ _JS_TN_INIT_HELPER_n tn0 | JSTN_MORE }, \
|
|
||||||
{ _JS_TN_INIT_HELPER_n tn1 | JSTN_MORE }, \
|
|
||||||
{ _JS_TN_INIT_HELPER_n tn2 } \
|
|
||||||
}; \
|
|
||||||
JSNativeTraceInfo name##_trcinfo = { name, name##_sns };
|
|
||||||
|
|
||||||
#define JS_DEFINE_TRCINFO_4(name, tn0, tn1, tn2, tn3) \
|
|
||||||
_JS_DEFINE_CALLINFO_n tn0 \
|
|
||||||
_JS_DEFINE_CALLINFO_n tn1 \
|
|
||||||
_JS_DEFINE_CALLINFO_n tn2 \
|
|
||||||
_JS_DEFINE_CALLINFO_n tn3 \
|
|
||||||
JSSpecializedNative name##_sns[] = { \
|
|
||||||
{ _JS_TN_INIT_HELPER_n tn0 | JSTN_MORE }, \
|
|
||||||
{ _JS_TN_INIT_HELPER_n tn1 | JSTN_MORE }, \
|
|
||||||
{ _JS_TN_INIT_HELPER_n tn2 | JSTN_MORE }, \
|
|
||||||
{ _JS_TN_INIT_HELPER_n tn3 } \
|
|
||||||
}; \
|
|
||||||
JSNativeTraceInfo name##_trcinfo = { name, name##_sns };
|
|
||||||
|
|
||||||
#define _JS_DEFINE_CALLINFO_n(n, args) JS_DEFINE_CALLINFO_##n args
|
|
||||||
|
|
||||||
jsdouble FASTCALL
|
|
||||||
js_StringToNumber(JSContext* cx, JSString* str, JSBool *ok);
|
|
||||||
|
|
||||||
/* Extern version of SetBuiltinError. */
|
|
||||||
extern JS_FRIEND_API(void)
|
|
||||||
js_SetTraceableNativeFailed(JSContext *cx);
|
|
||||||
|
|
||||||
extern jsdouble FASTCALL
|
|
||||||
js_dmod(jsdouble a, jsdouble b);
|
|
||||||
|
|
||||||
#else
|
|
||||||
|
|
||||||
#define JS_DEFINE_CALLINFO_1(linkage, rt, op, at0, isPure, storeAccSet)
|
|
||||||
#define JS_DEFINE_CALLINFO_2(linkage, rt, op, at0, at1, isPure, storeAccSet)
|
|
||||||
#define JS_DEFINE_CALLINFO_3(linkage, rt, op, at0, at1, at2, isPure, storeAccSet)
|
|
||||||
#define JS_DEFINE_CALLINFO_4(linkage, rt, op, at0, at1, at2, at3, isPure, storeAccSet)
|
|
||||||
#define JS_DEFINE_CALLINFO_5(linkage, rt, op, at0, at1, at2, at3, at4, isPure, storeAccSet)
|
|
||||||
#define JS_DEFINE_CALLINFO_6(linkage, rt, op, at0, at1, at2, at3, at4, at5, isPure, storeAccSet)
|
|
||||||
#define JS_DEFINE_CALLINFO_7(linkage, rt, op, at0, at1, at2, at3, at4, at5, at6, isPure, storeAccSet)
|
|
||||||
#define JS_DEFINE_CALLINFO_8(linkage, rt, op, at0, at1, at2, at3, at4, at5, at6, at7, isPure, storeAccSet)
|
|
||||||
#define JS_DECLARE_CALLINFO(name)
|
|
||||||
#define JS_DEFINE_TRCINFO_1(name, tn0)
|
|
||||||
#define JS_DEFINE_TRCINFO_2(name, tn0, tn1)
|
|
||||||
#define JS_DEFINE_TRCINFO_3(name, tn0, tn1, tn2)
|
|
||||||
#define JS_DEFINE_TRCINFO_4(name, tn0, tn1, tn2, tn3)
|
|
||||||
|
|
||||||
#endif /* !JS_TRACER */
|
|
||||||
|
|
||||||
/* Defined in jsarray.cpp. */
|
|
||||||
namespace js {
|
|
||||||
JS_DECLARE_CALLINFO(NewDenseEmptyArray)
|
|
||||||
JS_DECLARE_CALLINFO(NewDenseAllocatedArray)
|
|
||||||
JS_DECLARE_CALLINFO(NewDenseUnallocatedArray)
|
|
||||||
JS_DECLARE_CALLINFO(NewDenseAllocatedEmptyArray)
|
|
||||||
}
|
|
||||||
JS_DECLARE_CALLINFO(js_NewbornArrayPush_tn)
|
|
||||||
JS_DECLARE_CALLINFO(js_EnsureDenseArrayCapacity)
|
|
||||||
|
|
||||||
/* Defined in jsbuiltins.cpp. */
|
|
||||||
JS_DECLARE_CALLINFO(js_UnboxNumberAsDouble)
|
|
||||||
JS_DECLARE_CALLINFO(js_UnboxNumberAsInt32)
|
|
||||||
JS_DECLARE_CALLINFO(js_dmod)
|
|
||||||
JS_DECLARE_CALLINFO(js_imod)
|
|
||||||
JS_DECLARE_CALLINFO(js_DoubleToInt32)
|
|
||||||
JS_DECLARE_CALLINFO(js_DoubleToUint32)
|
|
||||||
JS_DECLARE_CALLINFO(js_StringToNumber)
|
|
||||||
JS_DECLARE_CALLINFO(js_StringToInt32)
|
|
||||||
JS_DECLARE_CALLINFO(js_AddProperty)
|
|
||||||
JS_DECLARE_CALLINFO(js_AddAtomProperty)
|
|
||||||
JS_DECLARE_CALLINFO(js_HasNamedProperty)
|
|
||||||
JS_DECLARE_CALLINFO(js_HasNamedPropertyInt32)
|
|
||||||
JS_DECLARE_CALLINFO(js_TypeOfObject)
|
|
||||||
JS_DECLARE_CALLINFO(js_BooleanIntToString)
|
|
||||||
JS_DECLARE_CALLINFO(js_NewNullClosure)
|
|
||||||
|
|
||||||
/* Defined in jsfun.cpp. */
|
|
||||||
JS_DECLARE_CALLINFO(js_AllocFlatClosure)
|
|
||||||
JS_DECLARE_CALLINFO(js_PutArgumentsOnTrace)
|
|
||||||
JS_DECLARE_CALLINFO(js_PutCallObjectOnTrace)
|
|
||||||
JS_DECLARE_CALLINFO(js_SetCallVar)
|
|
||||||
JS_DECLARE_CALLINFO(js_SetCallArg)
|
|
||||||
JS_DECLARE_CALLINFO(js_CloneFunctionObject)
|
|
||||||
JS_DECLARE_CALLINFO(js_CreateCallObjectOnTrace)
|
|
||||||
JS_DECLARE_CALLINFO(js_NewArgumentsOnTrace)
|
|
||||||
|
|
||||||
/* Defined in jsnum.cpp. */
|
|
||||||
JS_DECLARE_CALLINFO(js_NumberToString)
|
|
||||||
|
|
||||||
/* Defined in jsobj.cpp. */
|
|
||||||
JS_DECLARE_CALLINFO(js_Object_tn)
|
|
||||||
JS_DECLARE_CALLINFO(js_CreateThisFromTrace)
|
|
||||||
JS_DECLARE_CALLINFO(js_InitializerObject)
|
|
||||||
|
|
||||||
/* Defined in vm/RegExpObject.cpp. */
|
|
||||||
JS_DECLARE_CALLINFO(js_CloneRegExpObject)
|
|
||||||
|
|
||||||
/* Defined in jsstr.cpp. */
|
|
||||||
JS_DECLARE_CALLINFO(js_String_tn)
|
|
||||||
JS_DECLARE_CALLINFO(js_CompareStringsOnTrace)
|
|
||||||
JS_DECLARE_CALLINFO(js_ConcatStrings)
|
|
||||||
JS_DECLARE_CALLINFO(js_EqualStringsOnTrace)
|
|
||||||
JS_DECLARE_CALLINFO(js_FlattenOnTrace)
|
|
||||||
|
|
||||||
/* Defined in jstypedarray.cpp. */
|
|
||||||
JS_DECLARE_CALLINFO(js_TypedArray_uint8_clamp_double)
|
|
||||||
|
|
||||||
#endif /* jsbuiltins_h___ */
|
|
@ -80,7 +80,6 @@
|
|||||||
#include "jsscope.h"
|
#include "jsscope.h"
|
||||||
#include "jsscript.h"
|
#include "jsscript.h"
|
||||||
#include "jsstr.h"
|
#include "jsstr.h"
|
||||||
#include "jstracer.h"
|
|
||||||
|
|
||||||
#ifdef JS_METHODJIT
|
#ifdef JS_METHODJIT
|
||||||
# include "assembler/assembler/MacroAssembler.h"
|
# include "assembler/assembler/MacroAssembler.h"
|
||||||
@ -104,12 +103,6 @@ ThreadData::ThreadData(JSRuntime *rt)
|
|||||||
interruptFlags(0),
|
interruptFlags(0),
|
||||||
#ifdef JS_THREADSAFE
|
#ifdef JS_THREADSAFE
|
||||||
requestDepth(0),
|
requestDepth(0),
|
||||||
#endif
|
|
||||||
#ifdef JS_TRACER
|
|
||||||
onTraceCompartment(NULL),
|
|
||||||
recordingCompartment(NULL),
|
|
||||||
profilingCompartment(NULL),
|
|
||||||
maxCodeCacheBytes(DEFAULT_JIT_CACHE_SIZE),
|
|
||||||
#endif
|
#endif
|
||||||
waiveGCQuota(false),
|
waiveGCQuota(false),
|
||||||
tempLifoAlloc(TEMP_LIFO_ALLOC_PRIMARY_CHUNK_SIZE),
|
tempLifoAlloc(TEMP_LIFO_ALLOC_PRIMARY_CHUNK_SIZE),
|
||||||
@ -220,13 +213,6 @@ ThreadData::purgeRegExpPrivateCache()
|
|||||||
JSScript *
|
JSScript *
|
||||||
js_GetCurrentScript(JSContext *cx)
|
js_GetCurrentScript(JSContext *cx)
|
||||||
{
|
{
|
||||||
#ifdef JS_TRACER
|
|
||||||
VOUCH_DOES_NOT_REQUIRE_STACK();
|
|
||||||
if (JS_ON_TRACE(cx)) {
|
|
||||||
VMSideExit *bailExit = JS_TRACE_MONITOR_ON_TRACE(cx)->bailExit;
|
|
||||||
return bailExit ? bailExit->script : NULL;
|
|
||||||
}
|
|
||||||
#endif
|
|
||||||
return cx->hasfp() ? cx->fp()->maybeScript() : NULL;
|
return cx->hasfp() ? cx->fp()->maybeScript() : NULL;
|
||||||
}
|
}
|
||||||
|
|
||||||
@ -749,15 +735,6 @@ PopulateReportBlame(JSContext *cx, JSErrorReport *report)
|
|||||||
void
|
void
|
||||||
js_ReportOutOfMemory(JSContext *cx)
|
js_ReportOutOfMemory(JSContext *cx)
|
||||||
{
|
{
|
||||||
#ifdef JS_TRACER
|
|
||||||
/*
|
|
||||||
* If we are in a builtin called directly from trace, don't report an
|
|
||||||
* error. We will retry in the interpreter instead.
|
|
||||||
*/
|
|
||||||
if (JS_ON_TRACE(cx) && !JS_TRACE_MONITOR_ON_TRACE(cx)->bailExit)
|
|
||||||
return;
|
|
||||||
#endif
|
|
||||||
|
|
||||||
cx->runtime->hadOutOfMemory = true;
|
cx->runtime->hadOutOfMemory = true;
|
||||||
|
|
||||||
JSErrorReport report;
|
JSErrorReport report;
|
||||||
@ -1347,41 +1324,7 @@ js_GetScriptedCaller(JSContext *cx, StackFrame *fp)
|
|||||||
jsbytecode*
|
jsbytecode*
|
||||||
js_GetCurrentBytecodePC(JSContext* cx)
|
js_GetCurrentBytecodePC(JSContext* cx)
|
||||||
{
|
{
|
||||||
jsbytecode *pc, *imacpc;
|
return cx->hasfp() ? cx->regs().pc : NULL;
|
||||||
|
|
||||||
#ifdef JS_TRACER
|
|
||||||
if (JS_ON_TRACE(cx)) {
|
|
||||||
pc = JS_TRACE_MONITOR_ON_TRACE(cx)->bailExit->pc;
|
|
||||||
imacpc = JS_TRACE_MONITOR_ON_TRACE(cx)->bailExit->imacpc;
|
|
||||||
} else
|
|
||||||
#endif
|
|
||||||
{
|
|
||||||
JS_ASSERT_NOT_ON_TRACE(cx); /* for static analysis */
|
|
||||||
pc = cx->hasfp() ? cx->regs().pc : NULL;
|
|
||||||
if (!pc)
|
|
||||||
return NULL;
|
|
||||||
imacpc = cx->fp()->maybeImacropc();
|
|
||||||
}
|
|
||||||
|
|
||||||
/*
|
|
||||||
* If we are inside GetProperty_tn or similar, return a pointer to the
|
|
||||||
* current instruction in the script, not the CALL instruction in the
|
|
||||||
* imacro, for the benefit of callers doing bytecode inspection.
|
|
||||||
*/
|
|
||||||
return (*pc == JSOP_CALL && imacpc) ? imacpc : pc;
|
|
||||||
}
|
|
||||||
|
|
||||||
bool
|
|
||||||
js_CurrentPCIsInImacro(JSContext *cx)
|
|
||||||
{
|
|
||||||
#ifdef JS_TRACER
|
|
||||||
VOUCH_DOES_NOT_REQUIRE_STACK();
|
|
||||||
if (JS_ON_TRACE(cx))
|
|
||||||
return JS_TRACE_MONITOR_ON_TRACE(cx)->bailExit->imacpc != NULL;
|
|
||||||
return cx->fp()->hasImacropc();
|
|
||||||
#else
|
|
||||||
return false;
|
|
||||||
#endif
|
|
||||||
}
|
}
|
||||||
|
|
||||||
void
|
void
|
||||||
@ -1449,12 +1392,8 @@ JSContext::JSContext(JSRuntime *rt)
|
|||||||
resolveFlags(0),
|
resolveFlags(0),
|
||||||
rngSeed(0),
|
rngSeed(0),
|
||||||
iterValue(MagicValue(JS_NO_ITER_VALUE)),
|
iterValue(MagicValue(JS_NO_ITER_VALUE)),
|
||||||
#ifdef JS_TRACER
|
|
||||||
traceJitEnabled(false),
|
|
||||||
#endif
|
|
||||||
#ifdef JS_METHODJIT
|
#ifdef JS_METHODJIT
|
||||||
methodJitEnabled(false),
|
methodJitEnabled(false),
|
||||||
profilingEnabled(false),
|
|
||||||
#endif
|
#endif
|
||||||
inferenceEnabled(false),
|
inferenceEnabled(false),
|
||||||
#ifdef MOZ_TRACE_JSCALLS
|
#ifdef MOZ_TRACE_JSCALLS
|
||||||
@ -1629,7 +1568,7 @@ JSContext::purge()
|
|||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
#if defined(JS_TRACER) || defined(JS_METHODJIT)
|
#if defined(JS_METHODJIT)
|
||||||
static bool
|
static bool
|
||||||
ComputeIsJITBroken()
|
ComputeIsJITBroken()
|
||||||
{
|
{
|
||||||
@ -1705,15 +1644,6 @@ IsJITBrokenHere()
|
|||||||
void
|
void
|
||||||
JSContext::updateJITEnabled()
|
JSContext::updateJITEnabled()
|
||||||
{
|
{
|
||||||
#ifdef JS_TRACER
|
|
||||||
traceJitEnabled = ((runOptions & JSOPTION_JIT) &&
|
|
||||||
!IsJITBrokenHere() &&
|
|
||||||
compartment &&
|
|
||||||
!compartment->debugMode() &&
|
|
||||||
(debugHooks == &js_NullDebugHooks ||
|
|
||||||
(debugHooks == &runtime->globalDebugHooks &&
|
|
||||||
!runtime->debuggerInhibitsJIT())));
|
|
||||||
#endif
|
|
||||||
#ifdef JS_METHODJIT
|
#ifdef JS_METHODJIT
|
||||||
methodJitEnabled = (runOptions & JSOPTION_METHODJIT) &&
|
methodJitEnabled = (runOptions & JSOPTION_METHODJIT) &&
|
||||||
!IsJITBrokenHere()
|
!IsJITBrokenHere()
|
||||||
@ -1722,34 +1652,11 @@ JSContext::updateJITEnabled()
|
|||||||
JSC::MacroAssemblerX86Common::HasSSE2
|
JSC::MacroAssemblerX86Common::HasSSE2
|
||||||
# endif
|
# endif
|
||||||
;
|
;
|
||||||
#ifdef JS_TRACER
|
|
||||||
profilingEnabled = (runOptions & JSOPTION_PROFILING) && traceJitEnabled && methodJitEnabled;
|
|
||||||
#endif
|
|
||||||
#endif
|
#endif
|
||||||
}
|
}
|
||||||
|
|
||||||
namespace js {
|
namespace js {
|
||||||
|
|
||||||
JS_FORCES_STACK JS_FRIEND_API(void)
|
|
||||||
LeaveTrace(JSContext *cx)
|
|
||||||
{
|
|
||||||
#ifdef JS_TRACER
|
|
||||||
if (JS_ON_TRACE(cx))
|
|
||||||
DeepBail(cx);
|
|
||||||
#endif
|
|
||||||
}
|
|
||||||
|
|
||||||
bool
|
|
||||||
CanLeaveTrace(JSContext *cx)
|
|
||||||
{
|
|
||||||
JS_ASSERT(JS_ON_TRACE(cx));
|
|
||||||
#ifdef JS_TRACER
|
|
||||||
return JS_TRACE_MONITOR_ON_TRACE(cx)->bailExit != NULL;
|
|
||||||
#else
|
|
||||||
return false;
|
|
||||||
#endif
|
|
||||||
}
|
|
||||||
|
|
||||||
AutoEnumStateRooter::~AutoEnumStateRooter()
|
AutoEnumStateRooter::~AutoEnumStateRooter()
|
||||||
{
|
{
|
||||||
if (!stateValue.isNull()) {
|
if (!stateValue.isNull()) {
|
||||||
|
@ -70,18 +70,6 @@
|
|||||||
#pragma warning(disable:4355) /* Silence warning about "this" used in base member initializer list */
|
#pragma warning(disable:4355) /* Silence warning about "this" used in base member initializer list */
|
||||||
#endif
|
#endif
|
||||||
|
|
||||||
/* Forward declarations of nanojit types. */
|
|
||||||
namespace nanojit {
|
|
||||||
|
|
||||||
class Assembler;
|
|
||||||
class CodeAlloc;
|
|
||||||
class Fragment;
|
|
||||||
template<typename K> struct DefaultHash;
|
|
||||||
template<typename K, typename V, typename H> class HashMap;
|
|
||||||
template<typename T> class Seq;
|
|
||||||
|
|
||||||
} /* namespace nanojit */
|
|
||||||
|
|
||||||
JS_BEGIN_EXTERN_C
|
JS_BEGIN_EXTERN_C
|
||||||
struct DtoaState;
|
struct DtoaState;
|
||||||
JS_END_EXTERN_C
|
JS_END_EXTERN_C
|
||||||
@ -94,35 +82,12 @@ struct JSSharpObjectMap {
|
|||||||
|
|
||||||
namespace js {
|
namespace js {
|
||||||
|
|
||||||
/* Tracer constants. */
|
|
||||||
static const size_t MONITOR_N_GLOBAL_STATES = 4;
|
|
||||||
static const size_t FRAGMENT_TABLE_SIZE = 512;
|
|
||||||
static const size_t MAX_GLOBAL_SLOTS = 4096;
|
|
||||||
static const size_t GLOBAL_SLOTS_BUFFER_SIZE = MAX_GLOBAL_SLOTS + 1;
|
|
||||||
|
|
||||||
/* Forward declarations of tracer types. */
|
|
||||||
class VMAllocator;
|
|
||||||
class FrameInfoCache;
|
|
||||||
struct FrameInfo;
|
|
||||||
struct VMSideExit;
|
|
||||||
struct TreeFragment;
|
|
||||||
struct TracerState;
|
|
||||||
template<typename T> class Queue;
|
|
||||||
typedef Queue<uint16> SlotList;
|
|
||||||
class TypeMap;
|
|
||||||
class LoopProfile;
|
|
||||||
class InterpreterFrames;
|
|
||||||
|
|
||||||
#if defined(JS_JIT_SPEW) || defined(DEBUG)
|
|
||||||
struct FragPI;
|
|
||||||
typedef nanojit::HashMap<uint32, FragPI, nanojit::DefaultHash<uint32> > FragStatsMap;
|
|
||||||
#endif
|
|
||||||
|
|
||||||
namespace mjit {
|
namespace mjit {
|
||||||
class JaegerCompartment;
|
class JaegerCompartment;
|
||||||
}
|
}
|
||||||
|
|
||||||
class WeakMapBase;
|
class WeakMapBase;
|
||||||
|
class InterpreterFrames;
|
||||||
|
|
||||||
/*
|
/*
|
||||||
* GetSrcNote cache to avoid O(n^2) growth in finding a source note for a
|
* GetSrcNote cache to avoid O(n^2) growth in finding a source note for a
|
||||||
@ -167,25 +132,6 @@ struct ThreadData {
|
|||||||
unsigned requestDepth;
|
unsigned requestDepth;
|
||||||
#endif
|
#endif
|
||||||
|
|
||||||
#ifdef JS_TRACER
|
|
||||||
/*
|
|
||||||
* During trace execution (or during trace recording or
|
|
||||||
* profiling), these fields point to the compartment doing the
|
|
||||||
* execution on this thread. At other times, they are NULL. If a
|
|
||||||
* thread tries to execute/record/profile one trace while another
|
|
||||||
* is still running, the initial one will abort. Therefore, we
|
|
||||||
* only need to track one at a time.
|
|
||||||
*/
|
|
||||||
JSCompartment *onTraceCompartment;
|
|
||||||
JSCompartment *recordingCompartment;
|
|
||||||
JSCompartment *profilingCompartment;
|
|
||||||
|
|
||||||
/* Maximum size of the tracer's code cache before we start flushing. */
|
|
||||||
uint32 maxCodeCacheBytes;
|
|
||||||
|
|
||||||
static const uint32 DEFAULT_JIT_CACHE_SIZE = 16 * 1024 * 1024;
|
|
||||||
#endif
|
|
||||||
|
|
||||||
/* Keeper of the contiguous stack used by all contexts in this thread. */
|
/* Keeper of the contiguous stack used by all contexts in this thread. */
|
||||||
StackSpace stackSpace;
|
StackSpace stackSpace;
|
||||||
|
|
||||||
@ -615,14 +561,6 @@ struct JSRuntime
|
|||||||
/* Had an out-of-memory error which did not populate an exception. */
|
/* Had an out-of-memory error which did not populate an exception. */
|
||||||
JSBool hadOutOfMemory;
|
JSBool hadOutOfMemory;
|
||||||
|
|
||||||
#ifdef JS_TRACER
|
|
||||||
/* True if any debug hooks not supported by the JIT are enabled. */
|
|
||||||
bool debuggerInhibitsJIT() const {
|
|
||||||
return (globalDebugHooks.interruptHook ||
|
|
||||||
globalDebugHooks.callHook);
|
|
||||||
}
|
|
||||||
#endif
|
|
||||||
|
|
||||||
/*
|
/*
|
||||||
* Linked list of all js::Debugger objects. This may be accessed by the GC
|
* Linked list of all js::Debugger objects. This may be accessed by the GC
|
||||||
* thread, if any, or a thread that is in a request and holds gcLock.
|
* thread, if any, or a thread that is in a request and holds gcLock.
|
||||||
@ -1188,23 +1126,8 @@ struct JSContext
|
|||||||
/* Location to stash the iteration value between JSOP_MOREITER and JSOP_ITERNEXT. */
|
/* Location to stash the iteration value between JSOP_MOREITER and JSOP_ITERNEXT. */
|
||||||
js::Value iterValue;
|
js::Value iterValue;
|
||||||
|
|
||||||
#ifdef JS_TRACER
|
|
||||||
/*
|
|
||||||
* True if traces may be executed. Invariant: The value of traceJitenabled
|
|
||||||
* is always equal to the expression in updateJITEnabled below.
|
|
||||||
*
|
|
||||||
* This flag and the fields accessed by updateJITEnabled are written only
|
|
||||||
* in runtime->gcLock, to avoid race conditions that would leave the wrong
|
|
||||||
* value in traceJitEnabled. (But the interpreter reads this without
|
|
||||||
* locking. That can race against another thread setting debug hooks, but
|
|
||||||
* we always read cx->debugHooks without locking anyway.)
|
|
||||||
*/
|
|
||||||
bool traceJitEnabled;
|
|
||||||
#endif
|
|
||||||
|
|
||||||
#ifdef JS_METHODJIT
|
#ifdef JS_METHODJIT
|
||||||
bool methodJitEnabled;
|
bool methodJitEnabled;
|
||||||
bool profilingEnabled;
|
|
||||||
|
|
||||||
inline js::mjit::JaegerCompartment *jaegerCompartment();
|
inline js::mjit::JaegerCompartment *jaegerCompartment();
|
||||||
#endif
|
#endif
|
||||||
@ -2185,17 +2108,8 @@ js_GetCurrentBytecodePC(JSContext* cx);
|
|||||||
extern JSScript *
|
extern JSScript *
|
||||||
js_GetCurrentScript(JSContext* cx);
|
js_GetCurrentScript(JSContext* cx);
|
||||||
|
|
||||||
extern bool
|
|
||||||
js_CurrentPCIsInImacro(JSContext *cx);
|
|
||||||
|
|
||||||
namespace js {
|
namespace js {
|
||||||
|
|
||||||
extern JS_FORCES_STACK JS_FRIEND_API(void)
|
|
||||||
LeaveTrace(JSContext *cx);
|
|
||||||
|
|
||||||
extern bool
|
|
||||||
CanLeaveTrace(JSContext *cx);
|
|
||||||
|
|
||||||
#ifdef JS_METHODJIT
|
#ifdef JS_METHODJIT
|
||||||
namespace mjit {
|
namespace mjit {
|
||||||
void ExpandInlineFrames(JSCompartment *compartment);
|
void ExpandInlineFrames(JSCompartment *compartment);
|
||||||
|
@ -373,38 +373,10 @@ CallSetter(JSContext *cx, JSObject *obj, jsid id, StrictPropertyOp op, uintN att
|
|||||||
return CallJSPropertyOpSetter(cx, op, obj, id, strict, vp);
|
return CallJSPropertyOpSetter(cx, op, obj, id, strict, vp);
|
||||||
}
|
}
|
||||||
|
|
||||||
#ifdef JS_TRACER
|
|
||||||
/*
|
|
||||||
* Reconstruct the JS stack and clear cx->tracecx. We must be currently in a
|
|
||||||
* _FAIL builtin from trace on cx or another context on the same thread. The
|
|
||||||
* machine code for the trace remains on the C stack when js_DeepBail returns.
|
|
||||||
*
|
|
||||||
* Implemented in jstracer.cpp.
|
|
||||||
*/
|
|
||||||
JS_FORCES_STACK JS_FRIEND_API(void)
|
|
||||||
DeepBail(JSContext *cx);
|
|
||||||
#endif
|
|
||||||
|
|
||||||
static JS_INLINE void
|
|
||||||
LeaveTraceIfGlobalObject(JSContext *cx, JSObject *obj)
|
|
||||||
{
|
|
||||||
if (!obj->getParent())
|
|
||||||
LeaveTrace(cx);
|
|
||||||
}
|
|
||||||
|
|
||||||
static JS_INLINE void
|
|
||||||
LeaveTraceIfArgumentsObject(JSContext *cx, JSObject *obj)
|
|
||||||
{
|
|
||||||
if (obj->isArguments())
|
|
||||||
LeaveTrace(cx);
|
|
||||||
}
|
|
||||||
|
|
||||||
static inline JSAtom **
|
static inline JSAtom **
|
||||||
FrameAtomBase(JSContext *cx, js::StackFrame *fp)
|
FrameAtomBase(JSContext *cx, js::StackFrame *fp)
|
||||||
{
|
{
|
||||||
return fp->hasImacropc()
|
return fp->script()->atoms;
|
||||||
? cx->runtime->atomState.commonAtomsStart()
|
|
||||||
: fp->script()->atoms;
|
|
||||||
}
|
}
|
||||||
|
|
||||||
} /* namespace js */
|
} /* namespace js */
|
||||||
@ -525,14 +497,10 @@ JSContext::ensureParseMapPool()
|
|||||||
/*
|
/*
|
||||||
* Get the current frame, first lazily instantiating stack frames if needed.
|
* Get the current frame, first lazily instantiating stack frames if needed.
|
||||||
* (Do not access cx->fp() directly except in JS_REQUIRES_STACK code.)
|
* (Do not access cx->fp() directly except in JS_REQUIRES_STACK code.)
|
||||||
*
|
|
||||||
* LeaveTrace is defined in jstracer.cpp if JS_TRACER is defined.
|
|
||||||
*/
|
*/
|
||||||
static JS_FORCES_STACK JS_INLINE js::StackFrame *
|
static JS_FORCES_STACK JS_INLINE js::StackFrame *
|
||||||
js_GetTopStackFrame(JSContext *cx, FrameExpandKind expand)
|
js_GetTopStackFrame(JSContext *cx, FrameExpandKind expand)
|
||||||
{
|
{
|
||||||
js::LeaveTrace(cx);
|
|
||||||
|
|
||||||
#ifdef JS_METHODJIT
|
#ifdef JS_METHODJIT
|
||||||
if (expand)
|
if (expand)
|
||||||
js::mjit::ExpandInlineFrames(cx->compartment);
|
js::mjit::ExpandInlineFrames(cx->compartment);
|
||||||
|
Some files were not shown because too many files have changed in this diff Show More
Loading…
Reference in New Issue
Block a user