merge mozilla-inbound to mozilla-central a=merge

This commit is contained in:
Carsten "Tomcat" Book 2014-12-05 13:00:16 +01:00
Родитель 77f7453a32 568297df70
Коммит 772c7368d5
201 изменённых файлов: 6247 добавлений и 4755 удалений

Просмотреть файл

@ -99,6 +99,7 @@ pref("network.predictor.preserve", 50); // percentage of predictor data to keep
/* session history */
pref("browser.sessionhistory.max_total_viewers", 1);
pref("browser.sessionhistory.max_entries", 50);
pref("browser.sessionhistory.contentViewerTimeout", 360);
/* session store */
pref("browser.sessionstore.resume_session_once", false);

Просмотреть файл

@ -7291,17 +7291,6 @@ fi
AC_SUBST_LIST(MOZ_GLUE_WRAP_LDFLAGS)
export MOZ_GLUE_WRAP_LDFLAGS
dnl ========================================================
dnl = Use JS Call tracing
dnl ========================================================
MOZ_ARG_ENABLE_BOOL(trace-jscalls,
[ --enable-trace-jscalls Enable JS call enter/exit callback (default=no)],
MOZ_TRACE_JSCALLS=1,
MOZ_TRACE_JSCALLS= )
if test -n "$MOZ_TRACE_JSCALLS"; then
AC_DEFINE(MOZ_TRACE_JSCALLS)
fi
dnl ========================================================
dnl JS opt-mode assertions and minidump instrumentation
dnl ========================================================

Просмотреть файл

@ -53,7 +53,6 @@ Initialize()
nsresult rv = nsSHistory::Startup();
NS_ENSURE_SUCCESS(rv, rv);
nsSHEntryShared::Startup();
return NS_OK;
}

Просмотреть файл

@ -16,6 +16,7 @@
#include "nsThreadUtils.h"
#include "nsILayoutHistoryState.h"
#include "mozilla/Attributes.h"
#include "mozilla/Preferences.h"
#include "nsISupportsArray.h"
namespace dom = mozilla::dom;
@ -26,19 +27,18 @@ uint64_t gSHEntrySharedID = 0;
} // anonymous namespace
// Hardcode this to time out unused content viewers after 30 minutes
// XXX jlebar shouldn't this be a pref?
#define CONTENT_VIEWER_TIMEOUT_SECONDS (30*60)
#define CONTENT_VIEWER_TIMEOUT_SECONDS "browser.sessionhistory.contentViewerTimeout"
// Default this to time out unused content viewers after 30 minutes
#define CONTENT_VIEWER_TIMEOUT_SECONDS_DEFAULT (30*60)
typedef nsExpirationTracker<nsSHEntryShared, 3> HistoryTrackerBase;
class HistoryTracker MOZ_FINAL : public HistoryTrackerBase {
public:
// Expire cached contentviewers after 20-30 minutes in the cache.
HistoryTracker()
: HistoryTrackerBase(1000 * CONTENT_VIEWER_TIMEOUT_SECONDS / 2)
HistoryTracker(uint32_t aTimeout)
: HistoryTrackerBase(1000 * aTimeout / 2)
{
}
protected:
virtual void NotifyExpired(nsSHEntryShared *aObj) {
RemoveObject(aObj);
@ -49,9 +49,15 @@ protected:
static HistoryTracker *gHistoryTracker = nullptr;
void
nsSHEntryShared::Startup()
nsSHEntryShared::EnsureHistoryTracker()
{
gHistoryTracker = new HistoryTracker();
if (!gHistoryTracker) {
// nsExpirationTracker doesn't allow one to change the timer period,
// so just set it once when the history tracker is used for the first time.
gHistoryTracker = new HistoryTracker(
mozilla::Preferences::GetUint(CONTENT_VIEWER_TIMEOUT_SECONDS,
CONTENT_VIEWER_TIMEOUT_SECONDS_DEFAULT));
}
}
void
@ -79,14 +85,16 @@ nsSHEntryShared::~nsSHEntryShared()
RemoveFromExpirationTracker();
#ifdef DEBUG
// Check that we're not still on track to expire. We shouldn't be, because
// we just removed ourselves!
nsExpirationTracker<nsSHEntryShared, 3>::Iterator
iterator(gHistoryTracker);
if (gHistoryTracker) {
// Check that we're not still on track to expire. We shouldn't be, because
// we just removed ourselves!
nsExpirationTracker<nsSHEntryShared, 3>::Iterator
iterator(gHistoryTracker);
nsSHEntryShared *elem;
while ((elem = iterator.Next()) != nullptr) {
NS_ASSERTION(elem != this, "Found dead entry still in the tracker!");
nsSHEntryShared *elem;
while ((elem = iterator.Next()) != nullptr) {
NS_ASSERTION(elem != this, "Found dead entry still in the tracker!");
}
}
#endif
@ -118,7 +126,7 @@ nsSHEntryShared::Duplicate(nsSHEntryShared *aEntry)
void nsSHEntryShared::RemoveFromExpirationTracker()
{
if (GetExpirationState()->IsTracked()) {
if (gHistoryTracker && GetExpirationState()->IsTracked()) {
gHistoryTracker->RemoveObject(this);
}
}
@ -201,6 +209,7 @@ nsSHEntryShared::SetContentViewer(nsIContentViewer *aViewer)
mContentViewer = aViewer;
if (mContentViewer) {
EnsureHistoryTracker();
gHistoryTracker->AddObject(this);
nsCOMPtr<nsIDOMDocument> domDoc;

Просмотреть файл

@ -34,7 +34,7 @@ class nsSHEntryShared MOZ_FINAL : public nsIBFCacheEntry,
public nsIMutationObserver
{
public:
static void Startup();
static void EnsureHistoryTracker();
static void Shutdown();
nsSHEntryShared();

Просмотреть файл

@ -26,21 +26,18 @@ AnimationPlayer::WrapObject(JSContext* aCx)
return dom::AnimationPlayerBinding::Wrap(aCx, this);
}
Nullable<double>
AnimationPlayer::GetStartTime() const
{
return AnimationUtils::TimeDurationToDouble(mStartTime);
}
Nullable<TimeDuration>
AnimationPlayer::GetCurrentTime() const
{
Nullable<TimeDuration> result;
if (!mHoldTime.IsNull()) {
result = mHoldTime;
} else {
return result;
}
if (!mStartTime.IsNull()) {
Nullable<TimeDuration> timelineTime = mTimeline->GetCurrentTime();
if (!timelineTime.IsNull() && !mStartTime.IsNull()) {
if (!timelineTime.IsNull()) {
result.SetValue(timelineTime.Value() - mStartTime.Value());
}
}
@ -55,7 +52,7 @@ AnimationPlayer::PlayState() const
return AnimationPlayState::Idle;
}
if (mIsPaused) {
if (mStartTime.IsNull()) {
return AnimationPlayState::Paused;
}
@ -80,6 +77,12 @@ AnimationPlayer::Pause()
PostUpdate();
}
Nullable<double>
AnimationPlayer::GetStartTimeAsDouble() const
{
return AnimationUtils::TimeDurationToDouble(mStartTime);
}
Nullable<double>
AnimationPlayer::GetCurrentTimeAsDouble() const
{
@ -106,6 +109,24 @@ AnimationPlayer::Tick()
}
}
void
AnimationPlayer::ResolveStartTime()
{
// Currently we only expect this method to be called when we are in the
// middle of initiating/resuming playback so we should have an unresolved
// start time to update and a fixed current time to seek to.
MOZ_ASSERT(mStartTime.IsNull() && !mHoldTime.IsNull(),
"Resolving the start time but we don't appear to be waiting"
" to begin playback");
Nullable<TimeDuration> readyTime = mTimeline->GetCurrentTime();
// Bug 1096776: Once we support disappearing or inactive timelines we
// will need special handling here.
MOZ_ASSERT(!readyTime.IsNull(), "Missing or inactive timeline");
mStartTime.SetValue(readyTime.Value() - mHoldTime.Value());
mHoldTime.SetNull();
}
bool
AnimationPlayer::IsRunning() const
{
@ -164,35 +185,30 @@ AnimationPlayer::ComposeStyle(nsRefPtr<css::AnimValuesStyleRule>& aStyleRule,
void
AnimationPlayer::DoPlay()
{
// FIXME: When we implement finishing behavior (bug 1074630) we should
// not return early if mIsPaused is false since we may still need to seek.
// (However, we will need to pass a flag so that when we start playing due to
// a change in animation-play-state we *don't* trigger finishing behavior.)
if (!mIsPaused) {
return;
}
mIsPaused = false;
// FIXME: When we implement finishing behavior (bug 1074630) we will
// need to pass a flag so that when we start playing due to a change in
// animation-play-state we *don't* trigger finishing behavior.
Nullable<TimeDuration> timelineTime = mTimeline->GetCurrentTime();
if (timelineTime.IsNull()) {
// FIXME: We should just sit in the pending state in this case.
// We will introduce the pending state in Bug 927349.
Nullable<TimeDuration> currentTime = GetCurrentTime();
if (currentTime.IsNull()) {
mHoldTime.SetValue(TimeDuration(0));
} else if (mHoldTime.IsNull()) {
// If the hold time is null, we are already playing normally
return;
}
// Update start time to an appropriate offset from the current timeline time
MOZ_ASSERT(!mHoldTime.IsNull(), "Hold time should not be null when paused");
mStartTime.SetValue(timelineTime.Value() - mHoldTime.Value());
mHoldTime.SetNull();
ResolveStartTime();
}
void
AnimationPlayer::DoPause()
{
if (mIsPaused) {
if (IsPaused()) {
return;
}
mIsPaused = true;
// Mark this as no longer running on the compositor so that next time
// we update animations we won't throttle them and will have a chance
// to remove the animation from any layer it might be on.
mIsRunningOnCompositor = false;
// Bug 927349 - check for null result here and go to pending state

Просмотреть файл

@ -45,7 +45,6 @@ protected:
public:
explicit AnimationPlayer(AnimationTimeline* aTimeline)
: mTimeline(aTimeline)
, mIsPaused(false)
, mIsRunningOnCompositor(false)
, mIsPreviousStateFinished(false)
{
@ -63,7 +62,7 @@ public:
// AnimationPlayer methods
Animation* GetSource() const { return mSource; }
AnimationTimeline* Timeline() const { return mTimeline; }
Nullable<double> GetStartTime() const;
Nullable<TimeDuration> GetStartTime() const { return mStartTime; }
Nullable<TimeDuration> GetCurrentTime() const;
AnimationPlayState PlayState() const;
virtual void Play();
@ -74,6 +73,7 @@ public:
// from script. We often use the same methods internally and from
// script but when called from script we (or one of our subclasses) perform
// extra steps such as flushing style or converting the return type.
Nullable<double> GetStartTimeAsDouble() const;
Nullable<double> GetCurrentTimeAsDouble() const;
virtual AnimationPlayState PlayStateFromJS() const { return PlayState(); }
virtual void PlayFromJS() { Play(); }
@ -84,12 +84,16 @@ public:
void SetSource(Animation* aSource);
void Tick();
// Sets the start time of the player to the current time of its timeline.
// This should only be called on a player that is currently waiting to play
// (and therefore has a null start time but a fixed hold time).
void ResolveStartTime();
const nsString& Name() const {
return mSource ? mSource->Name() : EmptyString();
}
bool IsPaused() const { return mIsPaused; }
bool IsPaused() const { return PlayState() == AnimationPlayState::Paused; }
bool IsRunning() const;
bool HasCurrentSource() const {
@ -118,9 +122,6 @@ public:
nsCSSPropertySet& aSetProperties,
bool& aNeedsRefreshes);
// The beginning of the delay period.
Nullable<TimeDuration> mStartTime; // Timeline timescale
protected:
void DoPlay();
void DoPause();
@ -136,8 +137,9 @@ protected:
nsRefPtr<AnimationTimeline> mTimeline;
nsRefPtr<Animation> mSource;
// The beginning of the delay period.
Nullable<TimeDuration> mStartTime; // Timeline timescale
Nullable<TimeDuration> mHoldTime; // Player timescale
bool mIsPaused;
bool mIsRunningOnCompositor;
// Indicates whether we were in the finished state during our
// most recent unthrottled sample (our last ComposeStyle call).

Просмотреть файл

@ -217,7 +217,7 @@ WebGL2Context::TexImage3D(GLenum target, GLint level, GLenum internalformat,
if (pixels.IsNull()) {
data = nullptr;
dataLength = 0;
jsArrayType = js::Scalar::TypeMax;
jsArrayType = js::Scalar::MaxTypedArrayViewType;
} else {
const ArrayBufferView& view = pixels.Value();
view.ComputeLengthAndData();

Просмотреть файл

@ -597,7 +597,7 @@ public:
return TexImage2D_base(texImageTarget, level, internalFormat,
size.width, size.height, data->Stride(), 0,
format, type, data->GetData(), byteLength,
js::Scalar::TypeMax, srcFormat,
js::Scalar::MaxTypedArrayViewType, srcFormat,
mPixelStorePremultiplyAlpha);
}
@ -672,7 +672,7 @@ public:
return TexSubImage2D_base(texImageTarget.get(), level, xoffset, yoffset,
size.width, size.height, data->Stride(),
format, type, data->GetData(), byteLength,
js::Scalar::TypeMax, srcFormat,
js::Scalar::MaxTypedArrayViewType, srcFormat,
mPixelStorePremultiplyAlpha);
}
@ -1255,7 +1255,7 @@ protected:
// helpers
// If `isArrayType is TypeMax, it means no array.
// If jsArrayType is MaxTypedArrayViewType, it means no array.
void TexImage2D_base(TexImageTarget texImageTarget, GLint level,
GLenum internalFormat, GLsizei width,
GLsizei height, GLsizei srcStrideOrZero, GLint border,

Просмотреть файл

@ -4003,7 +4003,7 @@ WebGLContext::TexImage2D(GLenum rawTarget, GLint level,
if (pixels.IsNull()) {
data = nullptr;
length = 0;
jsArrayType = js::Scalar::TypeMax;
jsArrayType = js::Scalar::MaxTypedArrayViewType;
} else {
const ArrayBufferView& view = pixels.Value();
view.ComputeLengthAndData();
@ -4047,7 +4047,7 @@ WebGLContext::TexImage2D(GLenum rawTarget, GLint level,
return TexImage2D_base(rawTarget, level, internalformat, pixels->Width(),
pixels->Height(), 4*pixels->Width(), 0,
format, type, pixelData, pixelDataLength, js::Scalar::TypeMax,
format, type, pixelData, pixelDataLength, js::Scalar::MaxTypedArrayViewType,
WebGLTexelFormat::RGBA8, false);
}
@ -4230,7 +4230,7 @@ WebGLContext::TexSubImage2D(GLenum target, GLint level,
pixels->Width(), pixels->Height(),
4*pixels->Width(), format, type,
arr.Data(), arr.Length(),
js::Scalar::TypeMax,
js::Scalar::MaxTypedArrayViewType,
WebGLTexelFormat::RGBA8, false);
}

Просмотреть файл

@ -1212,9 +1212,9 @@ WebGLContext::ValidateTexInputData(GLenum type, js::Scalar::Type jsArrayType,
WebGLTexImageFunc func,
WebGLTexDimensions dims)
{
// We're using js::Scalar::TypeMax as dummy value for when the tex source
// wasn't a typed array.
if (jsArrayType == js::Scalar::TypeMax)
// We're using js::Scalar::MaxTypedArrayViewType as dummy value for when
// the tex source wasn't a typed array.
if (jsArrayType == js::Scalar::MaxTypedArrayViewType)
return true;
const char invalidTypedArray[] = "%s: Invalid typed array type for given"

Просмотреть файл

@ -52,6 +52,7 @@ using mozilla::CSSPoint from "Units.h";
using mozilla::CSSToScreenScale from "Units.h";
using mozilla::CommandInt from "mozilla/EventForwards.h";
using mozilla::layers::GeckoContentController::APZStateChange from "mozilla/layers/GeckoContentController.h";
using mozilla::WritingMode from "WritingModes.h";
namespace mozilla {
namespace dom {
@ -201,10 +202,13 @@ parent:
* seqno Current seqno value on the content side
* anchor Offset where the selection started
* focus Offset where the caret is
* writingMode CSS writing-mode in effect at the focus
* causedByComposition true if the change is caused by composition
*/
prio(urgent) async NotifyIMESelection(uint32_t seqno, uint32_t anchor,
uint32_t focus, bool causedByComposition);
uint32_t focus,
WritingMode writingMode,
bool causedByComposition);
/**
* Notifies chrome to refresh its text cache

Просмотреть файл

@ -229,6 +229,7 @@ TabParent::TabParent(nsIContentParent* aManager,
, mFrameElement(nullptr)
, mIMESelectionAnchor(0)
, mIMESelectionFocus(0)
, mWritingMode()
, mIMEComposing(false)
, mIMECompositionEnding(false)
, mIMECompositionStart(0)
@ -1395,6 +1396,7 @@ bool
TabParent::RecvNotifyIMESelection(const uint32_t& aSeqno,
const uint32_t& aAnchor,
const uint32_t& aFocus,
const mozilla::WritingMode& aWritingMode,
const bool& aCausedByComposition)
{
nsCOMPtr<nsIWidget> widget = GetWidget();
@ -1404,6 +1406,7 @@ TabParent::RecvNotifyIMESelection(const uint32_t& aSeqno,
if (aSeqno == mIMESeqno) {
mIMESelectionAnchor = aAnchor;
mIMESelectionFocus = aFocus;
mWritingMode = aWritingMode;
const nsIMEUpdatePreference updatePreference =
widget->GetIMEUpdatePreference();
if (updatePreference.WantSelectionChange() &&
@ -1585,6 +1588,7 @@ TabParent::HandleQueryContentEvent(WidgetQueryContentEvent& aEvent)
}
aEvent.mReply.mReversed = mIMESelectionFocus < mIMESelectionAnchor;
aEvent.mReply.mHasSelection = true;
aEvent.mReply.mWritingMode = mWritingMode;
aEvent.mSucceeded = true;
}
break;

Просмотреть файл

@ -20,6 +20,7 @@
#include "nsIXULBrowserWindow.h"
#include "nsWeakReference.h"
#include "Units.h"
#include "WritingModes.h"
#include "js/TypeDecls.h"
class nsFrameLoader;
@ -172,6 +173,7 @@ public:
virtual bool RecvNotifyIMESelection(const uint32_t& aSeqno,
const uint32_t& aAnchor,
const uint32_t& aFocus,
const mozilla::WritingMode& aWritingMode,
const bool& aCausedByComposition) MOZ_OVERRIDE;
virtual bool RecvNotifyIMETextHint(const nsString& aText) MOZ_OVERRIDE;
virtual bool RecvNotifyIMEMouseButtonEvent(const widget::IMENotification& aEventMessage,
@ -379,6 +381,7 @@ protected:
nsString mIMECacheText;
uint32_t mIMESelectionAnchor;
uint32_t mIMESelectionFocus;
mozilla::WritingMode mWritingMode;
bool mIMEComposing;
bool mIMECompositionEnding;
// Buffer to store composition text during ResetInputState

Просмотреть файл

@ -569,7 +569,7 @@ MP4Reader::NeedInput(DecoderData& aDecoder)
// which overrides our "few more samples" threshold.
return
!aDecoder.mError &&
!aDecoder.mEOS &&
!aDecoder.mDemuxEOS &&
aDecoder.mOutputRequested &&
aDecoder.mOutput.IsEmpty() &&
(aDecoder.mInputExhausted ||
@ -583,6 +583,7 @@ MP4Reader::Update(TrackType aTrack)
bool needInput = false;
bool needOutput = false;
bool eos = false;
auto& decoder = GetDecoderData(aTrack);
nsRefPtr<MediaData> output;
{
@ -598,6 +599,7 @@ MP4Reader::Update(TrackType aTrack)
output = decoder.mOutput[0];
decoder.mOutput.RemoveElementAt(0);
}
eos = decoder.mDrainComplete;
}
VLOG("Update(%s) ni=%d no=%d iex=%d or=%d fl=%d",
TrackTypeToStr(aTrack),
@ -614,8 +616,8 @@ MP4Reader::Update(TrackType aTrack)
} else {
{
MonitorAutoLock lock(decoder.mMonitor);
MOZ_ASSERT(!decoder.mEOS);
decoder.mEOS = true;
MOZ_ASSERT(!decoder.mDemuxEOS);
decoder.mDemuxEOS = true;
}
// DrainComplete takes care of reporting EOS upwards
decoder.mDecoder->Drain();
@ -624,6 +626,8 @@ MP4Reader::Update(TrackType aTrack)
if (needOutput) {
if (output) {
ReturnOutput(output, aTrack);
} else if (eos) {
ReturnEOS(aTrack);
}
}
}
@ -727,14 +731,9 @@ void
MP4Reader::DrainComplete(TrackType aTrack)
{
DecoderData& data = GetDecoderData(aTrack);
bool eos;
{
MonitorAutoLock mon(data.mMonitor);
eos = data.mEOS;
}
if (eos) {
ReturnEOS(aTrack);
}
MonitorAutoLock mon(data.mMonitor);
data.mDrainComplete = true;
ScheduleUpdate(aTrack);
}
void
@ -773,7 +772,8 @@ MP4Reader::Flush(TrackType aTrack)
{
MonitorAutoLock mon(data.mMonitor);
data.mIsFlushing = true;
data.mEOS = false;
data.mDemuxEOS = false;
data.mDrainComplete = false;
}
data.mDecoder->Flush();
{
@ -814,7 +814,7 @@ MP4Reader::SkipVideoDemuxToNextKeyFrame(int64_t aTimeThreshold, uint32_t& parsed
RequestSampleCallback::END_OF_STREAM);
{
MonitorAutoLock mon(mVideo.mMonitor);
mVideo.mEOS = true;
mVideo.mDemuxEOS = true;
}
return false;
}

Просмотреть файл

@ -158,7 +158,8 @@ private:
, mIsFlushing(false)
, mOutputRequested(false)
, mUpdateScheduled(false)
, mEOS(false)
, mDemuxEOS(false)
, mDrainComplete(false)
, mDiscontinuity(false)
{
}
@ -187,7 +188,8 @@ private:
bool mIsFlushing;
bool mOutputRequested;
bool mUpdateScheduled;
bool mEOS;
bool mDemuxEOS;
bool mDrainComplete;
bool mDiscontinuity;
};
DecoderData mAudio;

Просмотреть файл

@ -13,6 +13,7 @@
#include <istream>
#include <iterator>
#include <sstream>
#include <set>
#include "mozilla/Assertions.h"
#include "mozilla/Attributes.h"
@ -21,18 +22,80 @@
using namespace std;
FakeDecryptor* FakeDecryptor::sInstance = nullptr;
extern GMPPlatformAPI* g_platform_api; // Defined in gmp-fake.cpp
static bool sFinishedTruncateTest = false;
static bool sFinishedReplaceTest = false;
static bool sMultiClientTest = false;
void
MaybeFinish()
class GMPMutexAutoLock
{
if (sFinishedTruncateTest && sFinishedReplaceTest && sMultiClientTest) {
public:
explicit GMPMutexAutoLock(GMPMutex* aMutex) : mMutex(aMutex) {
mMutex->Acquire();
}
~GMPMutexAutoLock() {
mMutex->Release();
}
private:
GMPMutex* const mMutex;
};
class TestManager {
public:
TestManager() : mMutex(CreateMutex()) {}
// Register a test with the test manager.
void BeginTest(const string& aTestID) {
GMPMutexAutoLock lock(mMutex);
auto found = mTestIDs.find(aTestID);
if (found == mTestIDs.end()) {
mTestIDs.insert(aTestID);
} else {
Error("FAIL BeginTest test already existed: " + aTestID);
}
}
// Notify the test manager that the test is finished. If all tests are done,
// test manager will send "test-storage complete" to notify the parent that
// all tests are finished and also delete itself.
void EndTest(const string& aTestID) {
bool isEmpty = false;
{
GMPMutexAutoLock lock(mMutex);
auto found = mTestIDs.find(aTestID);
if (found != mTestIDs.end()) {
mTestIDs.erase(aTestID);
isEmpty = mTestIDs.empty();
} else {
Error("FAIL EndTest test not existed: " + aTestID);
return;
}
}
if (isEmpty) {
Finish();
delete this;
}
}
private:
~TestManager() {
mMutex->Destroy();
}
static void Error(const string& msg) {
FakeDecryptor::Message(msg);
}
static void Finish() {
FakeDecryptor::Message("test-storage complete");
}
}
static GMPMutex* CreateMutex() {
GMPMutex* mutex = nullptr;
g_platform_api->createmutex(&mutex);
return mutex;
}
GMPMutex* const mMutex;
set<string> mTestIDs;
};
FakeDecryptor::FakeDecryptor(GMPDecryptorHost* aHost)
: mCallback(nullptr)
@ -87,89 +150,129 @@ public:
class SendMessageTask : public GMPTask {
public:
SendMessageTask(const string& aMessage)
: mMessage(aMessage)
{}
SendMessageTask(const string& aMessage,
TestManager* aTestManager = nullptr,
const string& aTestID = "")
: mMessage(aMessage), mTestmanager(aTestManager), mTestID(aTestID) {}
void Run() MOZ_OVERRIDE {
FakeDecryptor::Message(mMessage);
if (mTestmanager) {
mTestmanager->EndTest(mTestID);
}
}
void Destroy() MOZ_OVERRIDE {
delete this;
}
private:
string mMessage;
TestManager* const mTestmanager;
const string mTestID;
};
class TestEmptyContinuation : public ReadContinuation {
public:
TestEmptyContinuation(TestManager* aTestManager, const string& aTestID)
: mTestmanager(aTestManager), mTestID(aTestID) {}
void ReadComplete(GMPErr aErr, const std::string& aData) MOZ_OVERRIDE {
if (aData != "") {
FakeDecryptor::Message("FAIL TestEmptyContinuation record was not truncated");
}
sFinishedTruncateTest = true;
MaybeFinish();
mTestmanager->EndTest(mTestID);
delete this;
}
private:
TestManager* const mTestmanager;
const string mTestID;
};
class TruncateContinuation : public ReadContinuation {
public:
TruncateContinuation(const string& aID,
TestManager* aTestManager,
const string& aTestID)
: mID(aID), mTestmanager(aTestManager), mTestID(aTestID) {}
void ReadComplete(GMPErr aErr, const std::string& aData) MOZ_OVERRIDE {
if (aData != TruncateRecordData) {
FakeDecryptor::Message("FAIL TruncateContinuation read data doesn't match written data");
}
WriteRecord(TruncateRecordId, nullptr, 0,
new ReadThenTask(TruncateRecordId, new TestEmptyContinuation()),
new SendMessageTask("FAIL in TruncateContinuation write."));
auto cont = new TestEmptyContinuation(mTestmanager, mTestID);
auto msg = "FAIL in TruncateContinuation write.";
auto failTask = new SendMessageTask(msg, mTestmanager, mTestID);
WriteRecord(mID, nullptr, 0, new ReadThenTask(mID, cont), failTask);
delete this;
}
private:
const string mID;
TestManager* const mTestmanager;
const string mTestID;
};
class VerifyAndFinishContinuation : public ReadContinuation {
public:
explicit VerifyAndFinishContinuation(string aValue)
: mValue(aValue)
{}
explicit VerifyAndFinishContinuation(string aValue,
TestManager* aTestManager,
const string& aTestID)
: mValue(aValue), mTestmanager(aTestManager), mTestID(aTestID) {}
void ReadComplete(GMPErr aErr, const std::string& aData) MOZ_OVERRIDE {
if (aData != mValue) {
FakeDecryptor::Message("FAIL VerifyAndFinishContinuation read data doesn't match expected data");
}
sFinishedReplaceTest = true;
MaybeFinish();
mTestmanager->EndTest(mTestID);
delete this;
}
private:
string mValue;
TestManager* const mTestmanager;
const string mTestID;
};
class VerifyAndOverwriteContinuation : public ReadContinuation {
public:
VerifyAndOverwriteContinuation(string aId, string aValue, string aOverwrite)
VerifyAndOverwriteContinuation(string aId, string aValue, string aOverwrite,
TestManager* aTestManager, const string& aTestID)
: mId(aId)
, mValue(aValue)
, mOverwrite(aOverwrite)
, mTestmanager(aTestManager)
, mTestID(aTestID)
{}
void ReadComplete(GMPErr aErr, const std::string& aData) MOZ_OVERRIDE {
if (aData != mValue) {
FakeDecryptor::Message("FAIL VerifyAndOverwriteContinuation read data doesn't match expected data");
}
WriteRecord(mId,
mOverwrite,
new ReadThenTask(mId, new VerifyAndFinishContinuation(mOverwrite)),
new SendMessageTask("FAIL in VerifyAndOverwriteContinuation write."));
auto cont = new VerifyAndFinishContinuation(mOverwrite, mTestmanager, mTestID);
auto msg = "FAIL in VerifyAndOverwriteContinuation write.";
auto failTask = new SendMessageTask(msg, mTestmanager, mTestID);
WriteRecord(mId, mOverwrite, new ReadThenTask(mId, cont), failTask);
delete this;
}
private:
string mId;
string mValue;
string mOverwrite;
TestManager* const mTestmanager;
const string mTestID;
};
static const string OpenAgainRecordId = "open-again-record-id";
class OpenedSecondTimeContinuation : public OpenContinuation {
public:
explicit OpenedSecondTimeContinuation(GMPRecord* aRecord)
: mRecord(aRecord)
{
}
explicit OpenedSecondTimeContinuation(GMPRecord* aRecord,
TestManager* aTestManager,
const string& aTestID)
: mRecord(aRecord), mTestmanager(aTestManager), mTestID(aTestID) {}
virtual void OpenComplete(GMPErr aStatus, GMPRecord* aRecord) MOZ_OVERRIDE {
if (GMP_SUCCEEDED(aStatus)) {
@ -177,34 +280,44 @@ public:
}
// Succeeded, open should have failed.
sMultiClientTest = true;
MaybeFinish();
mTestmanager->EndTest(mTestID);
mRecord->Close();
delete this;
}
private:
GMPRecord* mRecord;
TestManager* const mTestmanager;
const string mTestID;
};
class OpenedFirstTimeContinuation : public OpenContinuation {
public:
OpenedFirstTimeContinuation(const string& aID,
TestManager* aTestManager,
const string& aTestID)
: mID(aID), mTestmanager(aTestManager), mTestID(aTestID) {}
virtual void OpenComplete(GMPErr aStatus, GMPRecord* aRecord) MOZ_OVERRIDE {
if (GMP_FAILED(aStatus)) {
FakeDecryptor::Message("FAIL OpenAgainContinuation to open record initially.");
sMultiClientTest = true;
MaybeFinish();
mTestmanager->EndTest(mTestID);
return;
}
GMPOpenRecord(OpenAgainRecordId, new OpenedSecondTimeContinuation(aRecord));
auto cont = new OpenedSecondTimeContinuation(aRecord, mTestmanager, mTestID);
GMPOpenRecord(mID, cont);
delete this;
}
private:
const string mID;
TestManager* const mTestmanager;
const string mTestID;
};
void
FakeDecryptor::TestStorage()
static void
DoTestStorage(const string& aPrefix, TestManager* aTestManager)
{
// Basic I/O tests. We run three cases concurrently. The tests, like
// GMPStorage run asynchronously. When they've all passed, we send
@ -217,11 +330,14 @@ FakeDecryptor::TestStorage()
// read data, verify that we read what we wrote, then
// write 0 bytes to truncate record, then
// read data, verify that 0 bytes was read
// set sFinishedTruncateTest=true and MaybeFinish().
WriteRecord(TruncateRecordId,
TruncateRecordData,
new ReadThenTask(TruncateRecordId, new TruncateContinuation()),
new SendMessageTask("FAIL in TestStorage writing TruncateRecord."));
const string id1 = aPrefix + TruncateRecordId;
const string testID1 = aPrefix + "write-test-1";
aTestManager->BeginTest(testID1);
auto cont1 = new TruncateContinuation(id1, aTestManager, testID1);
auto msg1 = "FAIL in TestStorage writing TruncateRecord.";
auto failTask1 = new SendMessageTask(msg1, aTestManager, testID1);
WriteRecord(id1, TruncateRecordData,
new ReadThenTask(id1, cont1), failTask1);
// Test 2: Test that overwriting a record with a shorter record truncates
// the record to the shorter record.
@ -230,25 +346,75 @@ FakeDecryptor::TestStorage()
// read and verify record, then
// write a shorter record to same record.
// read and verify
// set sFinishedReplaceTest=true and MaybeFinish().
string id = "record1";
string id2 = aPrefix + "record1";
string record1 = "This is the first write to a record.";
string overwrite = "A shorter record";
WriteRecord(id,
record1,
new ReadThenTask(id, new VerifyAndOverwriteContinuation(id, record1, overwrite)),
new SendMessageTask("FAIL in TestStorage writing record1."));
const string testID2 = aPrefix + "write-test-2";
aTestManager->BeginTest(testID2);
auto task2 = new VerifyAndOverwriteContinuation(id2, record1, overwrite,
aTestManager, testID2);
auto msg2 = "FAIL in TestStorage writing record1.";
auto failTask2 = new SendMessageTask(msg2, aTestManager, testID2);
WriteRecord(id2, record1, new ReadThenTask(id2, task2), failTask2);
// Test 3: Test that opening a record while it's already open fails.
//
// Open record1, then
// open record1, should fail.
// close record1,
// set sMultiClientTest=true and MaybeFinish().
// close record1
const string id3 = aPrefix + OpenAgainRecordId;
const string testID3 = aPrefix + "open-test-1";
aTestManager->BeginTest(testID3);
auto task3 = new OpenedFirstTimeContinuation(id3, aTestManager, testID3);
GMPOpenRecord(id3, task3);
}
GMPOpenRecord(OpenAgainRecordId, new OpenedFirstTimeContinuation());
class TestStorageTask : public GMPTask {
public:
TestStorageTask(const string& aPrefix, TestManager* aTestManager)
: mPrefix(aPrefix), mTestManager(aTestManager) {}
virtual void Destroy() { delete this; }
virtual void Run() {
DoTestStorage(mPrefix, mTestManager);
}
private:
const string mPrefix;
TestManager* const mTestManager;
};
// Note: Once all tests finish, dispatch "test-pass" message,
void
FakeDecryptor::TestStorage()
{
TestManager* testManager = new TestManager();
GMPThread* thread1 = nullptr;
GMPThread* thread2 = nullptr;
// Main thread tests.
DoTestStorage("mt1-", testManager);
DoTestStorage("mt2-", testManager);
// Off-main-thread tests.
if (GMP_SUCCEEDED(g_platform_api->createthread(&thread1))) {
thread1->Post(new TestStorageTask("thread1-", testManager));
} else {
FakeDecryptor::Message("FAIL to create thread1 for storage tests");
}
if (GMP_SUCCEEDED(g_platform_api->createthread(&thread2))) {
thread2->Post(new TestStorageTask("thread2-", testManager));
} else {
FakeDecryptor::Message("FAIL to create thread2 for storage tests");
}
if (thread1) {
thread1->Join();
}
if (thread2) {
thread2->Join();
}
// Note: Once all tests finish, TestManager will dispatch "test-pass" message,
// which ends the test for the parent.
}

Просмотреть файл

@ -23,7 +23,7 @@ class GMPStorageChild;
class GMPRecordImpl : public GMPRecord
{
public:
NS_INLINE_DECL_REFCOUNTING(GMPRecordImpl)
NS_INLINE_DECL_THREADSAFE_REFCOUNTING(GMPRecordImpl)
GMPRecordImpl(GMPStorageChild* aOwner,
const nsCString& aName,
@ -52,7 +52,7 @@ private:
class GMPStorageChild : public PGMPStorageChild
{
public:
NS_INLINE_DECL_REFCOUNTING(GMPStorageChild)
NS_INLINE_DECL_THREADSAFE_REFCOUNTING(GMPStorageChild)
explicit GMPStorageChild(GMPChild* aPlugin);

Просмотреть файл

@ -82,7 +82,7 @@ public:
AnalyserNode::AnalyserNode(AudioContext* aContext)
: AudioNode(aContext,
1,
ChannelCountMode::Explicit,
ChannelCountMode::Max,
ChannelInterpretation::Speakers)
, mAnalysisBlock(2048)
, mMinDecibels(-100.)

Просмотреть файл

@ -27,6 +27,7 @@
#include "DynamicsCompressorNode.h"
#include "BiquadFilterNode.h"
#include "ScriptProcessorNode.h"
#include "StereoPannerNode.h"
#include "ChannelMergerNode.h"
#include "ChannelSplitterNode.h"
#include "MediaStreamAudioDestinationNode.h"
@ -278,6 +279,13 @@ AudioContext::CreateAnalyser()
return analyserNode.forget();
}
already_AddRefed<StereoPannerNode>
AudioContext::CreateStereoPanner()
{
nsRefPtr<StereoPannerNode> stereoPannerNode = new StereoPannerNode(this);
return stereoPannerNode.forget();
}
already_AddRefed<MediaElementAudioSourceNode>
AudioContext::CreateMediaElementSource(HTMLMediaElement& aMediaElement,
ErrorResult& aRv)

Просмотреть файл

@ -59,6 +59,7 @@ class MediaStreamAudioSourceNode;
class OscillatorNode;
class PannerNode;
class ScriptProcessorNode;
class StereoPannerNode;
class WaveShaperNode;
class PeriodicWave;
class Promise;
@ -143,6 +144,9 @@ public:
uint32_t aNumberOfOutputChannels,
ErrorResult& aRv);
already_AddRefed<StereoPannerNode>
CreateStereoPanner();
already_AddRefed<AnalyserNode>
CreateAnalyser();

Просмотреть файл

@ -185,6 +185,17 @@ AudioBufferInPlaceScale(float* aBlock,
}
}
void
AudioBlockPanMonoToStereo(const float aInput[WEBAUDIO_BLOCK_SIZE],
float aGainL[WEBAUDIO_BLOCK_SIZE],
float aGainR[WEBAUDIO_BLOCK_SIZE],
float aOutputL[WEBAUDIO_BLOCK_SIZE],
float aOutputR[WEBAUDIO_BLOCK_SIZE])
{
AudioBlockCopyChannelWithScale(aInput, aGainL, aOutputL);
AudioBlockCopyChannelWithScale(aInput, aGainR, aOutputR);
}
void
AudioBlockPanMonoToStereo(const float aInput[WEBAUDIO_BLOCK_SIZE],
float aGainL, float aGainR,
@ -215,13 +226,38 @@ AudioBlockPanStereoToStereo(const float aInputL[WEBAUDIO_BLOCK_SIZE],
if (aIsOnTheLeft) {
for (i = 0; i < WEBAUDIO_BLOCK_SIZE; ++i) {
*aOutputL++ = *aInputL++ + *aInputR * aGainL;
*aOutputR++ = *aInputR++ * aGainR;
aOutputL[i] = aInputL[i] + aInputR[i] * aGainL;
aOutputR[i] = aInputR[i] * aGainR;
}
} else {
for (i = 0; i < WEBAUDIO_BLOCK_SIZE; ++i) {
*aOutputL++ = *aInputL * aGainL;
*aOutputR++ = *aInputR++ + *aInputL++ * aGainR;
aOutputL[i] = aInputL[i] * aGainL;
aOutputR[i] = aInputR[i] + aInputL[i] * aGainR;
}
}
}
void
AudioBlockPanStereoToStereo(const float aInputL[WEBAUDIO_BLOCK_SIZE],
const float aInputR[WEBAUDIO_BLOCK_SIZE],
float aGainL[WEBAUDIO_BLOCK_SIZE],
float aGainR[WEBAUDIO_BLOCK_SIZE],
bool aIsOnTheLeft[WEBAUDIO_BLOCK_SIZE],
float aOutputL[WEBAUDIO_BLOCK_SIZE],
float aOutputR[WEBAUDIO_BLOCK_SIZE])
{
#ifdef BUILD_ARM_NEON
// No NEON version yet: bug 1105513
#endif
uint32_t i;
for (i = 0; i < WEBAUDIO_BLOCK_SIZE; i++) {
if (aIsOnTheLeft[i]) {
aOutputL[i] = aInputL[i] + aInputR[i] * aGainL[i];
aOutputR[i] = aInputR[i] * aGainR[i];
} else {
aOutputL[i] = aInputL[i] * aGainL[i];
aOutputR[i] = aInputR[i] + aInputL[i] * aGainR[i];
}
}
}

Просмотреть файл

@ -197,6 +197,13 @@ AudioBlockPanMonoToStereo(const float aInput[WEBAUDIO_BLOCK_SIZE],
float aGainL, float aGainR,
float aOutputL[WEBAUDIO_BLOCK_SIZE],
float aOutputR[WEBAUDIO_BLOCK_SIZE]);
void
AudioBlockPanMonoToStereo(const float aInput[WEBAUDIO_BLOCK_SIZE],
float aGainL[WEBAUDIO_BLOCK_SIZE],
float aGainR[WEBAUDIO_BLOCK_SIZE],
float aOutputL[WEBAUDIO_BLOCK_SIZE],
float aOutputR[WEBAUDIO_BLOCK_SIZE]);
/**
* Pan a stereo source according to right and left gain, and the position
* (whether the listener is on the left of the source or not).
@ -208,6 +215,14 @@ AudioBlockPanStereoToStereo(const float aInputL[WEBAUDIO_BLOCK_SIZE],
float aGainL, float aGainR, bool aIsOnTheLeft,
float aOutputL[WEBAUDIO_BLOCK_SIZE],
float aOutputR[WEBAUDIO_BLOCK_SIZE]);
void
AudioBlockPanStereoToStereo(const float aInputL[WEBAUDIO_BLOCK_SIZE],
const float aInputR[WEBAUDIO_BLOCK_SIZE],
float aGainL[WEBAUDIO_BLOCK_SIZE],
float aGainR[WEBAUDIO_BLOCK_SIZE],
bool aIsOnTheLeft[WEBAUDIO_BLOCK_SIZE],
float aOutputL[WEBAUDIO_BLOCK_SIZE],
float aOutputR[WEBAUDIO_BLOCK_SIZE]);
/**
* Return the sum of squares of all of the samples in the input.

Просмотреть файл

@ -8,6 +8,7 @@
#include "AudioNodeEngine.h"
#include "AudioNodeStream.h"
#include "AudioListener.h"
#include "PanningUtils.h"
#include "AudioBufferSourceNode.h"
#include "PlayingRefChangeHandler.h"
#include "blink/HRTFPanner.h"
@ -176,11 +177,6 @@ public:
// Compute how much the distance contributes to the gain reduction.
float ComputeDistanceGain();
void GainMonoToStereo(const AudioChunk& aInput, AudioChunk* aOutput,
float aGainL, float aGainR);
void GainStereoToStereo(const AudioChunk& aInput, AudioChunk* aOutput,
float aGainL, float aGainR, double aAzimuth);
void EqualPowerPanningFunction(const AudioChunk& aInput, AudioChunk* aOutput);
void HRTFPanningFunction(const AudioChunk& aInput, AudioChunk* aOutput);
@ -372,38 +368,11 @@ PannerNodeEngine::EqualPowerPanningFunction(const AudioChunk& aInput,
gainR = sin(0.5 * M_PI * normalizedAzimuth);
// Compute the output.
if (inputChannels == 1) {
GainMonoToStereo(aInput, aOutput, gainL, gainR);
} else {
GainStereoToStereo(aInput, aOutput, gainL, gainR, azimuth);
}
ApplyStereoPanning(aInput, aOutput, gainL, gainR, azimuth <= 0);
aOutput->mVolume = aInput.mVolume * distanceGain * coneGain;
}
void
PannerNodeEngine::GainMonoToStereo(const AudioChunk& aInput, AudioChunk* aOutput,
float aGainL, float aGainR)
{
float* outputL = static_cast<float*>(const_cast<void*>(aOutput->mChannelData[0]));
float* outputR = static_cast<float*>(const_cast<void*>(aOutput->mChannelData[1]));
const float* input = static_cast<float*>(const_cast<void*>(aInput.mChannelData[0]));
AudioBlockPanMonoToStereo(input, aGainL, aGainR, outputL, outputR);
}
void
PannerNodeEngine::GainStereoToStereo(const AudioChunk& aInput, AudioChunk* aOutput,
float aGainL, float aGainR, double aAzimuth)
{
float* outputL = static_cast<float*>(const_cast<void*>(aOutput->mChannelData[0]));
float* outputR = static_cast<float*>(const_cast<void*>(aOutput->mChannelData[1]));
const float* inputL = static_cast<float*>(const_cast<void*>(aInput.mChannelData[0]));
const float* inputR = static_cast<float*>(const_cast<void*>(aInput.mChannelData[1]));
AudioBlockPanStereoToStereo(inputL, inputR, aGainL, aGainR, aAzimuth <= 0, outputL, outputR);
}
// This algorithm is specified in the webaudio spec.
void
PannerNodeEngine::ComputeAzimuthAndElevation(float& aAzimuth, float& aElevation)

Просмотреть файл

@ -0,0 +1,65 @@
/* -*- Mode: C++; tab-width: 2; indent-tabs-mode: nil; c-basic-offset: 2 -*- */
/* vim:set ts=2 sw=2 sts=2 et cindent: */
/* This Source Code Form is subject to the terms of the Mozilla Public
* License, v. 2.0. If a copy of the MPL was not distributed with this
* file, You can obtain one at http://mozilla.org/MPL/2.0/. */
#ifndef PANNING_UTILS_H
#define PANNING_UTILS_H
#include "AudioSegment.h"
#include "AudioNodeEngine.h"
namespace mozilla {
namespace dom {
template<typename T>
void
GainMonoToStereo(const AudioChunk& aInput, AudioChunk* aOutput,
T aGainL, T aGainR)
{
float* outputL = static_cast<float*>(const_cast<void*>(aOutput->mChannelData[0]));
float* outputR = static_cast<float*>(const_cast<void*>(aOutput->mChannelData[1]));
const float* input = static_cast<float*>(const_cast<void*>(aInput.mChannelData[0]));
MOZ_ASSERT(aInput.ChannelCount() == 1);
MOZ_ASSERT(aOutput->ChannelCount() == 2);
AudioBlockPanMonoToStereo(input, aGainL, aGainR, outputL, outputR);
}
// T can be float or an array of float, and U can be bool or an array of bool,
// depending if the value of the parameters are constant for this block.
template<typename T, typename U>
void
GainStereoToStereo(const AudioChunk& aInput, AudioChunk* aOutput,
T aGainL, T aGainR, U aOnLeft)
{
float* outputL = static_cast<float*>(const_cast<void*>(aOutput->mChannelData[0]));
float* outputR = static_cast<float*>(const_cast<void*>(aOutput->mChannelData[1]));
const float* inputL = static_cast<float*>(const_cast<void*>(aInput.mChannelData[0]));
const float* inputR = static_cast<float*>(const_cast<void*>(aInput.mChannelData[1]));
MOZ_ASSERT(aInput.ChannelCount() == 2);
MOZ_ASSERT(aOutput->ChannelCount() == 2);
AudioBlockPanStereoToStereo(inputL, inputR, aGainL, aGainR, aOnLeft, outputL, outputR);
}
// T can be float or an array of float, and U can be bool or an array of bool,
// depending if the value of the parameters are constant for this block.
template<typename T, typename U>
void ApplyStereoPanning(const AudioChunk& aInput, AudioChunk* aOutput,
T aGainL, T aGainR, U aOnLeft)
{
if (aInput.mChannelData.Length() == 1) {
GainMonoToStereo(aInput, aOutput, aGainL, aGainR);
} else {
GainStereoToStereo(aInput, aOutput, aGainL, aGainR, aOnLeft);
}
}
} // dom
} // mozilla
#endif // PANNING_UTILS_H

Просмотреть файл

@ -0,0 +1,221 @@
/* -*- Mode: C++; tab-width: 2; indent-tabs-mode: nil; c-basic-offset: 2 -*- */
/* vim:set ts=2 sw=2 sts=2 et cindent: */
/* This Source Code Form is subject to the terms of the Mozilla Public
* License, v. 2.0. If a copy of the MPL was not distributed with this
* file, You can obtain one at http://mozilla.org/MPL/2.0/. */
#include "StereoPannerNode.h"
#include "mozilla/dom/StereoPannerNodeBinding.h"
#include "AudioNodeEngine.h"
#include "AudioNodeStream.h"
#include "AudioDestinationNode.h"
#include "WebAudioUtils.h"
#include "PanningUtils.h"
#include "AudioParamTimeline.h"
#include "AudioParam.h"
namespace mozilla {
namespace dom {
using namespace std;
NS_IMPL_CYCLE_COLLECTION_INHERITED(StereoPannerNode, AudioNode, mPan)
NS_INTERFACE_MAP_BEGIN_CYCLE_COLLECTION_INHERITED(StereoPannerNode)
NS_INTERFACE_MAP_END_INHERITING(AudioNode)
NS_IMPL_ADDREF_INHERITED(StereoPannerNode, AudioNode)
NS_IMPL_RELEASE_INHERITED(StereoPannerNode, AudioNode)
class StereoPannerNodeEngine : public AudioNodeEngine
{
public:
StereoPannerNodeEngine(AudioNode* aNode,
AudioDestinationNode* aDestination)
: AudioNodeEngine(aNode)
, mSource(nullptr)
, mDestination(static_cast<AudioNodeStream*>(aDestination->Stream()))
// Keep the default value in sync with the default value in
// StereoPannerNode::StereoPannerNode.
, mPan(0.f)
{
}
void SetSourceStream(AudioNodeStream* aSource)
{
mSource = aSource;
}
enum Parameters {
PAN
};
void SetTimelineParameter(uint32_t aIndex,
const AudioParamTimeline& aValue,
TrackRate aSampleRate) MOZ_OVERRIDE
{
switch (aIndex) {
case PAN:
MOZ_ASSERT(mSource && mDestination);
mPan = aValue;
WebAudioUtils::ConvertAudioParamToTicks(mPan, mSource, mDestination);
break;
default:
NS_ERROR("Bad StereoPannerNode TimelineParameter");
}
}
void GetGainValuesForPanning(float aPanning,
bool aMonoToStereo,
float& aLeftGain,
float& aRightGain)
{
// Clamp and normalize the panning in [0; 1]
aPanning = std::min(std::max(aPanning, -1.f), 1.f);
if (aMonoToStereo) {
aPanning += 1;
aPanning /= 2;
} else if (aPanning <= 0) {
aPanning += 1;
}
aLeftGain = cos(0.5 * M_PI * aPanning);
aRightGain = sin(0.5 * M_PI * aPanning);
}
void SetToSilentStereoBlock(AudioChunk* aChunk)
{
for (uint32_t channel = 0; channel < 2; channel++) {
float* samples = static_cast<float*>(const_cast<void*>(aChunk->mChannelData[channel]));
for (uint32_t i = 0; i < WEBAUDIO_BLOCK_SIZE; i++) {
samples[i] = 0.f;
}
}
}
void UpmixToStereoIfNeeded(const AudioChunk& aInput, AudioChunk* aOutput)
{
if (aInput.ChannelCount() == 2) {
*aOutput = aInput;
} else {
MOZ_ASSERT(aInput.ChannelCount() == 1);
AllocateAudioBlock(2, aOutput);
const float* input = static_cast<const float*>(aInput.mChannelData[0]);
for (uint32_t channel = 0; channel < 2; channel++) {
float* output = static_cast<float*>(const_cast<void*>(aOutput->mChannelData[channel]));
PodCopy(output, input, WEBAUDIO_BLOCK_SIZE);
}
}
}
virtual void ProcessBlock(AudioNodeStream* aStream,
const AudioChunk& aInput,
AudioChunk* aOutput,
bool *aFinished) MOZ_OVERRIDE
{
MOZ_ASSERT(mSource == aStream, "Invalid source stream");
// The output of this node is always stereo, no matter what the inputs are.
MOZ_ASSERT(aInput.ChannelCount() <= 2);
AllocateAudioBlock(2, aOutput);
bool monoToStereo = aInput.ChannelCount() == 1;
if (aInput.IsNull()) {
// If input is silent, so is the output
SetToSilentStereoBlock(aOutput);
} else if (mPan.HasSimpleValue()) {
float panning = mPan.GetValue();
// If the panning is 0.0, we can simply copy the input to the
// output, up-mixing to stereo if needed.
if (panning == 0.0f) {
UpmixToStereoIfNeeded(aInput, aOutput);
} else {
// Optimize the case where the panning is constant for this processing
// block: we can just apply a constant gain on the left and right
// channel
float gainL, gainR;
GetGainValuesForPanning(panning, monoToStereo, gainL, gainR);
ApplyStereoPanning(aInput, aOutput,
gainL * aInput.mVolume,
gainR * aInput.mVolume,
panning <= 0);
}
} else {
float computedGain[2][WEBAUDIO_BLOCK_SIZE];
bool onLeft[WEBAUDIO_BLOCK_SIZE];
for (size_t counter = 0; counter < WEBAUDIO_BLOCK_SIZE; ++counter) {
StreamTime tick = aStream->GetCurrentPosition();
float left, right;
float panning = mPan.GetValueAtTime(tick, counter);
GetGainValuesForPanning(panning, monoToStereo, left, right);
computedGain[0][counter] = left * aInput.mVolume;
computedGain[1][counter] = right * aInput.mVolume;
onLeft[counter] = panning <= 0;
}
// Apply the gain to the output buffer
ApplyStereoPanning(aInput, aOutput, computedGain[0], computedGain[1], onLeft);
}
}
virtual size_t SizeOfIncludingThis(MallocSizeOf aMallocSizeOf) const MOZ_OVERRIDE
{
return aMallocSizeOf(this) + SizeOfExcludingThis(aMallocSizeOf);
}
AudioNodeStream* mSource;
AudioNodeStream* mDestination;
AudioParamTimeline mPan;
};
StereoPannerNode::StereoPannerNode(AudioContext* aContext)
: AudioNode(aContext,
2,
ChannelCountMode::Clamped_max,
ChannelInterpretation::Speakers)
, mPan(new AudioParam(MOZ_THIS_IN_INITIALIZER_LIST(),
SendPanToStream, 0.f))
{
StereoPannerNodeEngine* engine = new StereoPannerNodeEngine(this, aContext->Destination());
mStream = aContext->Graph()->CreateAudioNodeStream(engine,
MediaStreamGraph::INTERNAL_STREAM);
engine->SetSourceStream(static_cast<AudioNodeStream*>(mStream.get()));
}
StereoPannerNode::~StereoPannerNode()
{
}
size_t
StereoPannerNode::SizeOfExcludingThis(MallocSizeOf aMallocSizeOf) const
{
size_t amount = AudioNode::SizeOfExcludingThis(aMallocSizeOf);
amount += mPan->SizeOfIncludingThis(aMallocSizeOf);
return amount;
}
size_t
StereoPannerNode::SizeOfIncludingThis(MallocSizeOf aMallocSizeOf) const
{
return aMallocSizeOf(this) + SizeOfExcludingThis(aMallocSizeOf);
}
JSObject*
StereoPannerNode::WrapObject(JSContext* aCx)
{
return StereoPannerNodeBinding::Wrap(aCx, this);
}
void
StereoPannerNode::SendPanToStream(AudioNode* aNode)
{
StereoPannerNode* This = static_cast<StereoPannerNode*>(aNode);
SendTimelineParameterToStream(This, StereoPannerNodeEngine::PAN, *This->mPan);
}
}
}

Просмотреть файл

@ -0,0 +1,71 @@
/* -*- Mode: C++; tab-width: 2; indent-tabs-mode: nil; c-basic-offset: 2 -*- */
/* vim:set ts=2 sw=2 sts=2 et cindent: */
/* This Source Code Form is subject to the terms of the Mozilla Public
* License, v. 2.0. If a copy of the MPL was not distributed with this
* file, You can obtain one at http://mozilla.org/MPL/2.0/. */
#ifndef StereoPannerNode_h_
#define StereoPannerNode_h_
#include "AudioNode.h"
#include "mozilla/dom/StereoPannerNodeBinding.h"
namespace mozilla {
namespace dom {
class AudioContext;
class StereoPannerNode : public AudioNode
{
public:
MOZ_DECLARE_REFCOUNTED_TYPENAME(StereoPannerNode)
explicit StereoPannerNode(AudioContext* aContext);
virtual JSObject* WrapObject(JSContext* aCx) MOZ_OVERRIDE;
virtual void SetChannelCount(uint32_t aChannelCount, ErrorResult& aRv) MOZ_OVERRIDE
{
if (aChannelCount > 2) {
aRv.Throw(NS_ERROR_DOM_NOT_SUPPORTED_ERR);
return;
}
AudioNode::SetChannelCount(aChannelCount, aRv);
}
virtual void SetChannelCountModeValue(ChannelCountMode aMode, ErrorResult& aRv) MOZ_OVERRIDE
{
if (aMode == ChannelCountMode::Max) {
aRv.Throw(NS_ERROR_DOM_NOT_SUPPORTED_ERR);
return;
}
AudioNode::SetChannelCountModeValue(aMode, aRv);
}
AudioParam* Pan() const
{
return mPan;
}
NS_DECL_ISUPPORTS_INHERITED
NS_DECL_CYCLE_COLLECTION_CLASS_INHERITED(StereoPannerNode, AudioNode)
virtual const char* NodeType() const
{
return "StereoPannerNode";
}
virtual size_t SizeOfExcludingThis(MallocSizeOf aMallocSizeOf) const MOZ_OVERRIDE;
virtual size_t SizeOfIncludingThis(MallocSizeOf aMallocSizeOf) const MOZ_OVERRIDE;
protected:
virtual ~StereoPannerNode();
private:
static void SendPanToStream(AudioNode* aNode);
nsRefPtr<AudioParam> mPan;
};
}
}
#endif

Просмотреть файл

@ -58,6 +58,7 @@ EXPORTS.mozilla.dom += [
'PannerNode.h',
'PeriodicWave.h',
'ScriptProcessorNode.h',
'StereoPannerNode.h',
'WaveShaperNode.h',
]
@ -93,6 +94,7 @@ UNIFIED_SOURCES += [
'PannerNode.cpp',
'PeriodicWave.cpp',
'ScriptProcessorNode.cpp',
'StereoPannerNode.cpp',
'ThreeDPoint.cpp',
'WaveShaperNode.cpp',
'WebAudioUtils.cpp',

Просмотреть файл

@ -132,6 +132,8 @@ skip-if = (toolkit == 'gonk' && !debug)
[test_pannerNodeChannelCount.html]
[test_pannerNodeHRTFSymmetry.html]
[test_pannerNodeTail.html]
[test_stereoPannerNode.html]
[test_stereoPannerNodePassThrough.html]
[test_periodicWave.html]
[test_scriptProcessorNode.html]
[test_scriptProcessorNodeChannelCount.html]

Просмотреть файл

@ -30,8 +30,8 @@ addLoadEvent(function() {
source.connect(analyser);
analyser.connect(destination);
is(analyser.channelCount, 1, "analyser node has 2 input channels by default");
is(analyser.channelCountMode, "explicit", "Correct channelCountMode for the analyser node");
is(analyser.channelCount, 1, "analyser node has 1 input channels by default");
is(analyser.channelCountMode, "max", "Correct channelCountMode for the analyser node");
is(analyser.channelInterpretation, "speakers", "Correct channelCountInterpretation for the analyser node");
is(analyser.fftSize, 2048, "Correct default value for fftSize");

Просмотреть файл

@ -0,0 +1,243 @@
<!DOCTYPE HTML>
<html>
<head>
<title>Test StereoPannerNode</title>
<script type="text/javascript" src="/tests/SimpleTest/SimpleTest.js"></script>
<script type="text/javascript" src="webaudio.js"></script>
<link rel="stylesheet" type="text/css" href="/tests/SimpleTest/test.css" />
</head>
<body>
<pre id="test">
<script class="testbody" type="text/javascript">
var SR = 44100;
var BUF_SIZE = 128;
var PANNING = 0.1;
var GAIN = 0.5;
// Cheap reimplementation of some bits of the spec
function gainForPanningMonoToStereo(panning) {
panning += 1;
panning /= 2;
return [ Math.cos(0.5 * Math.PI * panning),
Math.sin(0.5 * Math.PI * panning) ];
}
function gainForPanningStereoToStereo(panning) {
if (panning <= 0) {
panning += 1.;
}
return [ Math.cos(0.5 * Math.PI * panning),
Math.sin(0.5 * Math.PI * panning) ];
}
function applyStereoToStereoPanning(l, r, panningValues, panning) {
var outL, outR;
if (panning <= 0) {
outL = l + r * panningValues[0];
outR = r * panningValues[1];
} else {
outL = l * panningValues[0];
outR = r + l * panningValues[1];
}
return [outL,outR];
}
function applyMonoToStereoPanning(c, panning) {
return [c * panning[0], c * panning[1]];
}
// Test the DOM interface
var context = new OfflineAudioContext(1, 1, SR);
var stereoPanner = context.createStereoPanner();
ok(stereoPanner.pan, "The AudioParam member must exist");
is(stereoPanner.pan.value, 0.0, "Correct initial value");
is(stereoPanner.pan.defaultValue, 0.0, "Correct default value");
is(stereoPanner.channelCount, 2, "StereoPannerNode node has 2 input channels by default");
is(stereoPanner.channelCountMode, "clamped-max", "Correct channelCountMode for the StereoPannerNode");
is(stereoPanner.channelInterpretation, "speakers", "Correct channelCountInterpretation for the StereoPannerNode");
expectException(function() {
stereoPanner.channelCount = 3;
}, DOMException.NOT_SUPPORTED_ERR);
expectException(function() {
stereoPanner.channelCountMode = "max";
}, DOMException.NOT_SUPPORTED_ERR);
// A sine to be used to fill the buffers
function sine(t) {
return Math.sin(440 * 2 * Math.PI * t / context.sampleRate);
}
// A couple mono and stereo buffers: the StereoPannerNode equation is different
// if the input is mono or stereo
var stereoBuffer = context.createBuffer(2, BUF_SIZE, context.sampleRate);
var monoBuffer = context.createBuffer(1, BUF_SIZE, context.sampleRate);
for (var i = 0; i < BUF_SIZE; ++i) {
monoBuffer.getChannelData(0)[i] =
stereoBuffer.getChannelData(0)[i] =
stereoBuffer.getChannelData(1)[i] = sine(i);
}
// Expected test vectors
function expectedBufferNoop(gain) {
gain = gain || 1.0;
var expectedBuffer = context.createBuffer(2, BUF_SIZE, SR);
for (var i = 0; i < BUF_SIZE; i++) {
expectedBuffer.getChannelData(0)[i] = gain * sine(i);
expectedBuffer.getChannelData(1)[i] = gain * sine(i);
}
return expectedBuffer;
}
function expectedBufferForStereo(gain) {
gain = gain || 1.0;
var expectedBuffer = context.createBuffer(2, BUF_SIZE, SR);
var gainPanning = gainForPanningStereoToStereo(PANNING);
gainPanning[0] *= gain;
gainPanning[1] *= gain;
for (var i = 0; i < BUF_SIZE; i++) {
var values = [ sine(i), sine(i) ];
var processed = applyStereoToStereoPanning(values[0], values[1], gainPanning, PANNING);
expectedBuffer.getChannelData(0)[i] = processed[0];
expectedBuffer.getChannelData(1)[i] = processed[1];
}
return expectedBuffer;
}
function expectedBufferForMono(gain) {
gain = gain || 1.0;
var expectedBuffer = context.createBuffer(2, BUF_SIZE, SR);
var gainPanning = gainForPanningMonoToStereo(PANNING);
gainPanning[0] *= gain;
gainPanning[1] *= gain;
for (var i = 0; i < BUF_SIZE; i++) {
var value = sine(i);
var processed = applyMonoToStereoPanning(value, gainPanning);
expectedBuffer.getChannelData(0)[i] = processed[0];
expectedBuffer.getChannelData(1)[i] = processed[1];
}
return expectedBuffer;
}
// Actual test cases
var tests = [
function monoPanningNoop(ctx, panner) {
var monoSource = ctx.createBufferSource();
monoSource.connect(panner);
monoSource.buffer = monoBuffer;
monoSource.start(0);
return expectedBufferNoop();
},
function stereoPanningNoop(ctx, panner) {
var stereoSource = ctx.createBufferSource();
stereoSource.connect(panner);
stereoSource.buffer = stereoBuffer;
stereoSource.start(0);
return expectedBufferNoop();
},
function stereoPanningAutomation(ctx, panner) {
var stereoSource = ctx.createBufferSource();
stereoSource.connect(panner);
stereoSource.buffer = stereoBuffer;
panner.pan.setValueAtTime(0.1, 0.0);
stereoSource.start(0);
return expectedBufferForStereo();
},
function stereoPanning(ctx, panner) {
var stereoSource = ctx.createBufferSource();
stereoSource.buffer = stereoBuffer;
stereoSource.connect(panner);
panner.pan.value = 0.1;
stereoSource.start(0);
return expectedBufferForStereo();
},
function monoPanningAutomation(ctx, panner) {
var monoSource = ctx.createBufferSource();
monoSource.connect(panner);
monoSource.buffer = monoBuffer;
panner.pan.setValueAtTime(PANNING, 0.0);
monoSource.start(0);
return expectedBufferForMono();
},
function monoPanning(ctx, panner) {
var monoSource = ctx.createBufferSource();
monoSource.connect(panner);
monoSource.buffer = monoBuffer;
panner.pan.value = 0.1;
monoSource.start(0);
return expectedBufferForMono();
},
function monoPanningWithGain(ctx, panner) {
var monoSource = ctx.createBufferSource();
var gain = ctx.createGain();
gain.gain.value = GAIN;
monoSource.connect(gain);
gain.connect(panner);
monoSource.buffer = monoBuffer;
panner.pan.value = 0.1;
monoSource.start(0);
return expectedBufferForMono(GAIN);
},
function stereoPanningWithGain(ctx, panner) {
var stereoSource = ctx.createBufferSource();
var gain = ctx.createGain();
gain.gain.value = GAIN;
stereoSource.connect(gain);
gain.connect(panner);
stereoSource.buffer = stereoBuffer;
panner.pan.value = 0.1;
stereoSource.start(0);
return expectedBufferForStereo(GAIN);
},
function monoPanningWithGainAndAutomation(ctx, panner) {
var monoSource = ctx.createBufferSource();
var gain = ctx.createGain();
gain.gain.value = GAIN;
monoSource.connect(gain);
gain.connect(panner);
monoSource.buffer = monoBuffer;
panner.pan.setValueAtTime(PANNING, 0);
monoSource.start(0);
return expectedBufferForMono(GAIN);
},
function stereoPanningWithGainAndAutomation(ctx, panner) {
var stereoSource = ctx.createBufferSource();
var gain = ctx.createGain();
gain.gain.value = GAIN;
stereoSource.connect(gain);
gain.connect(panner);
stereoSource.buffer = stereoBuffer;
panner.pan.setValueAtTime(PANNING, 0);
stereoSource.start(0);
return expectedBufferForStereo(GAIN);
}
];
var finished = 0;
function finish() {
if (++finished == tests.length) {
SimpleTest.finish();
}
}
tests.forEach(function(f) {
var ac = new OfflineAudioContext(2, BUF_SIZE, SR);
var panner = ac.createStereoPanner();
panner.connect(ac.destination);
var expected = f(ac, panner);
ac.oncomplete = function(e) {
info(f.name);
compareBuffers(e.renderedBuffer, expected);
finish();
};
ac.startRendering()
});
SimpleTest.waitForExplicitFinish();
</script>
</pre>
<pre id=dump>
</pre>
</body>
</html>

Просмотреть файл

@ -0,0 +1,47 @@
<!DOCTYPE HTML>
<html>
<head>
<title>Test StereoPanerNode with passthrough</title>
<script type="text/javascript" src="/tests/SimpleTest/SimpleTest.js"></script>
<script type="text/javascript" src="webaudio.js"></script>
<link rel="stylesheet" type="text/css" href="/tests/SimpleTest/test.css" />
</head>
<body>
<pre id="test">
<script class="testbody" type="text/javascript">
var gTest = {
length: 2048,
numberOfChannels: 1,
createGraph: function(context) {
var source = context.createBufferSource();
var stereoPanner = context.createStereoPanner();
source.buffer = this.buffer;
source.connect(stereoPanner);
var stereoPannerWrapped = SpecialPowers.wrap(stereoPanner);
ok("passThrough" in stereoPannerWrapped, "StereoPannerNode should support the passThrough API");
stereoPannerWrapped.passThrough = true;
source.start(0);
return stereoPanner;
},
createExpectedBuffers: function(context) {
this.buffer = context.createBuffer(1, 2048, context.sampleRate);
for (var i = 0; i < 2048; ++i) {
this.buffer.getChannelData(0)[i] = Math.sin(440 * 2 * Math.PI * i / context.sampleRate);
}
return [this.buffer];
},
};
runTest();
</script>
</pre>
</body>
</html>

Просмотреть файл

@ -473,6 +473,7 @@ let SettingsRequestManager = {
let store = lock.getObjectStore(aTask.principal);
if (!store) {
if (DEBUG) debug("Rejecting Set task on lock " + aTask.data.lockID);
this.removeLock(data.lockID);
return Promise.reject({task: aTask, error: "Cannot get object store"});
}

Просмотреть файл

@ -955,6 +955,8 @@ var interfaceNamesInGlobalScope =
{name: "SpeechSynthesisVoice", b2g: true},
// IMPORTANT: Do not change this list without review from a DOM peer!
{name: "SpecialPowers", xbl: false},
// IMPORTANT: Do not change this list without review from a DOM peer!
"StereoPannerNode",
// IMPORTANT: Do not change this list without review from a DOM peer!
"Storage",
// IMPORTANT: Do not change this list without review from a DOM peer!

Просмотреть файл

@ -19,7 +19,7 @@ interface AnimationPlayer {
[Pure]
readonly attribute Animation? source;
readonly attribute AnimationTimeline timeline;
[Pure]
[BinaryName="startTimeAsDouble"]
readonly attribute double? startTime;
[BinaryName="currentTimeAsDouble"]
readonly attribute double? currentTime;

Просмотреть файл

@ -41,6 +41,8 @@ interface AudioContext : EventTarget {
optional unsigned long numberOfInputChannels = 2,
optional unsigned long numberOfOutputChannels = 2);
[NewObject]
StereoPannerNode createStereoPanner();
[NewObject]
AnalyserNode createAnalyser();
[NewObject, Throws]

Просмотреть файл

@ -0,0 +1,19 @@
/* -*- Mode: IDL; tab-width: 2; indent-tabs-mode: nil; c-basic-offset: 2 -*- */
/* This Source Code Form is subject to the terms of the Mozilla Public
* License, v. 2.0. If a copy of the MPL was not distributed with this file,
* You can obtain one at http://mozilla.org/MPL/2.0/.
*
* The origin of this IDL file is
* https://dvcs.w3.org/hg/audio/raw-file/tip/webaudio/specification.html
*
* Copyright © 2012 W3C® (MIT, ERCIM, Keio), All Rights Reserved. W3C
* liability, trademark and document use rules apply.
*/
interface StereoPannerNode : AudioNode {
readonly attribute AudioParam pan;
};
// Mozilla extension
StereoPannerNode implements AudioNodePassThrough;

Просмотреть файл

@ -374,6 +374,7 @@ WEBIDL_FILES = [
'SocketCommon.webidl',
'SourceBuffer.webidl',
'SourceBufferList.webidl',
'StereoPannerNode.webidl',
'Storage.webidl',
'StorageEvent.webidl',
'StorageType.webidl',

Просмотреть файл

@ -238,18 +238,6 @@ gfxContext::Fill(const Pattern& aPattern)
FillAzure(aPattern, 1.0f);
}
void
gfxContext::FillWithOpacity(gfxFloat aOpacity)
{
FillWithOpacity(PatternFromState(this), aOpacity);
}
void
gfxContext::FillWithOpacity(const Pattern& aPattern, gfxFloat aOpacity)
{
FillAzure(aPattern, Float(aOpacity));
}
void
gfxContext::MoveTo(const gfxPoint& pt)
{
@ -309,21 +297,6 @@ gfxContext::Rectangle(const gfxRect& rect, bool snapToPixels)
mPathBuilder->Close();
}
void
gfxContext::Polygon(const gfxPoint *points, uint32_t numPoints)
{
if (numPoints == 0) {
return;
}
EnsurePathBuilder();
mPathBuilder->MoveTo(ToPoint(points[0]));
for (uint32_t i = 1; i < numPoints; i++) {
mPathBuilder->LineTo(ToPoint(points[i]));
}
}
void
gfxContext::DrawSurface(gfxASurface *surface, const gfxSize& size)
{

Просмотреть файл

@ -108,15 +108,6 @@ public:
void Fill();
void Fill(const Pattern& aPattern);
/**
* Fill the current path according to the current settings and
* with |aOpacity|.
*
* Does not consume the current path.
*/
void FillWithOpacity(gfxFloat aOpacity);
void FillWithOpacity(const Pattern& aPattern, gfxFloat aOpacity);
/**
* Forgets the current path.
*/
@ -169,11 +160,6 @@ public:
void Rectangle(const gfxRect& rect, bool snapToPixels = false);
void SnappedRectangle(const gfxRect& rect) { return Rectangle(rect, true); }
/**
* Draw a polygon from the given points
*/
void Polygon(const gfxPoint *points, uint32_t numPoints);
/**
** Transformation Matrix manipulation
**/

Просмотреть файл

@ -200,6 +200,8 @@ gfxPatternDrawable::Draw(gfxContext* aContext,
gfxFloat aOpacity,
const gfxMatrix& aTransform)
{
DrawTarget& aDrawTarget = *aContext->GetDrawTarget();
if (!mPattern)
return false;
@ -216,12 +218,11 @@ gfxPatternDrawable::Draw(gfxContext* aContext,
aOpacity, aTransform);
}
aContext->NewPath();
gfxMatrix oldMatrix = mPattern->GetMatrix();
mPattern->SetMatrix(aTransform * oldMatrix);
aContext->SetPattern(mPattern);
aContext->Rectangle(aFillRect);
aContext->FillWithOpacity(aOpacity);
DrawOptions drawOptions(aOpacity);
aDrawTarget.FillRect(ToRect(aFillRect),
*mPattern->GetPattern(&aDrawTarget), drawOptions);
mPattern->SetMatrix(oldMatrix);
return true;
}

Просмотреть файл

@ -9,11 +9,6 @@
#include "nsTArrayForwardDeclare.h"
#include "gfxPlatform.h"
#define MAC_OS_X_VERSION_10_6_HEX 0x00001060
#define MAC_OS_X_VERSION_10_7_HEX 0x00001070
#define MAC_OS_X_MAJOR_VERSION_MASK 0xFFFFFFF0U
namespace mozilla { namespace gfx { class DrawTarget; }}
class gfxPlatformMac : public gfxPlatform {

Просмотреть файл

@ -1552,6 +1552,8 @@ gfxWindowsPlatform::GetDXGIAdapter()
return mAdapter;
}
#define TEXTURE_SIZE 32
// See bug 1083071. On some drivers, Direct3D 11 CreateShaderResourceView fails
// with E_OUTOFMEMORY.
bool DoesD3D11DeviceWork(ID3D11Device *device)
@ -1588,25 +1590,10 @@ bool DoesD3D11DeviceWork(ID3D11Device *device)
}
}
if (GetModuleHandleW(L"atidxx32.dll")) {
nsCOMPtr<nsIGfxInfo> gfxInfo = do_GetService("@mozilla.org/gfx/info;1");
if (gfxInfo) {
nsString vendorID, vendorID2;
gfxInfo->GetAdapterVendorID(vendorID);
gfxInfo->GetAdapterVendorID2(vendorID2);
if (vendorID.EqualsLiteral("0x8086") && vendorID2.IsEmpty()) {
#if defined(MOZ_CRASHREPORTER)
CrashReporter::AppendAppNotesToCrashReport(NS_LITERAL_CSTRING("Unexpected Intel/AMD dual-GPU setup\n"));
#endif
return false;
}
}
}
RefPtr<ID3D11Texture2D> texture;
D3D11_TEXTURE2D_DESC desc;
desc.Width = 32;
desc.Height = 32;
desc.Width = TEXTURE_SIZE;
desc.Height = TEXTURE_SIZE;
desc.MipLevels = 1;
desc.ArraySize = 1;
desc.Format = DXGI_FORMAT_B8G8R8A8_UNORM;
@ -1616,7 +1603,16 @@ bool DoesD3D11DeviceWork(ID3D11Device *device)
desc.CPUAccessFlags = 0;
desc.MiscFlags = D3D11_RESOURCE_MISC_SHARED_KEYEDMUTEX;
desc.BindFlags = D3D11_BIND_RENDER_TARGET | D3D11_BIND_SHADER_RESOURCE;
if (FAILED(device->CreateTexture2D(&desc, NULL, byRef(texture)))) {
int color[TEXTURE_SIZE * TEXTURE_SIZE];
D3D11_SUBRESOURCE_DATA data;
data.pSysMem = color;
data.SysMemPitch = TEXTURE_SIZE * 4;
data.SysMemSlicePitch = 0;
for (int i = 0; i < sizeof(color)/sizeof(color[0]); i++) {
color[i] = 0xff00ffff;
}
if (FAILED(device->CreateTexture2D(&desc, &data, byRef(texture)))) {
return false;
}
@ -1646,6 +1642,47 @@ bool DoesD3D11DeviceWork(ID3D11Device *device)
return false;
}
desc.Usage = D3D11_USAGE_STAGING;
desc.CPUAccessFlags = D3D11_CPU_ACCESS_READ;
desc.MiscFlags = 0;
desc.BindFlags = 0;
RefPtr<ID3D11Texture2D> cpuTexture;
if (FAILED(device->CreateTexture2D(&desc, &data, byRef(cpuTexture)))) {
return false;
}
nsRefPtr<IDXGIKeyedMutex> sharedMutex;
nsRefPtr<ID3D11DeviceContext> deviceContext;
sharedResource->QueryInterface(__uuidof(IDXGIKeyedMutex), getter_AddRefs(sharedMutex));
device->GetImmediateContext(getter_AddRefs(deviceContext));
if (FAILED(sharedMutex->AcquireSync(0, 30*1000))) {
#if defined(MOZ_CRASHREPORTER)
CrashReporter::AppendAppNotesToCrashReport(NS_LITERAL_CSTRING("Keyed Mutex timeout\n"));
#endif
// only wait for 30 seconds
return false;
}
int resultColor;
deviceContext->CopyResource(cpuTexture, sharedTexture);
D3D11_MAPPED_SUBRESOURCE mapped;
deviceContext->Map(cpuTexture, 0, D3D11_MAP_READ, 0, &mapped);
resultColor = *(int*)mapped.pData;
deviceContext->Unmap(cpuTexture, 0);
sharedMutex->ReleaseSync(0);
if (resultColor != color[0]) {
// Shared surfaces seem to be broken on dual AMD & Intel HW when using the
// AMD GPU
#if defined(MOZ_CRASHREPORTER)
CrashReporter::AppendAppNotesToCrashReport(NS_LITERAL_CSTRING("Shared Surfaces don't work\n"));
#endif
return false;
}
RefPtr<ID3D11ShaderResourceView> sharedView;
// This if(FAILED()) is the one that actually fails on systems affected by bug 1083071.

Просмотреть файл

@ -218,6 +218,19 @@ SVGDocumentWrapper::SetCurrentTime(float aTime)
}
}
void
SVGDocumentWrapper::TickRefreshDriver()
{
nsCOMPtr<nsIPresShell> presShell;
mViewer->GetPresShell(getter_AddRefs(presShell));
if (presShell) {
nsPresContext* presContext = presShell->GetPresContext();
if (presContext) {
presContext->RefreshDriver()->DoTick();
}
}
}
/** nsIStreamListener methods **/
/* void onDataAvailable (in nsIRequest request, in nsISupports ctxt,

Просмотреть файл

@ -137,6 +137,7 @@ public:
void ResetAnimation();
float GetCurrentTime();
void SetCurrentTime(float aTime);
void TickRefreshDriver();
/**
* Force a layout flush of the underlying SVG document.

Просмотреть файл

@ -506,9 +506,10 @@ VectorImage::RequestRefresh(const TimeStamp& aTime)
return;
}
// TODO: Implement for b666446.
EvaluateAnimation();
mSVGDocumentWrapper->TickRefreshDriver();
if (mHasPendingInvalidation) {
SendInvalidationNotifications();
mHasPendingInvalidation = false;

Просмотреть файл

@ -129,6 +129,10 @@ PrincipalToPrincipalInfo(nsIPrincipal* aPrincipal,
return rv;
}
if (NS_WARN_IF(!uri)) {
return NS_ERROR_FAILURE;
}
nsCString spec;
rv = uri->GetSpec(spec);
if (NS_WARN_IF(NS_FAILED(rv))) {

Просмотреть файл

@ -326,6 +326,7 @@ selfhosting_srcs := \
$(srcdir)/builtin/Object.js \
$(srcdir)/builtin/String.js \
$(srcdir)/builtin/Set.js \
$(srcdir)/builtin/TypedArray.js \
$(srcdir)/builtin/TypedObject.js \
$(srcdir)/builtin/WeakSet.js \
$(NULL)

Просмотреть файл

@ -762,29 +762,6 @@ AsmJSModule::staticallyLink(ExclusiveContext *cx)
MOZ_ASSERT(isStaticallyLinked());
}
#if defined(JS_CODEGEN_X86) || defined(JS_CODEGEN_X64)
static inline size_t
ViewTypeByteSize(AsmJSHeapAccess::ViewType vt)
{
switch (vt) {
case AsmJSHeapAccess::Int8:
case AsmJSHeapAccess::Uint8:
case AsmJSHeapAccess::Uint8Clamped:
case AsmJSHeapAccess::Int16:
case AsmJSHeapAccess::Uint16:
case AsmJSHeapAccess::Int32:
case AsmJSHeapAccess::Uint32:
case AsmJSHeapAccess::Float32:
case AsmJSHeapAccess::Float64:
return 1 << TypedArrayShift(Scalar::Type(vt));
case AsmJSHeapAccess::Float32x4:
case AsmJSHeapAccess::Int32x4:
return 16;
}
MOZ_CRASH("unexpected view type");
}
#endif // JS_CODEGEN_X86 || JS_CODEGEN_X64
void
AsmJSModule::initHeap(Handle<ArrayBufferObjectMaybeShared *> heap, JSContext *cx)
{
@ -805,9 +782,9 @@ AsmJSModule::initHeap(Handle<ArrayBufferObjectMaybeShared *> heap, JSContext *cx
// ptr + data-type-byte-size > heapLength
// i.e. ptr >= heapLength + 1 - data-type-byte-size
// (Note that we need >= as this is what codegen uses.)
AsmJSHeapAccess::ViewType vt = access.viewType();
size_t scalarByteSize = 1 << TypedArrayShift(access.type());
X86Assembler::setPointer(access.patchLengthAt(code_),
(void*)(heap->byteLength() + 1 - ViewTypeByteSize(vt)));
(void*)(heap->byteLength() + 1 - scalarByteSize));
}
void *addr = access.patchOffsetAt(code_);
uint32_t disp = reinterpret_cast<uint32_t>(X86Assembler::getPointer(addr));
@ -827,8 +804,8 @@ AsmJSModule::initHeap(Handle<ArrayBufferObjectMaybeShared *> heap, JSContext *cx
const jit::AsmJSHeapAccess &access = heapAccesses_[i];
if (access.hasLengthCheck()) {
// See comment above for x86 codegen.
X86Assembler::setInt32(access.patchLengthAt(code_),
heapLength + 1 - ViewTypeByteSize(access.viewType()));
size_t scalarByteSize = 1 << TypedArrayShift(access.type());
X86Assembler::setInt32(access.patchLengthAt(code_), heapLength + 1 - scalarByteSize);
}
}
#elif defined(JS_CODEGEN_ARM) || defined(JS_CODEGEN_MIPS)

Просмотреть файл

@ -331,10 +331,10 @@ ContextToPC(CONTEXT *context)
#if defined(JS_CODEGEN_X64)
template <class T>
static void
SetXMMRegToNaN(AsmJSHeapAccess::ViewType viewType, T *xmm_reg)
SetXMMRegToNaN(Scalar::Type viewType, T *xmm_reg)
{
switch (viewType) {
case AsmJSHeapAccess::Float32: {
case Scalar::Float32: {
JS_STATIC_ASSERT(sizeof(T) == 4 * sizeof(float));
float *floats = reinterpret_cast<float*>(xmm_reg);
floats[0] = GenericNaN();
@ -343,41 +343,42 @@ SetXMMRegToNaN(AsmJSHeapAccess::ViewType viewType, T *xmm_reg)
floats[3] = 0;
break;
}
case AsmJSHeapAccess::Float64: {
case Scalar::Float64: {
JS_STATIC_ASSERT(sizeof(T) == 2 * sizeof(double));
double *dbls = reinterpret_cast<double*>(xmm_reg);
dbls[0] = GenericNaN();
dbls[1] = 0;
break;
}
case AsmJSHeapAccess::Float32x4: {
case Scalar::Float32x4: {
JS_STATIC_ASSERT(sizeof(T) == 4 * sizeof(float));
float *floats = reinterpret_cast<float*>(xmm_reg);
for (unsigned i = 0; i < 4; i++)
floats[i] = GenericNaN();
break;
}
case AsmJSHeapAccess::Int32x4: {
case Scalar::Int32x4: {
JS_STATIC_ASSERT(sizeof(T) == 4 * sizeof(int32_t));
int32_t *ints = reinterpret_cast<int32_t*>(xmm_reg);
for (unsigned i = 0; i < 4; i++)
ints[i] = 0;
break;
}
case AsmJSHeapAccess::Int8:
case AsmJSHeapAccess::Uint8:
case AsmJSHeapAccess::Int16:
case AsmJSHeapAccess::Uint16:
case AsmJSHeapAccess::Int32:
case AsmJSHeapAccess::Uint32:
case AsmJSHeapAccess::Uint8Clamped:
case Scalar::Int8:
case Scalar::Uint8:
case Scalar::Int16:
case Scalar::Uint16:
case Scalar::Int32:
case Scalar::Uint32:
case Scalar::Uint8Clamped:
case Scalar::MaxTypedArrayViewType:
MOZ_CRASH("unexpected type in SetXMMRegToNaN");
}
}
# if !defined(XP_MACOSX)
static void
SetRegisterToCoercedUndefined(CONTEXT *context, AsmJSHeapAccess::ViewType viewType, AnyRegister reg)
SetRegisterToCoercedUndefined(CONTEXT *context, Scalar::Type viewType, AnyRegister reg)
{
if (reg.isFloat()) {
switch (reg.fpu().code()) {
@ -482,7 +483,7 @@ HandleFault(PEXCEPTION_POINTERS exception)
// register) and set the PC to the next op. Upon return from the handler,
// execution will resume at this next PC.
if (heapAccess->isLoad())
SetRegisterToCoercedUndefined(context, heapAccess->viewType(), heapAccess->loadedReg());
SetRegisterToCoercedUndefined(context, heapAccess->type(), heapAccess->loadedReg());
*ppc += heapAccess->opLength();
return true;
@ -532,7 +533,7 @@ SetRegisterToCoercedUndefined(mach_port_t rtThread, x86_thread_state64_t &state,
if (kret != KERN_SUCCESS)
return false;
AsmJSHeapAccess::ViewType viewType = heapAccess.viewType();
Scalar::Type viewType = heapAccess.type();
switch (heapAccess.loadedReg().fpu().code()) {
case X86Registers::xmm0: SetXMMRegToNaN(viewType, &fstate.__fpu_xmm0); break;
case X86Registers::xmm1: SetXMMRegToNaN(viewType, &fstate.__fpu_xmm1); break;
@ -874,7 +875,7 @@ HandleFault(int signum, siginfo_t *info, void *ctx)
// register) and set the PC to the next op. Upon return from the handler,
// execution will resume at this next PC.
if (heapAccess->isLoad())
SetRegisterToCoercedUndefined(context, heapAccess->viewType(), heapAccess->loadedReg());
SetRegisterToCoercedUndefined(context, heapAccess->type(), heapAccess->loadedReg());
*ppc += heapAccess->opLength();
return true;

Просмотреть файл

@ -2756,7 +2756,7 @@ class FunctionCompiler
curBlock_->setSlot(info().localSlot(local.slot), def);
}
MDefinition *loadHeap(AsmJSHeapAccess::ViewType vt, MDefinition *ptr, NeedsBoundsCheck chk)
MDefinition *loadHeap(Scalar::Type vt, MDefinition *ptr, NeedsBoundsCheck chk)
{
if (inDeadCode())
return nullptr;
@ -2767,8 +2767,7 @@ class FunctionCompiler
return load;
}
void storeHeap(AsmJSHeapAccess::ViewType vt, MDefinition *ptr, MDefinition *v,
NeedsBoundsCheck chk)
void storeHeap(Scalar::Type vt, MDefinition *ptr, MDefinition *v, NeedsBoundsCheck chk)
{
if (inDeadCode())
return;
@ -2786,7 +2785,7 @@ class FunctionCompiler
curBlock_->add(ins);
}
MDefinition *atomicLoadHeap(AsmJSHeapAccess::ViewType vt, MDefinition *ptr, NeedsBoundsCheck chk)
MDefinition *atomicLoadHeap(Scalar::Type vt, MDefinition *ptr, NeedsBoundsCheck chk)
{
if (inDeadCode())
return nullptr;
@ -2798,8 +2797,7 @@ class FunctionCompiler
return load;
}
void atomicStoreHeap(AsmJSHeapAccess::ViewType vt, MDefinition *ptr, MDefinition *v,
NeedsBoundsCheck chk)
void atomicStoreHeap(Scalar::Type vt, MDefinition *ptr, MDefinition *v, NeedsBoundsCheck chk)
{
if (inDeadCode())
return;
@ -2810,8 +2808,8 @@ class FunctionCompiler
curBlock_->add(store);
}
MDefinition *atomicCompareExchangeHeap(AsmJSHeapAccess::ViewType vt, MDefinition *ptr,
MDefinition *oldv, MDefinition *newv, NeedsBoundsCheck chk)
MDefinition *atomicCompareExchangeHeap(Scalar::Type vt, MDefinition *ptr, MDefinition *oldv,
MDefinition *newv, NeedsBoundsCheck chk)
{
if (inDeadCode())
return nullptr;
@ -2824,8 +2822,8 @@ class FunctionCompiler
return cas;
}
MDefinition *atomicBinopHeap(js::jit::AtomicOp op, AsmJSHeapAccess::ViewType vt,
MDefinition *ptr, MDefinition *v, NeedsBoundsCheck chk)
MDefinition *atomicBinopHeap(js::jit::AtomicOp op, Scalar::Type vt, MDefinition *ptr,
MDefinition *v, NeedsBoundsCheck chk)
{
if (inDeadCode())
return nullptr;
@ -4453,7 +4451,7 @@ CheckLoadArray(FunctionCompiler &f, ParseNode *elem, MDefinition **def, Type *ty
if (!CheckArrayAccess(f, ElemBase(elem), ElemIndex(elem), &viewType, &pointerDef, &needsBoundsCheck))
return false;
*def = f.loadHeap(AsmJSHeapAccess::ViewType(viewType), pointerDef, needsBoundsCheck);
*def = f.loadHeap(viewType, pointerDef, needsBoundsCheck);
*type = TypedArrayLoadType(viewType);
return true;
}
@ -4547,7 +4545,7 @@ CheckStoreArray(FunctionCompiler &f, ParseNode *lhs, ParseNode *rhs, MDefinition
MOZ_CRASH("Unexpected view type");
}
f.storeHeap(AsmJSHeapAccess::ViewType(viewType), pointerDef, rhsDef, needsBoundsCheck);
f.storeHeap(viewType, pointerDef, rhsDef, needsBoundsCheck);
*def = rhsDef;
*type = rhsType;
@ -4815,7 +4813,7 @@ CheckAtomicsLoad(FunctionCompiler &f, ParseNode *call, MDefinition **def, Type *
if (!CheckSharedArrayAtomicAccess(f, arrayArg, indexArg, &viewType, &pointerDef, &needsBoundsCheck))
return false;
*def = f.atomicLoadHeap(AsmJSHeapAccess::ViewType(viewType), pointerDef, needsBoundsCheck);
*def = f.atomicLoadHeap(viewType, pointerDef, needsBoundsCheck);
*type = Type::Signed;
return true;
}
@ -4844,7 +4842,7 @@ CheckAtomicsStore(FunctionCompiler &f, ParseNode *call, MDefinition **def, Type
if (!rhsType.isIntish())
return f.failf(arrayArg, "%s is not a subtype of intish", rhsType.toChars());
f.atomicStoreHeap(AsmJSHeapAccess::ViewType(viewType), pointerDef, rhsDef, needsBoundsCheck);
f.atomicStoreHeap(viewType, pointerDef, rhsDef, needsBoundsCheck);
*def = rhsDef;
*type = Type::Signed;
@ -4875,8 +4873,7 @@ CheckAtomicsBinop(FunctionCompiler &f, ParseNode *call, MDefinition **def, Type
if (!valueArgType.isIntish())
return f.failf(valueArg, "%s is not a subtype of intish", valueArgType.toChars());
*def = f.atomicBinopHeap(op, AsmJSHeapAccess::ViewType(viewType), pointerDef, valueArgDef,
needsBoundsCheck);
*def = f.atomicBinopHeap(op, viewType, pointerDef, valueArgDef, needsBoundsCheck);
*type = Type::Signed;
return true;
}
@ -4914,8 +4911,8 @@ CheckAtomicsCompareExchange(FunctionCompiler &f, ParseNode *call, MDefinition **
if (!newValueArgType.isIntish())
return f.failf(newValueArg, "%s is not a subtype of intish", newValueArgType.toChars());
*def = f.atomicCompareExchangeHeap(AsmJSHeapAccess::ViewType(viewType), pointerDef,
oldValueArgDef, newValueArgDef, needsBoundsCheck);
*def = f.atomicCompareExchangeHeap(viewType, pointerDef, oldValueArgDef, newValueArgDef,
needsBoundsCheck);
*type = Type::Signed;
return true;
}
@ -5615,7 +5612,7 @@ CheckSimdShuffle(FunctionCompiler &f, ParseNode *call, AsmJSSimdType opType, MDe
static bool
CheckSimdLoadStoreArgs(FunctionCompiler &f, ParseNode *call, AsmJSSimdType opType,
AsmJSHeapAccess::ViewType *viewType, MDefinition **index,
Scalar::Type *viewType, MDefinition **index,
NeedsBoundsCheck *needsBoundsCheck)
{
ParseNode *view = CallArgList(call);
@ -5633,8 +5630,8 @@ CheckSimdLoadStoreArgs(FunctionCompiler &f, ParseNode *call, AsmJSSimdType opTyp
*needsBoundsCheck = NEEDS_BOUNDS_CHECK;
switch (opType) {
case AsmJSSimdType_int32x4: *viewType = AsmJSHeapAccess::Int32x4; break;
case AsmJSSimdType_float32x4: *viewType = AsmJSHeapAccess::Float32x4; break;
case AsmJSSimdType_int32x4: *viewType = Scalar::Int32x4; break;
case AsmJSSimdType_float32x4: *viewType = Scalar::Float32x4; break;
}
ParseNode *indexExpr = NextNode(view);
@ -5674,7 +5671,7 @@ CheckSimdLoad(FunctionCompiler &f, ParseNode *call, AsmJSSimdType opType, MDefin
if (numArgs != 2)
return f.failf(call, "expected 2 arguments to SIMD load, got %u", numArgs);
AsmJSHeapAccess::ViewType viewType;
Scalar::Type viewType;
MDefinition *index;
NeedsBoundsCheck needsBoundsCheck;
if (!CheckSimdLoadStoreArgs(f, call, opType, &viewType, &index, &needsBoundsCheck))
@ -5692,7 +5689,7 @@ CheckSimdStore(FunctionCompiler &f, ParseNode *call, AsmJSSimdType opType, MDefi
if (numArgs != 3)
return f.failf(call, "expected 3 arguments to SIMD load, got %u", numArgs);
AsmJSHeapAccess::ViewType viewType;
Scalar::Type viewType;
MDefinition *index;
NeedsBoundsCheck needsBoundsCheck;
if (!CheckSimdLoadStoreArgs(f, call, opType, &viewType, &index, &needsBoundsCheck))

Просмотреть файл

@ -8,13 +8,13 @@ function StarGeneratorNext(val) {
// common case with a single call. It's also inlined in Baseline.
if (!IsSuspendedStarGenerator(this)) {
if (!IsObject(this) || !IsStarGeneratorObject(this))
if (!IsObject(this) || !IsStarGeneratorObject(this))
return callFunction(CallStarGeneratorMethodIfWrapped, this, val, "StarGeneratorNext");
if (StarGeneratorObjectIsClosed(this))
if (StarGeneratorObjectIsClosed(this))
return { value: undefined, done: true };
if (GeneratorIsRunning(this))
if (GeneratorIsRunning(this))
ThrowError(JSMSG_NESTING_GENERATOR);
}
@ -29,13 +29,13 @@ function StarGeneratorNext(val) {
function StarGeneratorThrow(val) {
if (!IsSuspendedStarGenerator(this)) {
if (!IsObject(this) || !IsStarGeneratorObject(this))
if (!IsObject(this) || !IsStarGeneratorObject(this))
return callFunction(CallStarGeneratorMethodIfWrapped, this, val, "StarGeneratorThrow");
if (StarGeneratorObjectIsClosed(this))
if (StarGeneratorObjectIsClosed(this))
throw val;
if (GeneratorIsRunning(this))
if (GeneratorIsRunning(this))
ThrowError(JSMSG_NESTING_GENERATOR);
}

Просмотреть файл

@ -63,6 +63,9 @@ GetBuildConfiguration(JSContext *cx, unsigned argc, jsval *vp)
if (!JS_SetProperty(cx, info, "exact-rooting", TrueHandleValue))
return false;
if (!JS_SetProperty(cx, info, "trace-jscalls-api", FalseHandleValue))
return false;
RootedValue value(cx);
#ifdef DEBUG
value = BooleanValue(true);
@ -144,14 +147,6 @@ GetBuildConfiguration(JSContext *cx, unsigned argc, jsval *vp)
if (!JS_SetProperty(cx, info, "dtrace", value))
return false;
#ifdef MOZ_TRACE_JSCALLS
value = BooleanValue(true);
#else
value = BooleanValue(false);
#endif
if (!JS_SetProperty(cx, info, "trace-jscalls-api", value))
return false;
#ifdef JSGC_INCREMENTAL
value = BooleanValue(true);
#else

Просмотреть файл

@ -0,0 +1,75 @@
/* This Source Code Form is subject to the terms of the Mozilla Public
* License, v. 2.0. If a copy of the MPL was not distributed with this
* file, You can obtain one at http://mozilla.org/MPL/2.0/. */
// ES6 draft rev28 (2014/10/14) 22.2.3.10 %TypedArray%.prototype.find(predicate [,thisArg]).
function TypedArrayFind(predicate, thisArg = undefined) {
// This function is not generic.
if (!IsObject(this) || !IsTypedArray(this)) {
return callFunction(CallTypedArrayMethodIfWrapped, this, predicate, thisArg,
"TypedArrayFind");
}
// Steps 1-2.
var O = this;
// Steps 3-5.
var len = TypedArrayLength(O);
// Step 6.
if (arguments.length === 0)
ThrowError(JSMSG_MISSING_FUN_ARG, 0, "%TypedArray%.prototype.find");
if (!IsCallable(predicate))
ThrowError(JSMSG_NOT_FUNCTION, DecompileArg(0, predicate));
// Step 7.
var T = thisArg;
// Steps 8-9. */
// Steps a (implicit), and g.
for (var k = 0; k < len; k++) {
// Steps a-c.
var kValue = O[k];
// Steps d-f.
if (callFunction(predicate, T, kValue, k, O))
return kValue;
}
// Step 10.
return undefined;
}
// ES6 draft rev28 (2014/10/14) 22.2.3.11 %TypedArray%.prototype.findIndex(predicate [,thisArg]).
function TypedArrayFindIndex(predicate, thisArg = undefined) {
// This function is not generic.
if (!IsObject(this) || !IsTypedArray(this)) {
return callFunction(CallTypedArrayMethodIfWrapped, this, predicate, thisArg,
"TypedArrayFindIndex");
}
// Steps 1-2.
var O = this;
// Steps 3-5.
var len = TypedArrayLength(O);
// Step 6.
if (arguments.length === 0)
ThrowError(JSMSG_MISSING_FUN_ARG, 0, "%TypedArray%.prototype.findIndex");
if (!IsCallable(predicate))
ThrowError(JSMSG_NOT_FUNCTION, DecompileArg(0, predicate));
// Step 7.
var T = thisArg;
// Steps 8-9.
// Steps a (implicit), and g.
for (var k = 0; k < len; k++) {
// Steps a-f.
if (callFunction(predicate, T, O[k], k, O))
return k;
}
// Step 10.
return -1;
}

Просмотреть файл

@ -277,7 +277,9 @@ ScalarTypeDescr::typeName(Type type)
case constant_: return #name_;
JS_FOR_EACH_SCALAR_TYPE_REPR(NUMERIC_TYPE_TO_STRING)
#undef NUMERIC_TYPE_TO_STRING
case Scalar::TypeMax:
case Scalar::Float32x4:
case Scalar::Int32x4:
case Scalar::MaxTypedArrayViewType:
MOZ_CRASH();
}
MOZ_CRASH("Invalid type");
@ -313,7 +315,9 @@ ScalarTypeDescr::call(JSContext *cx, unsigned argc, Value *vp)
JS_FOR_EACH_SCALAR_TYPE_REPR(SCALARTYPE_CALL)
#undef SCALARTYPE_CALL
case Scalar::TypeMax:
case Scalar::Float32x4:
case Scalar::Int32x4:
case Scalar::MaxTypedArrayViewType:
MOZ_CRASH();
}
return true;

Просмотреть файл

@ -267,6 +267,10 @@ class ScalarTypeDescr : public SimpleTypeDescr
"TypedObjectConstants.h must be consistent with Scalar::Type");
static_assert(Scalar::Uint8Clamped == JS_SCALARTYPEREPR_UINT8_CLAMPED,
"TypedObjectConstants.h must be consistent with Scalar::Type");
static_assert(Scalar::Float32x4 == JS_SCALARTYPEREPR_FLOAT32X4,
"TypedObjectConstants.h must be consistent with Scalar::Type");
static_assert(Scalar::Int32x4 == JS_SCALARTYPEREPR_INT32X4,
"TypedObjectConstants.h must be consistent with Scalar::Type");
return Type(getReservedSlot(JS_DESCR_SLOT_TYPE).toInt32());
}

Просмотреть файл

@ -68,6 +68,8 @@
#define JS_SCALARTYPEREPR_FLOAT32 6
#define JS_SCALARTYPEREPR_FLOAT64 7
#define JS_SCALARTYPEREPR_UINT8_CLAMPED 8
#define JS_SCALARTYPEREPR_FLOAT32X4 10
#define JS_SCALARTYPEREPR_INT32X4 11
// These constants are for use exclusively in JS code. In C++ code,
// prefer ReferenceTypeRepresentation::TYPE_ANY etc, which allows

Просмотреть файл

@ -3132,17 +3132,6 @@ MOZ_ARG_WITH_STRING(wrap-malloc,
[ --with-wrap-malloc=DIR Location of malloc wrapper library],
WRAP_LDFLAGS="${WRAP_LDFLAGS} $withval")
dnl ========================================================
dnl = Use JS Call tracing
dnl ========================================================
MOZ_ARG_ENABLE_BOOL(trace-jscalls,
[ --enable-trace-jscalls Enable JS call enter/exit callback (default=no)],
MOZ_TRACE_JSCALLS=1,
MOZ_TRACE_JSCALLS= )
if test -n "$MOZ_TRACE_JSCALLS"; then
AC_DEFINE(MOZ_TRACE_JSCALLS)
fi
dnl ========================================================
dnl = Use incremental GC
dnl ========================================================

Просмотреть файл

@ -257,7 +257,9 @@ the compartment to which the handler method belongs.
resumption value each handler returns establishes the completion value
reported to the next handler.
This property is ignored on `"debugger"` frames.
This handler is not called on `"debugger"` frames. It is also not called
when unwinding a frame due to an over-recursion or out-of-memory
exception.
`onResume`
: This property must be either `undefined` or a function. If it is a

Просмотреть файл

@ -151,6 +151,9 @@ compartment.
`continue`, or `break` statement, or a new exception. In those cases the
old exception does not continue to propagate; it is discarded.)
This handler is not called when unwinding a frame due to an over-recursion
or out-of-memory exception.
<code>sourceHandler(<i>ASuffusionOfYellow</i>)</code>
: This method is never called. If it is ever called, a contradiction has
been proven, and the debugger is free to assume that everything is true.

Просмотреть файл

@ -1075,8 +1075,8 @@ EmitAtomOp(ExclusiveContext *cx, JSAtom *atom, JSOp op, BytecodeEmitter *bce)
MOZ_ASSERT(JOF_OPTYPE(op) == JOF_ATOM);
// .generator lookups should be emitted as JSOP_GETALIASEDVAR instead of
// JSOP_NAME etc, to bypass |with| objects on the scope chain.
MOZ_ASSERT_IF(op == JSOP_NAME || op == JSOP_GETGNAME, atom != cx->names().dotGenerator);
// JSOP_GETNAME etc, to bypass |with| objects on the scope chain.
MOZ_ASSERT_IF(op == JSOP_GETNAME || op == JSOP_GETGNAME, atom != cx->names().dotGenerator);
if (op == JSOP_GETPROP && atom == cx->names().length) {
/* Specialize length accesses for the interpreter. */
@ -1554,7 +1554,7 @@ TryConvertFreeName(BytecodeEmitter *bce, ParseNode *pn)
if (bce->emitterMode == BytecodeEmitter::SelfHosting) {
JSOp op;
switch (pn->getOp()) {
case JSOP_NAME: op = JSOP_GETINTRINSIC; break;
case JSOP_GETNAME: op = JSOP_GETINTRINSIC; break;
case JSOP_SETNAME: op = JSOP_SETINTRINSIC; break;
/* Other *NAME ops aren't (yet) supported in self-hosted code. */
default: MOZ_CRASH("intrinsic");
@ -1608,7 +1608,7 @@ TryConvertFreeName(BytecodeEmitter *bce, ParseNode *pn)
if (LookupAliasedName(bce, script, pn->pn_atom->asPropertyName(), &slot, pn)) {
JSOp op;
switch (pn->getOp()) {
case JSOP_NAME: op = JSOP_GETALIASEDVAR; break;
case JSOP_GETNAME: op = JSOP_GETALIASEDVAR; break;
case JSOP_SETNAME: op = JSOP_SETALIASEDVAR; break;
default: return false;
}
@ -1661,7 +1661,7 @@ TryConvertFreeName(BytecodeEmitter *bce, ParseNode *pn)
JSOp op;
switch (pn->getOp()) {
case JSOP_NAME: op = JSOP_GETGNAME; break;
case JSOP_GETNAME: op = JSOP_GETGNAME; break;
case JSOP_SETNAME: op = StrictifySetNameOp(JSOP_SETGNAME, bce); break;
case JSOP_SETCONST:
// Not supported.
@ -1680,12 +1680,12 @@ TryConvertFreeName(BytecodeEmitter *bce, ParseNode *pn)
* The caller can test pn->pn_cookie.isFree() to tell whether optimization
* occurred, in which case BindNameToSlotHelper also updated pn->pn_op. If
* pn->pn_cookie.isFree() is still true on return, pn->pn_op still may have
* been optimized, e.g., from JSOP_NAME to JSOP_CALLEE. Whether or not
* been optimized, e.g., from JSOP_GETNAME to JSOP_CALLEE. Whether or not
* pn->pn_op was modified, if this function finds an argument or local variable
* name, PND_CONST will be set in pn_dflags for read-only properties after a
* successful return.
*
* NB: if you add more opcodes specialized from JSOP_NAME, etc., don't forget
* NB: if you add more opcodes specialized from JSOP_GETNAME, etc., don't forget
* to update the special cases in EmitFor (for-in) and EmitAssignment (= and
* op=, e.g. +=).
*/
@ -1723,7 +1723,7 @@ BindNameToSlotHelper(ExclusiveContext *cx, BytecodeEmitter *bce, ParseNode *pn)
// Throw an error on attempts to mutate const-declared bindings.
switch (op) {
case JSOP_NAME:
case JSOP_GETNAME:
case JSOP_SETCONST:
break;
default:
@ -1798,7 +1798,7 @@ BindNameToSlotHelper(ExclusiveContext *cx, BytecodeEmitter *bce, ParseNode *pn)
switch (dn->kind()) {
case Definition::ARG:
switch (op) {
case JSOP_NAME: op = JSOP_GETARG; break;
case JSOP_GETNAME: op = JSOP_GETARG; break;
case JSOP_SETNAME: op = JSOP_SETARG; break;
default: MOZ_CRASH("arg");
}
@ -1810,7 +1810,7 @@ BindNameToSlotHelper(ExclusiveContext *cx, BytecodeEmitter *bce, ParseNode *pn)
case Definition::CONST:
case Definition::LET:
switch (op) {
case JSOP_NAME: op = JSOP_GETLOCAL; break;
case JSOP_GETNAME: op = JSOP_GETLOCAL; break;
case JSOP_SETNAME: op = JSOP_SETLOCAL; break;
case JSOP_SETCONST: op = JSOP_SETLOCAL; break;
default: MOZ_CRASH("local");
@ -1833,7 +1833,7 @@ BindNameToSlotHelper(ExclusiveContext *cx, BytecodeEmitter *bce, ParseNode *pn)
MOZ_ASSERT(pn->pn_atom == fun->atom());
/*
* Leave pn->isOp(JSOP_NAME) if bce->fun is heavyweight to
* Leave pn->isOp(JSOP_GETNAME) if bce->fun is heavyweight to
* address two cases: a new binding introduced by eval, and
* assignment to the name in strict mode.
*
@ -2338,7 +2338,7 @@ EmitNameOp(ExclusiveContext *cx, BytecodeEmitter *bce, ParseNode *pn, bool callC
/* Need to provide |this| value for call */
if (callContext) {
if (op == JSOP_NAME && bce->needsImplicitThis()) {
if (op == JSOP_GETNAME && bce->needsImplicitThis()) {
if (!EmitAtomOp(cx, pn, JSOP_IMPLICITTHIS, bce))
return false;
} else {
@ -2469,7 +2469,7 @@ EmitNameIncDec(ExclusiveContext *cx, ParseNode *pn, BytecodeEmitter *bce)
if (!EmitAtomOp(cx, pn->pn_kid, global ? JSOP_BINDGNAME : JSOP_BINDNAME, bce)) // OBJ
return false;
if (!EmitAtomOp(cx, pn->pn_kid, global ? JSOP_GETGNAME : JSOP_NAME, bce)) // OBJ V
if (!EmitAtomOp(cx, pn->pn_kid, global ? JSOP_GETGNAME : JSOP_GETNAME, bce)) // OBJ V
return false;
if (Emit1(cx, bce, JSOP_POS) < 0) // OBJ N
return false;
@ -4037,7 +4037,7 @@ EmitAssignment(ExclusiveContext *cx, BytecodeEmitter *bce, ParseNode *lhs, JSOp
if (lhs->isOp(JSOP_CALLEE)) {
if (Emit1(cx, bce, JSOP_CALLEE) < 0)
return false;
} else if (lhs->isOp(JSOP_NAME) || lhs->isOp(JSOP_GETGNAME)) {
} else if (lhs->isOp(JSOP_GETNAME) || lhs->isOp(JSOP_GETGNAME)) {
if (!EmitIndex32(cx, lhs->getOp(), atomIndex, bce))
return false;
} else {

Просмотреть файл

@ -174,8 +174,8 @@ struct BytecodeEmitter
Normal,
/*
* Emit JSOP_GETINTRINSIC instead of JSOP_NAME and assert that
* JSOP_NAME and JSOP_*GNAME don't ever get emitted. See the comment
* Emit JSOP_GETINTRINSIC instead of JSOP_GETNAME and assert that
* JSOP_GETNAME and JSOP_*GNAME don't ever get emitted. See the comment
* for the field |selfHostingMode| in Parser.h for details.
*/
SelfHosting,

Просмотреть файл

@ -87,7 +87,7 @@ class FullParseHandler
const Token &currentToken() { return tokenStream.currentToken(); }
ParseNode *newName(PropertyName *name, uint32_t blockid, const TokenPos &pos) {
return new_<NameNode>(PNK_NAME, JSOP_NAME, name, blockid, pos);
return new_<NameNode>(PNK_NAME, JSOP_GETNAME, name, blockid, pos);
}
ParseNode *newComputedName(ParseNode *expr, uint32_t begin, uint32_t end) {
@ -371,7 +371,7 @@ class FullParseHandler
if (!makeGen)
return false;
MOZ_ASSERT(genName->getOp() == JSOP_NAME);
MOZ_ASSERT(genName->getOp() == JSOP_GETNAME);
genName->setOp(JSOP_SETNAME);
genName->markAsAssigned();
ParseNode *genInit = newBinary(PNK_ASSIGN, genName, makeGen);

Просмотреть файл

@ -400,8 +400,8 @@ enum ParseNodeKind
* PNK_COMPUTED_NAME unary ES6 ComputedPropertyName.
* pn_kid: the AssignmentExpression inside the square brackets
* PNK_NAME, name pn_atom: name, string, or object atom
* PNK_STRING pn_op: JSOP_NAME, JSOP_STRING, or JSOP_OBJECT
* If JSOP_NAME, pn_op may be JSOP_*ARG or JSOP_*VAR
* PNK_STRING pn_op: JSOP_GETNAME, JSOP_STRING, or JSOP_OBJECT
* If JSOP_GETNAME, pn_op may be JSOP_*ARG or JSOP_*VAR
* with pn_cookie telling (staticLevel, slot) (see
* jsscript.h's UPVAR macros) and pn_dflags telling
* const-ness and static analysis results

Просмотреть файл

@ -1169,7 +1169,7 @@ Parser<FullParseHandler>::makeDefIntoUse(Definition *dn, ParseNode *pn, JSAtom *
MOZ_ASSERT(dn->isKind(PNK_NAME));
MOZ_ASSERT(dn->isArity(PN_NAME));
MOZ_ASSERT(dn->pn_atom == atom);
dn->setOp((js_CodeSpec[dn->getOp()].format & JOF_SET) ? JSOP_SETNAME : JSOP_NAME);
dn->setOp((js_CodeSpec[dn->getOp()].format & JOF_SET) ? JSOP_SETNAME : JSOP_GETNAME);
dn->setDefn(false);
dn->setUsed(true);
dn->pn_lexdef = (Definition *) pn;
@ -3156,8 +3156,8 @@ Parser<ParseHandler>::bindVarOrGlobalConst(BindData<ParseHandler> *data,
Node pn = data->pn;
bool isConstDecl = data->op == JSOP_DEFCONST;
/* Default best op for pn is JSOP_NAME; we'll try to improve below. */
parser->handler.setOp(pn, JSOP_NAME);
/* Default best op for pn is JSOP_GETNAME; we'll try to improve below. */
parser->handler.setOp(pn, JSOP_GETNAME);
if (!parser->checkStrictBinding(name, pn))
return false;
@ -6779,7 +6779,7 @@ Parser<FullParseHandler>::legacyComprehensionTail(ParseNode *bodyExpr, unsigned
name = tokenStream.currentName();
/*
* Create a name node with pn_op JSOP_NAME. We can't set pn_op to
* Create a name node with pn_op JSOP_GETNAME. We can't set pn_op to
* JSOP_GETLOCAL here, because we don't yet know the block's depth
* in the operand stack frame. The code generator computes that,
* and it tries to bind all names to slots, so we must let it do

Просмотреть файл

@ -38,15 +38,6 @@ using mozilla::ArrayLength;
using mozilla::PodCopy;
using mozilla::PodZero;
//#define PROFILE_NURSERY
#ifdef PROFILE_NURSERY
/*
* Print timing information for minor GCs that take longer than this time in microseconds.
*/
static int64_t GCReportThreshold = INT64_MAX;
#endif
bool
js::Nursery::init(uint32_t maxNurseryBytes)
{
@ -72,11 +63,16 @@ js::Nursery::init(uint32_t maxNurseryBytes)
setCurrentChunk(0);
updateDecommittedRegion();
#ifdef PROFILE_NURSERY
char *env = getenv("JS_MINORGC_TIME");
if (env)
GCReportThreshold = atoi(env);
#endif
char *env = getenv("JS_GC_PROFILE_NURSERY");
if (env) {
if (0 == strcmp(env, "help")) {
fprintf(stderr, "JS_GC_PROFILE_NURSERY=N\n\n"
"\tReport minor GC's taking more than N microseconds.");
exit(0);
}
enableProfiling_ = true;
profileThreshold_ = atoi(env);
}
MOZ_ASSERT(isEnabled());
return true;
@ -726,15 +722,9 @@ js::Nursery::MinorGCCallback(JSTracer *jstrc, void **thingp, JSGCTraceKind kind)
*thingp = trc->nursery->moveToTenured(trc, static_cast<JSObject *>(*thingp));
}
#ifdef PROFILE_NURSERY
#define TIME_START(name) int64_t timstampStart_##name = PRMJ_Now()
#define TIME_END(name) int64_t timstampEnd_##name = PRMJ_Now()
#define TIME_START(name) int64_t timstampStart_##name = enableProfiling_ ? PRMJ_Now() : 0
#define TIME_END(name) int64_t timstampEnd_##name = enableProfiling_ ? PRMJ_Now() : 0
#define TIME_TOTAL(name) (timstampEnd_##name - timstampStart_##name)
#else
#define TIME_START(name)
#define TIME_END(name)
#define TIME_TOTAL(name)
#endif
void
js::Nursery::collect(JSRuntime *rt, JS::gcreason::Reason reason, TypeObjectList *pretenureTypes)
@ -886,10 +876,8 @@ js::Nursery::collect(JSRuntime *rt, JS::gcreason::Reason reason, TypeObjectList
TraceMinorGCEnd();
#ifdef PROFILE_NURSERY
int64_t totalTime = TIME_TOTAL(total);
if (totalTime >= GCReportThreshold) {
if (enableProfiling_ && totalTime >= profileThreshold_) {
static bool printedHeader = false;
if (!printedHeader) {
fprintf(stderr,
@ -925,7 +913,6 @@ js::Nursery::collect(JSRuntime *rt, JS::gcreason::Reason reason, TypeObjectList
TIME_TOTAL(sweep));
#undef FMT
}
#endif
}
#undef TIME_START

Просмотреть файл

@ -67,7 +67,9 @@ class Nursery
heapEnd_(0),
currentChunk_(0),
numActiveChunks_(0),
numNurseryChunks_(0)
numNurseryChunks_(0),
profileThreshold_(0),
enableProfiling_(false)
{}
~Nursery();
@ -203,6 +205,10 @@ class Nursery
/* Number of chunks allocated for the nursery. */
int numNurseryChunks_;
/* Report minor collections taking more than this many us, if enabled. */
int64_t profileThreshold_;
bool enableProfiling_;
/*
* The set of externally malloced slots potentially kept live by objects
* stored in the nursery. Any external slots that do not belong to a

Просмотреть файл

@ -285,19 +285,27 @@ ZoneList::ZoneList(Zone *zone)
zone->listNext_ = nullptr;
}
ZoneList::~ZoneList()
{
MOZ_ASSERT(isEmpty());
}
void
ZoneList::check() const
{
#ifdef DEBUG
MOZ_ASSERT((head == nullptr) == (tail == nullptr));
if (head) {
Zone *zone = head;
while (zone != tail) {
zone = zone->listNext_;
MOZ_ASSERT(zone);
}
MOZ_ASSERT(!zone->listNext_);
if (!head)
return;
Zone *zone = head;
for (;;) {
MOZ_ASSERT(zone && zone->isOnList());
if (zone == tail)
break;
zone = zone->listNext_;
}
MOZ_ASSERT(!zone->listNext_);
#endif
}
@ -310,18 +318,20 @@ Zone *
ZoneList::front() const
{
MOZ_ASSERT(!isEmpty());
MOZ_ASSERT(head->isOnList());
return head;
}
void
ZoneList::append(Zone *zone)
{
MOZ_ASSERT(!zone->isOnList());
ZoneList singleZone(zone);
append(singleZone);
transferFrom(singleZone);
}
void
ZoneList::append(ZoneList &other)
ZoneList::transferFrom(ZoneList &other)
{
check();
other.check();
@ -332,9 +342,12 @@ ZoneList::append(ZoneList &other)
else
head = other.head;
tail = other.tail;
other.head = nullptr;
other.tail = nullptr;
}
Zone *
void
ZoneList::removeFront()
{
MOZ_ASSERT(!isEmpty());
@ -346,17 +359,4 @@ ZoneList::removeFront()
tail = nullptr;
front->listNext_ = Zone::NotOnList;
return front;
}
void
ZoneList::transferFrom(ZoneList& other)
{
MOZ_ASSERT(isEmpty());
other.check();
head = other.head;
tail = other.tail;
other.head = nullptr;
other.tail = nullptr;
}

Просмотреть файл

@ -0,0 +1,13 @@
/*
* Any copyright is dedicated to the Public Domain.
* https://creativecommons.org/publicdomain/zero/1.0/
*/
var global = newGlobal();
var array = global.Int8Array(10);
assertEq(array.find(v => v == 1), undefined)
assertEq(array.findIndex(v => v == 0), 0)
if (typeof reportCompare === "function")
reportCompare(true, true);

Просмотреть файл

@ -0,0 +1,11 @@
// |jit-test| allow-oom
g = newGlobal()
g.parent = this
g.eval("Debugger(parent).onExceptionUnwind=(function(){})")
gcparam("maxBytes", gcparam("gcBytes"))
function f() {
f()
y(arguments)
}
f()

Просмотреть файл

@ -1,25 +0,0 @@
enableOsiPointRegisterChecks();
gczeal(4);
eval("(function() { " + "\
for ( var CHARCODE = 1024; CHARCODE < 65536; CHARCODE+= 1234 ) {\
unescape( '%u'+(ToUnicodeString(CHARCODE)).substring(0,3) )\
}\
function ToUnicodeString( n ) {\
var string = ToHexString(n);\
return string;\
}\
function ToHexString( n ) {\
var hex = new Array();\
for ( var mag = 1; Math.pow(16,mag) <= n ; mag++ ) {}\
for ( index = 0, mag -= 1; mag > 0; index++, mag-- ) {\
hex[index] = Math.floor( n / Math.pow(16,mag) );\
var string ='';\
string <<= 'A';\
string += hex[index];\
}\
if ( 'var MYVAR=Number.NEGATIVE_INFINITY;MYVAR++;MYVAR' )\
string = '0' + string;\
return string;\
}\
" + " })();");

Просмотреть файл

@ -2265,7 +2265,7 @@ BaselineCompiler::emit_JSOP_SETALIASEDVAR()
}
bool
BaselineCompiler::emit_JSOP_NAME()
BaselineCompiler::emit_JSOP_GETNAME()
{
frame.syncStack(0);

Просмотреть файл

@ -129,7 +129,7 @@ namespace jit {
_(JSOP_GETXPROP) \
_(JSOP_GETALIASEDVAR) \
_(JSOP_SETALIASEDVAR) \
_(JSOP_NAME) \
_(JSOP_GETNAME) \
_(JSOP_BINDNAME) \
_(JSOP_DELNAME) \
_(JSOP_GETINTRINSIC) \

Просмотреть файл

@ -6145,7 +6145,7 @@ DoGetNameFallback(JSContext *cx, BaselineFrame *frame, ICGetName_Fallback *stub_
mozilla::DebugOnly<JSOp> op = JSOp(*pc);
FallbackICSpew(cx, stub, "GetName(%s)", js_CodeName[JSOp(*pc)]);
MOZ_ASSERT(op == JSOP_NAME || op == JSOP_GETGNAME);
MOZ_ASSERT(op == JSOP_GETNAME || op == JSOP_GETGNAME);
RootedPropertyName name(cx, script->getName(pc));

Просмотреть файл

@ -3854,7 +3854,7 @@ class ICIn_Fallback : public ICFallbackStub
};
// GetName
// JSOP_NAME
// JSOP_GETNAME
// JSOP_GETGNAME
class ICGetName_Fallback : public ICMonitoredFallbackStub
{

Просмотреть файл

@ -148,7 +148,7 @@ BytecodeAnalysis::init(TempAllocator &alloc, GSNCache &gsn)
}
break;
case JSOP_NAME:
case JSOP_GETNAME:
case JSOP_BINDNAME:
case JSOP_SETNAME:
case JSOP_DELNAME:

Разница между файлами не показана из-за своего большого размера Загрузить разницу

Просмотреть файл

@ -49,7 +49,7 @@ class OutOfLineRegExpTest;
class CodeGenerator : public CodeGeneratorSpecific
{
bool generateArgumentsChecks(bool bailout = true);
void generateArgumentsChecks(bool bailout = true);
bool generateBody();
public:
@ -61,321 +61,321 @@ class CodeGenerator : public CodeGeneratorSpecific
bool generateAsmJS(AsmJSFunctionLabels *labels);
bool link(JSContext *cx, types::CompilerConstraintList *constraints);
bool visitLabel(LLabel *lir);
bool visitNop(LNop *lir);
bool visitOsiPoint(LOsiPoint *lir);
bool visitGoto(LGoto *lir);
bool visitTableSwitch(LTableSwitch *ins);
bool visitTableSwitchV(LTableSwitchV *ins);
bool visitCloneLiteral(LCloneLiteral *lir);
bool visitParameter(LParameter *lir);
bool visitCallee(LCallee *lir);
bool visitIsConstructing(LIsConstructing *lir);
bool visitStart(LStart *lir);
bool visitReturn(LReturn *ret);
bool visitDefVar(LDefVar *lir);
bool visitDefFun(LDefFun *lir);
bool visitOsrEntry(LOsrEntry *lir);
bool visitOsrScopeChain(LOsrScopeChain *lir);
bool visitOsrValue(LOsrValue *lir);
bool visitOsrReturnValue(LOsrReturnValue *lir);
bool visitOsrArgumentsObject(LOsrArgumentsObject *lir);
bool visitStackArgT(LStackArgT *lir);
bool visitStackArgV(LStackArgV *lir);
bool visitMoveGroup(LMoveGroup *group);
bool visitValueToInt32(LValueToInt32 *lir);
bool visitValueToDouble(LValueToDouble *lir);
bool visitValueToFloat32(LValueToFloat32 *lir);
bool visitFloat32ToDouble(LFloat32ToDouble *lir);
bool visitDoubleToFloat32(LDoubleToFloat32 *lir);
bool visitInt32ToFloat32(LInt32ToFloat32 *lir);
bool visitInt32ToDouble(LInt32ToDouble *lir);
void visitLabel(LLabel *lir);
void visitNop(LNop *lir);
void visitOsiPoint(LOsiPoint *lir);
void visitGoto(LGoto *lir);
void visitTableSwitch(LTableSwitch *ins);
void visitTableSwitchV(LTableSwitchV *ins);
void visitCloneLiteral(LCloneLiteral *lir);
void visitParameter(LParameter *lir);
void visitCallee(LCallee *lir);
void visitIsConstructing(LIsConstructing *lir);
void visitStart(LStart *lir);
void visitReturn(LReturn *ret);
void visitDefVar(LDefVar *lir);
void visitDefFun(LDefFun *lir);
void visitOsrEntry(LOsrEntry *lir);
void visitOsrScopeChain(LOsrScopeChain *lir);
void visitOsrValue(LOsrValue *lir);
void visitOsrReturnValue(LOsrReturnValue *lir);
void visitOsrArgumentsObject(LOsrArgumentsObject *lir);
void visitStackArgT(LStackArgT *lir);
void visitStackArgV(LStackArgV *lir);
void visitMoveGroup(LMoveGroup *group);
void visitValueToInt32(LValueToInt32 *lir);
void visitValueToDouble(LValueToDouble *lir);
void visitValueToFloat32(LValueToFloat32 *lir);
void visitFloat32ToDouble(LFloat32ToDouble *lir);
void visitDoubleToFloat32(LDoubleToFloat32 *lir);
void visitInt32ToFloat32(LInt32ToFloat32 *lir);
void visitInt32ToDouble(LInt32ToDouble *lir);
void emitOOLTestObject(Register objreg, Label *ifTruthy, Label *ifFalsy, Register scratch);
bool visitTestOAndBranch(LTestOAndBranch *lir);
bool visitTestVAndBranch(LTestVAndBranch *lir);
bool visitFunctionDispatch(LFunctionDispatch *lir);
bool visitTypeObjectDispatch(LTypeObjectDispatch *lir);
bool visitBooleanToString(LBooleanToString *lir);
void visitTestOAndBranch(LTestOAndBranch *lir);
void visitTestVAndBranch(LTestVAndBranch *lir);
void visitFunctionDispatch(LFunctionDispatch *lir);
void visitTypeObjectDispatch(LTypeObjectDispatch *lir);
void visitBooleanToString(LBooleanToString *lir);
void emitIntToString(Register input, Register output, Label *ool);
bool visitIntToString(LIntToString *lir);
bool visitDoubleToString(LDoubleToString *lir);
bool visitValueToString(LValueToString *lir);
bool visitValueToObjectOrNull(LValueToObjectOrNull *lir);
bool visitInteger(LInteger *lir);
bool visitRegExp(LRegExp *lir);
bool visitRegExpExec(LRegExpExec *lir);
bool visitOutOfLineRegExpExec(OutOfLineRegExpExec *ool);
bool visitRegExpTest(LRegExpTest *lir);
bool visitOutOfLineRegExpTest(OutOfLineRegExpTest *ool);
bool visitRegExpReplace(LRegExpReplace *lir);
bool visitStringReplace(LStringReplace *lir);
bool visitLambda(LLambda *lir);
bool visitLambdaArrow(LLambdaArrow *lir);
bool visitLambdaForSingleton(LLambdaForSingleton *lir);
bool visitLambdaPar(LLambdaPar *lir);
bool visitPointer(LPointer *lir);
bool visitSlots(LSlots *lir);
bool visitLoadSlotT(LLoadSlotT *lir);
bool visitLoadSlotV(LLoadSlotV *lir);
bool visitStoreSlotT(LStoreSlotT *lir);
bool visitStoreSlotV(LStoreSlotV *lir);
bool visitElements(LElements *lir);
bool visitConvertElementsToDoubles(LConvertElementsToDoubles *lir);
bool visitMaybeToDoubleElement(LMaybeToDoubleElement *lir);
bool visitMaybeCopyElementsForWrite(LMaybeCopyElementsForWrite *lir);
bool visitGuardObjectIdentity(LGuardObjectIdentity *guard);
bool visitGuardShapePolymorphic(LGuardShapePolymorphic *lir);
bool visitTypeBarrierV(LTypeBarrierV *lir);
bool visitTypeBarrierO(LTypeBarrierO *lir);
bool visitMonitorTypes(LMonitorTypes *lir);
bool visitPostWriteBarrierO(LPostWriteBarrierO *lir);
bool visitPostWriteBarrierV(LPostWriteBarrierV *lir);
bool visitOutOfLineCallPostWriteBarrier(OutOfLineCallPostWriteBarrier *ool);
bool visitCallNative(LCallNative *call);
bool emitCallInvokeFunction(LInstruction *call, Register callereg,
void visitIntToString(LIntToString *lir);
void visitDoubleToString(LDoubleToString *lir);
void visitValueToString(LValueToString *lir);
void visitValueToObjectOrNull(LValueToObjectOrNull *lir);
void visitInteger(LInteger *lir);
void visitRegExp(LRegExp *lir);
void visitRegExpExec(LRegExpExec *lir);
void visitOutOfLineRegExpExec(OutOfLineRegExpExec *ool);
void visitRegExpTest(LRegExpTest *lir);
void visitOutOfLineRegExpTest(OutOfLineRegExpTest *ool);
void visitRegExpReplace(LRegExpReplace *lir);
void visitStringReplace(LStringReplace *lir);
void visitLambda(LLambda *lir);
void visitLambdaArrow(LLambdaArrow *lir);
void visitLambdaForSingleton(LLambdaForSingleton *lir);
void visitLambdaPar(LLambdaPar *lir);
void visitPointer(LPointer *lir);
void visitSlots(LSlots *lir);
void visitLoadSlotT(LLoadSlotT *lir);
void visitLoadSlotV(LLoadSlotV *lir);
void visitStoreSlotT(LStoreSlotT *lir);
void visitStoreSlotV(LStoreSlotV *lir);
void visitElements(LElements *lir);
void visitConvertElementsToDoubles(LConvertElementsToDoubles *lir);
void visitMaybeToDoubleElement(LMaybeToDoubleElement *lir);
void visitMaybeCopyElementsForWrite(LMaybeCopyElementsForWrite *lir);
void visitGuardObjectIdentity(LGuardObjectIdentity *guard);
void visitGuardShapePolymorphic(LGuardShapePolymorphic *lir);
void visitTypeBarrierV(LTypeBarrierV *lir);
void visitTypeBarrierO(LTypeBarrierO *lir);
void visitMonitorTypes(LMonitorTypes *lir);
void visitPostWriteBarrierO(LPostWriteBarrierO *lir);
void visitPostWriteBarrierV(LPostWriteBarrierV *lir);
void visitOutOfLineCallPostWriteBarrier(OutOfLineCallPostWriteBarrier *ool);
void visitCallNative(LCallNative *call);
void emitCallInvokeFunction(LInstruction *call, Register callereg,
uint32_t argc, uint32_t unusedStack);
bool visitCallGeneric(LCallGeneric *call);
bool visitCallKnown(LCallKnown *call);
bool emitCallInvokeFunction(LApplyArgsGeneric *apply, Register extraStackSize);
void visitCallGeneric(LCallGeneric *call);
void visitCallKnown(LCallKnown *call);
void emitCallInvokeFunction(LApplyArgsGeneric *apply, Register extraStackSize);
void emitPushArguments(LApplyArgsGeneric *apply, Register extraStackSpace);
void emitPopArguments(LApplyArgsGeneric *apply, Register extraStackSize);
bool visitApplyArgsGeneric(LApplyArgsGeneric *apply);
bool visitBail(LBail *lir);
bool visitUnreachable(LUnreachable *unreachable);
bool visitGetDynamicName(LGetDynamicName *lir);
bool visitFilterArgumentsOrEvalS(LFilterArgumentsOrEvalS *lir);
bool visitFilterArgumentsOrEvalV(LFilterArgumentsOrEvalV *lir);
bool visitCallDirectEvalS(LCallDirectEvalS *lir);
bool visitCallDirectEvalV(LCallDirectEvalV *lir);
bool visitDoubleToInt32(LDoubleToInt32 *lir);
bool visitFloat32ToInt32(LFloat32ToInt32 *lir);
bool visitNewArrayCallVM(LNewArray *lir);
bool visitNewArray(LNewArray *lir);
bool visitOutOfLineNewArray(OutOfLineNewArray *ool);
bool visitNewArrayCopyOnWrite(LNewArrayCopyOnWrite *lir);
bool visitNewArrayDynamicLength(LNewArrayDynamicLength *lir);
bool visitNewObjectVMCall(LNewObject *lir);
bool visitNewObject(LNewObject *lir);
bool visitOutOfLineNewObject(OutOfLineNewObject *ool);
bool visitNewTypedObject(LNewTypedObject *lir);
bool visitNewDeclEnvObject(LNewDeclEnvObject *lir);
bool visitNewCallObject(LNewCallObject *lir);
bool visitNewSingletonCallObject(LNewSingletonCallObject *lir);
bool visitNewCallObjectPar(LNewCallObjectPar *lir);
bool visitNewStringObject(LNewStringObject *lir);
bool visitNewPar(LNewPar *lir);
bool visitNewDenseArrayPar(LNewDenseArrayPar *lir);
bool visitNewDerivedTypedObject(LNewDerivedTypedObject *lir);
bool visitInitElem(LInitElem *lir);
bool visitInitElemGetterSetter(LInitElemGetterSetter *lir);
bool visitMutateProto(LMutateProto *lir);
bool visitInitProp(LInitProp *lir);
bool visitInitPropGetterSetter(LInitPropGetterSetter *lir);
bool visitCreateThis(LCreateThis *lir);
bool visitCreateThisWithProto(LCreateThisWithProto *lir);
bool visitCreateThisWithTemplate(LCreateThisWithTemplate *lir);
bool visitCreateArgumentsObject(LCreateArgumentsObject *lir);
bool visitGetArgumentsObjectArg(LGetArgumentsObjectArg *lir);
bool visitSetArgumentsObjectArg(LSetArgumentsObjectArg *lir);
bool visitReturnFromCtor(LReturnFromCtor *lir);
bool visitComputeThis(LComputeThis *lir);
bool visitLoadArrowThis(LLoadArrowThis *lir);
bool visitArrayLength(LArrayLength *lir);
bool visitSetArrayLength(LSetArrayLength *lir);
bool visitTypedArrayLength(LTypedArrayLength *lir);
bool visitTypedArrayElements(LTypedArrayElements *lir);
bool visitTypedObjectElements(LTypedObjectElements *lir);
bool visitSetTypedObjectOffset(LSetTypedObjectOffset *lir);
bool visitTypedObjectProto(LTypedObjectProto *ins);
bool visitStringLength(LStringLength *lir);
bool visitSubstr(LSubstr *lir);
bool visitInitializedLength(LInitializedLength *lir);
bool visitSetInitializedLength(LSetInitializedLength *lir);
bool visitNotO(LNotO *ins);
bool visitNotV(LNotV *ins);
bool visitBoundsCheck(LBoundsCheck *lir);
bool visitBoundsCheckRange(LBoundsCheckRange *lir);
bool visitBoundsCheckLower(LBoundsCheckLower *lir);
bool visitLoadFixedSlotV(LLoadFixedSlotV *ins);
bool visitLoadFixedSlotT(LLoadFixedSlotT *ins);
bool visitStoreFixedSlotV(LStoreFixedSlotV *ins);
bool visitStoreFixedSlotT(LStoreFixedSlotT *ins);
bool emitGetPropertyPolymorphic(LInstruction *lir, Register obj,
void visitApplyArgsGeneric(LApplyArgsGeneric *apply);
void visitBail(LBail *lir);
void visitUnreachable(LUnreachable *unreachable);
void visitGetDynamicName(LGetDynamicName *lir);
void visitFilterArgumentsOrEvalS(LFilterArgumentsOrEvalS *lir);
void visitFilterArgumentsOrEvalV(LFilterArgumentsOrEvalV *lir);
void visitCallDirectEvalS(LCallDirectEvalS *lir);
void visitCallDirectEvalV(LCallDirectEvalV *lir);
void visitDoubleToInt32(LDoubleToInt32 *lir);
void visitFloat32ToInt32(LFloat32ToInt32 *lir);
void visitNewArrayCallVM(LNewArray *lir);
void visitNewArray(LNewArray *lir);
void visitOutOfLineNewArray(OutOfLineNewArray *ool);
void visitNewArrayCopyOnWrite(LNewArrayCopyOnWrite *lir);
void visitNewArrayDynamicLength(LNewArrayDynamicLength *lir);
void visitNewObjectVMCall(LNewObject *lir);
void visitNewObject(LNewObject *lir);
void visitOutOfLineNewObject(OutOfLineNewObject *ool);
void visitNewTypedObject(LNewTypedObject *lir);
void visitNewDeclEnvObject(LNewDeclEnvObject *lir);
void visitNewCallObject(LNewCallObject *lir);
void visitNewSingletonCallObject(LNewSingletonCallObject *lir);
void visitNewCallObjectPar(LNewCallObjectPar *lir);
void visitNewStringObject(LNewStringObject *lir);
void visitNewPar(LNewPar *lir);
void visitNewDenseArrayPar(LNewDenseArrayPar *lir);
void visitNewDerivedTypedObject(LNewDerivedTypedObject *lir);
void visitInitElem(LInitElem *lir);
void visitInitElemGetterSetter(LInitElemGetterSetter *lir);
void visitMutateProto(LMutateProto *lir);
void visitInitProp(LInitProp *lir);
void visitInitPropGetterSetter(LInitPropGetterSetter *lir);
void visitCreateThis(LCreateThis *lir);
void visitCreateThisWithProto(LCreateThisWithProto *lir);
void visitCreateThisWithTemplate(LCreateThisWithTemplate *lir);
void visitCreateArgumentsObject(LCreateArgumentsObject *lir);
void visitGetArgumentsObjectArg(LGetArgumentsObjectArg *lir);
void visitSetArgumentsObjectArg(LSetArgumentsObjectArg *lir);
void visitReturnFromCtor(LReturnFromCtor *lir);
void visitComputeThis(LComputeThis *lir);
void visitLoadArrowThis(LLoadArrowThis *lir);
void visitArrayLength(LArrayLength *lir);
void visitSetArrayLength(LSetArrayLength *lir);
void visitTypedArrayLength(LTypedArrayLength *lir);
void visitTypedArrayElements(LTypedArrayElements *lir);
void visitTypedObjectElements(LTypedObjectElements *lir);
void visitSetTypedObjectOffset(LSetTypedObjectOffset *lir);
void visitTypedObjectProto(LTypedObjectProto *ins);
void visitStringLength(LStringLength *lir);
void visitSubstr(LSubstr *lir);
void visitInitializedLength(LInitializedLength *lir);
void visitSetInitializedLength(LSetInitializedLength *lir);
void visitNotO(LNotO *ins);
void visitNotV(LNotV *ins);
void visitBoundsCheck(LBoundsCheck *lir);
void visitBoundsCheckRange(LBoundsCheckRange *lir);
void visitBoundsCheckLower(LBoundsCheckLower *lir);
void visitLoadFixedSlotV(LLoadFixedSlotV *ins);
void visitLoadFixedSlotT(LLoadFixedSlotT *ins);
void visitStoreFixedSlotV(LStoreFixedSlotV *ins);
void visitStoreFixedSlotT(LStoreFixedSlotT *ins);
void emitGetPropertyPolymorphic(LInstruction *lir, Register obj,
Register scratch, const TypedOrValueRegister &output);
bool visitGetPropertyPolymorphicV(LGetPropertyPolymorphicV *ins);
bool visitGetPropertyPolymorphicT(LGetPropertyPolymorphicT *ins);
bool emitSetPropertyPolymorphic(LInstruction *lir, Register obj,
void visitGetPropertyPolymorphicV(LGetPropertyPolymorphicV *ins);
void visitGetPropertyPolymorphicT(LGetPropertyPolymorphicT *ins);
void emitSetPropertyPolymorphic(LInstruction *lir, Register obj,
Register scratch, const ConstantOrRegister &value);
bool visitSetPropertyPolymorphicV(LSetPropertyPolymorphicV *ins);
bool visitArraySplice(LArraySplice *splice);
bool visitSetPropertyPolymorphicT(LSetPropertyPolymorphicT *ins);
bool visitAbsI(LAbsI *lir);
bool visitAtan2D(LAtan2D *lir);
bool visitHypot(LHypot *lir);
bool visitPowI(LPowI *lir);
bool visitPowD(LPowD *lir);
bool visitRandom(LRandom *lir);
bool visitMathFunctionD(LMathFunctionD *ins);
bool visitMathFunctionF(LMathFunctionF *ins);
bool visitModD(LModD *ins);
bool visitMinMaxI(LMinMaxI *lir);
bool visitBinaryV(LBinaryV *lir);
bool emitCompareS(LInstruction *lir, JSOp op, Register left, Register right, Register output);
bool visitCompareS(LCompareS *lir);
bool visitCompareStrictS(LCompareStrictS *lir);
bool visitCompareVM(LCompareVM *lir);
bool visitIsNullOrLikeUndefined(LIsNullOrLikeUndefined *lir);
bool visitIsNullOrLikeUndefinedAndBranch(LIsNullOrLikeUndefinedAndBranch *lir);
bool visitEmulatesUndefined(LEmulatesUndefined *lir);
bool visitEmulatesUndefinedAndBranch(LEmulatesUndefinedAndBranch *lir);
bool emitConcat(LInstruction *lir, Register lhs, Register rhs, Register output);
bool visitConcat(LConcat *lir);
bool visitConcatPar(LConcatPar *lir);
bool visitCharCodeAt(LCharCodeAt *lir);
bool visitFromCharCode(LFromCharCode *lir);
bool visitStringSplit(LStringSplit *lir);
bool visitFunctionEnvironment(LFunctionEnvironment *lir);
bool visitForkJoinContext(LForkJoinContext *lir);
bool visitGuardThreadExclusive(LGuardThreadExclusive *lir);
bool visitCallGetProperty(LCallGetProperty *lir);
bool visitCallGetElement(LCallGetElement *lir);
bool visitCallSetElement(LCallSetElement *lir);
bool visitCallInitElementArray(LCallInitElementArray *lir);
bool visitThrow(LThrow *lir);
bool visitTypeOfV(LTypeOfV *lir);
bool visitOutOfLineTypeOfV(OutOfLineTypeOfV *ool);
bool visitToIdV(LToIdV *lir);
template<typename T> bool emitLoadElementT(LLoadElementT *lir, const T &source);
bool visitLoadElementT(LLoadElementT *lir);
bool visitLoadElementV(LLoadElementV *load);
bool visitLoadElementHole(LLoadElementHole *lir);
bool visitLoadUnboxedPointerV(LLoadUnboxedPointerV *lir);
bool visitLoadUnboxedPointerT(LLoadUnboxedPointerT *lir);
bool visitStoreElementT(LStoreElementT *lir);
bool visitStoreElementV(LStoreElementV *lir);
bool visitStoreElementHoleT(LStoreElementHoleT *lir);
bool visitStoreElementHoleV(LStoreElementHoleV *lir);
bool visitStoreUnboxedPointer(LStoreUnboxedPointer *lir);
bool emitArrayPopShift(LInstruction *lir, const MArrayPopShift *mir, Register obj,
void visitSetPropertyPolymorphicV(LSetPropertyPolymorphicV *ins);
void visitArraySplice(LArraySplice *splice);
void visitSetPropertyPolymorphicT(LSetPropertyPolymorphicT *ins);
void visitAbsI(LAbsI *lir);
void visitAtan2D(LAtan2D *lir);
void visitHypot(LHypot *lir);
void visitPowI(LPowI *lir);
void visitPowD(LPowD *lir);
void visitRandom(LRandom *lir);
void visitMathFunctionD(LMathFunctionD *ins);
void visitMathFunctionF(LMathFunctionF *ins);
void visitModD(LModD *ins);
void visitMinMaxI(LMinMaxI *lir);
void visitBinaryV(LBinaryV *lir);
void emitCompareS(LInstruction *lir, JSOp op, Register left, Register right, Register output);
void visitCompareS(LCompareS *lir);
void visitCompareStrictS(LCompareStrictS *lir);
void visitCompareVM(LCompareVM *lir);
void visitIsNullOrLikeUndefined(LIsNullOrLikeUndefined *lir);
void visitIsNullOrLikeUndefinedAndBranch(LIsNullOrLikeUndefinedAndBranch *lir);
void visitEmulatesUndefined(LEmulatesUndefined *lir);
void visitEmulatesUndefinedAndBranch(LEmulatesUndefinedAndBranch *lir);
void emitConcat(LInstruction *lir, Register lhs, Register rhs, Register output);
void visitConcat(LConcat *lir);
void visitConcatPar(LConcatPar *lir);
void visitCharCodeAt(LCharCodeAt *lir);
void visitFromCharCode(LFromCharCode *lir);
void visitStringSplit(LStringSplit *lir);
void visitFunctionEnvironment(LFunctionEnvironment *lir);
void visitForkJoinContext(LForkJoinContext *lir);
void visitGuardThreadExclusive(LGuardThreadExclusive *lir);
void visitCallGetProperty(LCallGetProperty *lir);
void visitCallGetElement(LCallGetElement *lir);
void visitCallSetElement(LCallSetElement *lir);
void visitCallInitElementArray(LCallInitElementArray *lir);
void visitThrow(LThrow *lir);
void visitTypeOfV(LTypeOfV *lir);
void visitOutOfLineTypeOfV(OutOfLineTypeOfV *ool);
void visitToIdV(LToIdV *lir);
template<typename T> void emitLoadElementT(LLoadElementT *lir, const T &source);
void visitLoadElementT(LLoadElementT *lir);
void visitLoadElementV(LLoadElementV *load);
void visitLoadElementHole(LLoadElementHole *lir);
void visitLoadUnboxedPointerV(LLoadUnboxedPointerV *lir);
void visitLoadUnboxedPointerT(LLoadUnboxedPointerT *lir);
void visitStoreElementT(LStoreElementT *lir);
void visitStoreElementV(LStoreElementV *lir);
void visitStoreElementHoleT(LStoreElementHoleT *lir);
void visitStoreElementHoleV(LStoreElementHoleV *lir);
void visitStoreUnboxedPointer(LStoreUnboxedPointer *lir);
void emitArrayPopShift(LInstruction *lir, const MArrayPopShift *mir, Register obj,
Register elementsTemp, Register lengthTemp, TypedOrValueRegister out);
bool visitArrayPopShiftV(LArrayPopShiftV *lir);
bool visitArrayPopShiftT(LArrayPopShiftT *lir);
bool emitArrayPush(LInstruction *lir, const MArrayPush *mir, Register obj,
void visitArrayPopShiftV(LArrayPopShiftV *lir);
void visitArrayPopShiftT(LArrayPopShiftT *lir);
void emitArrayPush(LInstruction *lir, const MArrayPush *mir, Register obj,
ConstantOrRegister value, Register elementsTemp, Register length);
bool visitArrayPushV(LArrayPushV *lir);
bool visitArrayPushT(LArrayPushT *lir);
bool visitArrayConcat(LArrayConcat *lir);
bool visitArrayJoin(LArrayJoin *lir);
bool visitLoadTypedArrayElement(LLoadTypedArrayElement *lir);
bool visitLoadTypedArrayElementHole(LLoadTypedArrayElementHole *lir);
bool visitStoreTypedArrayElement(LStoreTypedArrayElement *lir);
bool visitStoreTypedArrayElementHole(LStoreTypedArrayElementHole *lir);
bool visitCompareExchangeTypedArrayElement(LCompareExchangeTypedArrayElement *lir);
bool visitAtomicTypedArrayElementBinop(LAtomicTypedArrayElementBinop *lir);
bool visitClampIToUint8(LClampIToUint8 *lir);
bool visitClampDToUint8(LClampDToUint8 *lir);
bool visitClampVToUint8(LClampVToUint8 *lir);
bool visitCallIteratorStart(LCallIteratorStart *lir);
bool visitIteratorStart(LIteratorStart *lir);
bool visitIteratorMore(LIteratorMore *lir);
bool visitIsNoIterAndBranch(LIsNoIterAndBranch *lir);
bool visitIteratorEnd(LIteratorEnd *lir);
bool visitArgumentsLength(LArgumentsLength *lir);
bool visitGetFrameArgument(LGetFrameArgument *lir);
bool visitSetFrameArgumentT(LSetFrameArgumentT *lir);
bool visitSetFrameArgumentC(LSetFrameArgumentC *lir);
bool visitSetFrameArgumentV(LSetFrameArgumentV *lir);
bool visitRunOncePrologue(LRunOncePrologue *lir);
bool emitRest(LInstruction *lir, Register array, Register numActuals,
void visitArrayPushV(LArrayPushV *lir);
void visitArrayPushT(LArrayPushT *lir);
void visitArrayConcat(LArrayConcat *lir);
void visitArrayJoin(LArrayJoin *lir);
void visitLoadTypedArrayElement(LLoadTypedArrayElement *lir);
void visitLoadTypedArrayElementHole(LLoadTypedArrayElementHole *lir);
void visitStoreTypedArrayElement(LStoreTypedArrayElement *lir);
void visitStoreTypedArrayElementHole(LStoreTypedArrayElementHole *lir);
void visitCompareExchangeTypedArrayElement(LCompareExchangeTypedArrayElement *lir);
void visitAtomicTypedArrayElementBinop(LAtomicTypedArrayElementBinop *lir);
void visitClampIToUint8(LClampIToUint8 *lir);
void visitClampDToUint8(LClampDToUint8 *lir);
void visitClampVToUint8(LClampVToUint8 *lir);
void visitCallIteratorStart(LCallIteratorStart *lir);
void visitIteratorStart(LIteratorStart *lir);
void visitIteratorMore(LIteratorMore *lir);
void visitIsNoIterAndBranch(LIsNoIterAndBranch *lir);
void visitIteratorEnd(LIteratorEnd *lir);
void visitArgumentsLength(LArgumentsLength *lir);
void visitGetFrameArgument(LGetFrameArgument *lir);
void visitSetFrameArgumentT(LSetFrameArgumentT *lir);
void visitSetFrameArgumentC(LSetFrameArgumentC *lir);
void visitSetFrameArgumentV(LSetFrameArgumentV *lir);
void visitRunOncePrologue(LRunOncePrologue *lir);
void emitRest(LInstruction *lir, Register array, Register numActuals,
Register temp0, Register temp1, unsigned numFormals,
JSObject *templateObject, bool saveAndRestore, Register resultreg);
bool visitRest(LRest *lir);
bool visitRestPar(LRestPar *lir);
bool visitCallSetProperty(LCallSetProperty *ins);
bool visitCallDeleteProperty(LCallDeleteProperty *lir);
bool visitCallDeleteElement(LCallDeleteElement *lir);
bool visitBitNotV(LBitNotV *lir);
bool visitBitOpV(LBitOpV *lir);
bool emitInstanceOf(LInstruction *ins, JSObject *prototypeObject);
bool visitIn(LIn *ins);
bool visitInArray(LInArray *ins);
bool visitInstanceOfO(LInstanceOfO *ins);
bool visitInstanceOfV(LInstanceOfV *ins);
bool visitCallInstanceOf(LCallInstanceOf *ins);
bool visitProfilerStackOp(LProfilerStackOp *lir);
bool visitGetDOMProperty(LGetDOMProperty *lir);
bool visitGetDOMMember(LGetDOMMember *lir);
bool visitSetDOMProperty(LSetDOMProperty *lir);
bool visitCallDOMNative(LCallDOMNative *lir);
bool visitCallGetIntrinsicValue(LCallGetIntrinsicValue *lir);
bool visitIsCallable(LIsCallable *lir);
bool visitOutOfLineIsCallable(OutOfLineIsCallable *ool);
bool visitIsObject(LIsObject *lir);
bool visitIsObjectAndBranch(LIsObjectAndBranch *lir);
bool visitHaveSameClass(LHaveSameClass *lir);
bool visitHasClass(LHasClass *lir);
bool visitAsmJSParameter(LAsmJSParameter *lir);
bool visitAsmJSReturn(LAsmJSReturn *ret);
bool visitAsmJSVoidReturn(LAsmJSVoidReturn *ret);
bool visitLexicalCheck(LLexicalCheck *ins);
bool visitThrowUninitializedLexical(LThrowUninitializedLexical *ins);
bool visitDebugger(LDebugger *ins);
void visitRest(LRest *lir);
void visitRestPar(LRestPar *lir);
void visitCallSetProperty(LCallSetProperty *ins);
void visitCallDeleteProperty(LCallDeleteProperty *lir);
void visitCallDeleteElement(LCallDeleteElement *lir);
void visitBitNotV(LBitNotV *lir);
void visitBitOpV(LBitOpV *lir);
void emitInstanceOf(LInstruction *ins, JSObject *prototypeObject);
void visitIn(LIn *ins);
void visitInArray(LInArray *ins);
void visitInstanceOfO(LInstanceOfO *ins);
void visitInstanceOfV(LInstanceOfV *ins);
void visitCallInstanceOf(LCallInstanceOf *ins);
void visitProfilerStackOp(LProfilerStackOp *lir);
void visitGetDOMProperty(LGetDOMProperty *lir);
void visitGetDOMMember(LGetDOMMember *lir);
void visitSetDOMProperty(LSetDOMProperty *lir);
void visitCallDOMNative(LCallDOMNative *lir);
void visitCallGetIntrinsicValue(LCallGetIntrinsicValue *lir);
void visitIsCallable(LIsCallable *lir);
void visitOutOfLineIsCallable(OutOfLineIsCallable *ool);
void visitIsObject(LIsObject *lir);
void visitIsObjectAndBranch(LIsObjectAndBranch *lir);
void visitHaveSameClass(LHaveSameClass *lir);
void visitHasClass(LHasClass *lir);
void visitAsmJSParameter(LAsmJSParameter *lir);
void visitAsmJSReturn(LAsmJSReturn *ret);
void visitAsmJSVoidReturn(LAsmJSVoidReturn *ret);
void visitLexicalCheck(LLexicalCheck *ins);
void visitThrowUninitializedLexical(LThrowUninitializedLexical *ins);
void visitDebugger(LDebugger *ins);
bool visitCheckOverRecursed(LCheckOverRecursed *lir);
bool visitCheckOverRecursedFailure(CheckOverRecursedFailure *ool);
void visitCheckOverRecursed(LCheckOverRecursed *lir);
void visitCheckOverRecursedFailure(CheckOverRecursedFailure *ool);
bool visitCheckOverRecursedPar(LCheckOverRecursedPar *lir);
void visitCheckOverRecursedPar(LCheckOverRecursedPar *lir);
bool visitInterruptCheckPar(LInterruptCheckPar *lir);
bool visitOutOfLineInterruptCheckPar(OutOfLineInterruptCheckPar *ool);
void visitInterruptCheckPar(LInterruptCheckPar *lir);
void visitOutOfLineInterruptCheckPar(OutOfLineInterruptCheckPar *ool);
bool visitInterruptCheckImplicit(LInterruptCheckImplicit *ins);
bool visitOutOfLineInterruptCheckImplicit(OutOfLineInterruptCheckImplicit *ins);
void visitInterruptCheckImplicit(LInterruptCheckImplicit *ins);
void visitOutOfLineInterruptCheckImplicit(OutOfLineInterruptCheckImplicit *ins);
bool visitUnboxFloatingPoint(LUnboxFloatingPoint *lir);
bool visitOutOfLineUnboxFloatingPoint(OutOfLineUnboxFloatingPoint *ool);
bool visitOutOfLineStoreElementHole(OutOfLineStoreElementHole *ool);
void visitUnboxFloatingPoint(LUnboxFloatingPoint *lir);
void visitOutOfLineUnboxFloatingPoint(OutOfLineUnboxFloatingPoint *ool);
void visitOutOfLineStoreElementHole(OutOfLineStoreElementHole *ool);
bool visitOutOfLineNewGCThingPar(OutOfLineNewGCThingPar *ool);
void visitOutOfLineNewGCThingPar(OutOfLineNewGCThingPar *ool);
void loadJSScriptForBlock(MBasicBlock *block, Register reg);
void loadOutermostJSScript(Register reg);
// Inline caches visitors.
bool visitOutOfLineCache(OutOfLineUpdateCache *ool);
void visitOutOfLineCache(OutOfLineUpdateCache *ool);
bool visitGetPropertyCacheV(LGetPropertyCacheV *ins);
bool visitGetPropertyCacheT(LGetPropertyCacheT *ins);
bool visitGetElementCacheV(LGetElementCacheV *ins);
bool visitGetElementCacheT(LGetElementCacheT *ins);
bool visitSetElementCacheV(LSetElementCacheV *ins);
bool visitSetElementCacheT(LSetElementCacheT *ins);
bool visitBindNameCache(LBindNameCache *ins);
bool visitCallSetProperty(LInstruction *ins);
bool visitSetPropertyCacheV(LSetPropertyCacheV *ins);
bool visitSetPropertyCacheT(LSetPropertyCacheT *ins);
bool visitGetNameCache(LGetNameCache *ins);
bool visitCallsiteCloneCache(LCallsiteCloneCache *ins);
void visitGetPropertyCacheV(LGetPropertyCacheV *ins);
void visitGetPropertyCacheT(LGetPropertyCacheT *ins);
void visitGetElementCacheV(LGetElementCacheV *ins);
void visitGetElementCacheT(LGetElementCacheT *ins);
void visitSetElementCacheV(LSetElementCacheV *ins);
void visitSetElementCacheT(LSetElementCacheT *ins);
void visitBindNameCache(LBindNameCache *ins);
void visitCallSetProperty(LInstruction *ins);
void visitSetPropertyCacheV(LSetPropertyCacheV *ins);
void visitSetPropertyCacheT(LSetPropertyCacheT *ins);
void visitGetNameCache(LGetNameCache *ins);
void visitCallsiteCloneCache(LCallsiteCloneCache *ins);
bool visitGetPropertyIC(OutOfLineUpdateCache *ool, DataPtr<GetPropertyIC> &ic);
bool visitGetPropertyParIC(OutOfLineUpdateCache *ool, DataPtr<GetPropertyParIC> &ic);
bool visitSetPropertyIC(OutOfLineUpdateCache *ool, DataPtr<SetPropertyIC> &ic);
bool visitSetPropertyParIC(OutOfLineUpdateCache *ool, DataPtr<SetPropertyParIC> &ic);
bool visitGetElementIC(OutOfLineUpdateCache *ool, DataPtr<GetElementIC> &ic);
bool visitGetElementParIC(OutOfLineUpdateCache *ool, DataPtr<GetElementParIC> &ic);
bool visitSetElementIC(OutOfLineUpdateCache *ool, DataPtr<SetElementIC> &ic);
bool visitSetElementParIC(OutOfLineUpdateCache *ool, DataPtr<SetElementParIC> &ic);
bool visitBindNameIC(OutOfLineUpdateCache *ool, DataPtr<BindNameIC> &ic);
bool visitNameIC(OutOfLineUpdateCache *ool, DataPtr<NameIC> &ic);
bool visitCallsiteCloneIC(OutOfLineUpdateCache *ool, DataPtr<CallsiteCloneIC> &ic);
void visitGetPropertyIC(OutOfLineUpdateCache *ool, DataPtr<GetPropertyIC> &ic);
void visitGetPropertyParIC(OutOfLineUpdateCache *ool, DataPtr<GetPropertyParIC> &ic);
void visitSetPropertyIC(OutOfLineUpdateCache *ool, DataPtr<SetPropertyIC> &ic);
void visitSetPropertyParIC(OutOfLineUpdateCache *ool, DataPtr<SetPropertyParIC> &ic);
void visitGetElementIC(OutOfLineUpdateCache *ool, DataPtr<GetElementIC> &ic);
void visitGetElementParIC(OutOfLineUpdateCache *ool, DataPtr<GetElementParIC> &ic);
void visitSetElementIC(OutOfLineUpdateCache *ool, DataPtr<SetElementIC> &ic);
void visitSetElementParIC(OutOfLineUpdateCache *ool, DataPtr<SetElementParIC> &ic);
void visitBindNameIC(OutOfLineUpdateCache *ool, DataPtr<BindNameIC> &ic);
void visitNameIC(OutOfLineUpdateCache *ool, DataPtr<NameIC> &ic);
void visitCallsiteCloneIC(OutOfLineUpdateCache *ool, DataPtr<CallsiteCloneIC> &ic);
bool visitAssertRangeI(LAssertRangeI *ins);
bool visitAssertRangeD(LAssertRangeD *ins);
bool visitAssertRangeF(LAssertRangeF *ins);
bool visitAssertRangeV(LAssertRangeV *ins);
void visitAssertRangeI(LAssertRangeI *ins);
void visitAssertRangeD(LAssertRangeD *ins);
void visitAssertRangeF(LAssertRangeF *ins);
void visitAssertRangeV(LAssertRangeV *ins);
bool visitInterruptCheck(LInterruptCheck *lir);
bool visitAsmJSInterruptCheck(LAsmJSInterruptCheck *lir);
bool visitRecompileCheck(LRecompileCheck *ins);
void visitInterruptCheck(LInterruptCheck *lir);
void visitAsmJSInterruptCheck(LAsmJSInterruptCheck *lir);
void visitRecompileCheck(LRecompileCheck *ins);
IonScriptCounts *extractScriptCounts() {
IonScriptCounts *counts = scriptCounts_;
@ -384,32 +384,32 @@ class CodeGenerator : public CodeGeneratorSpecific
}
private:
bool addGetPropertyCache(LInstruction *ins, RegisterSet liveRegs, Register objReg,
void addGetPropertyCache(LInstruction *ins, RegisterSet liveRegs, Register objReg,
PropertyName *name, TypedOrValueRegister output,
bool monitoredResult, jsbytecode *profilerLeavePc);
bool addGetElementCache(LInstruction *ins, Register obj, ConstantOrRegister index,
void addGetElementCache(LInstruction *ins, Register obj, ConstantOrRegister index,
TypedOrValueRegister output, bool monitoredResult,
bool allowDoubleResult, jsbytecode *profilerLeavePc);
bool addSetPropertyCache(LInstruction *ins, RegisterSet liveRegs, Register objReg,
void addSetPropertyCache(LInstruction *ins, RegisterSet liveRegs, Register objReg,
PropertyName *name, ConstantOrRegister value, bool strict,
bool needsTypeBarrier, jsbytecode *profilerLeavePc);
bool addSetElementCache(LInstruction *ins, Register obj, Register unboxIndex, Register temp,
void addSetElementCache(LInstruction *ins, Register obj, Register unboxIndex, Register temp,
FloatRegister tempDouble, FloatRegister tempFloat32,
ValueOperand index, ConstantOrRegister value,
bool strict, bool guardHoles, jsbytecode *profilerLeavePc);
bool generateBranchV(const ValueOperand &value, Label *ifTrue, Label *ifFalse, FloatRegister fr);
bool emitAllocateGCThingPar(LInstruction *lir, Register objReg, Register cxReg,
void emitAllocateGCThingPar(LInstruction *lir, Register objReg, Register cxReg,
Register tempReg1, Register tempReg2,
NativeObject *templateObj);
bool emitCallToUncompiledScriptPar(LInstruction *lir, Register calleeReg);
void emitCallToUncompiledScriptPar(LInstruction *lir, Register calleeReg);
void emitLambdaInit(Register resultReg, Register scopeChainReg,
const LambdaFunctionInfo &info);
bool emitFilterArgumentsOrEval(LInstruction *lir, Register string, Register temp1,
void emitFilterArgumentsOrEval(LInstruction *lir, Register string, Register temp1,
Register temp2);
IonScriptCounts *maybeCreateScriptCounts();
@ -475,19 +475,19 @@ class CodeGenerator : public CodeGeneratorSpecific
int32_t offsetAdjustment);
// Bailout if an element about to be written to is a hole.
bool emitStoreHoleCheck(Register elements, const LAllocation *index, int32_t offsetAdjustment,
void emitStoreHoleCheck(Register elements, const LAllocation *index, int32_t offsetAdjustment,
LSnapshot *snapshot);
bool emitAssertRangeI(const Range *r, Register input);
bool emitAssertRangeD(const Range *r, FloatRegister input, FloatRegister temp);
void emitAssertRangeI(const Range *r, Register input);
void emitAssertRangeD(const Range *r, FloatRegister input, FloatRegister temp);
Vector<CodeOffsetLabel, 0, JitAllocPolicy> ionScriptLabels_;
#ifdef DEBUG
bool branchIfInvalidated(Register temp, Label *invalidated);
void branchIfInvalidated(Register temp, Label *invalidated);
bool emitDebugResultChecks(LInstruction *ins);
bool emitObjectOrStringResultChecks(LInstruction *lir, MDefinition *mir);
bool emitValueResultChecks(LInstruction *lir, MDefinition *mir);
void emitDebugResultChecks(LInstruction *ins);
void emitObjectOrStringResultChecks(LInstruction *lir, MDefinition *mir);
void emitValueResultChecks(LInstruction *lir, MDefinition *mir);
#endif
// Script counts created during code generation.

Просмотреть файл

@ -113,6 +113,10 @@ class CompactBufferWriter
: enoughMemory_(true)
{ }
void setOOM() {
enoughMemory_ = false;
}
// Note: writeByte() takes uint32 to catch implicit casts with a runtime
// assert.
void writeByte(uint32_t byte) {

Просмотреть файл

@ -1688,7 +1688,7 @@ IonBuilder::inspectOpcode(JSOp op)
return setStaticName(obj, name);
}
case JSOP_NAME:
case JSOP_GETNAME:
{
PropertyName *name = info().getAtom(pc)->asPropertyName();
return jsop_getname(name);

Просмотреть файл

@ -46,7 +46,7 @@ class IonCacheVisitor
{
public:
#define VISIT_INS(op) \
virtual bool visit##op##IC(CodeGenerator *codegen) { \
virtual void visit##op##IC(CodeGenerator *codegen) { \
MOZ_CRASH("NYI: " #op "IC"); \
}
@ -152,7 +152,7 @@ class IonCache
virtual Kind kind() const = 0;
virtual bool accept(CodeGenerator *codegen, IonCacheVisitor *visitor) = 0;
virtual void accept(CodeGenerator *codegen, IonCacheVisitor *visitor) = 0;
public:
@ -516,8 +516,8 @@ class DispatchIonCache : public IonCache
return IonCache::Cache_##ickind; \
} \
\
bool accept(CodeGenerator *codegen, IonCacheVisitor *visitor) { \
return visitor->visit##ickind##IC(codegen); \
void accept(CodeGenerator *codegen, IonCacheVisitor *visitor) { \
visitor->visit##ickind##IC(codegen); \
} \
\
static const VMFunction UpdateInfo;

Просмотреть файл

@ -719,15 +719,15 @@ class LNode
LIR_OPCODE_LIST(LIROP)
# undef LIROP
virtual bool accept(LElementVisitor *visitor) = 0;
virtual void accept(LElementVisitor *visitor) = 0;
#define LIR_HEADER(opcode) \
Opcode op() const { \
return LInstruction::LOp_##opcode; \
} \
bool accept(LElementVisitor *visitor) { \
void accept(LElementVisitor *visitor) { \
visitor->setElement(this); \
return visitor->visit##opcode(this); \
visitor->visit##opcode(this); \
}
};
@ -823,7 +823,7 @@ class LElementVisitor
{}
public:
#define VISIT_INS(op) virtual bool visit##op(L##op *) { MOZ_CRASH("NYI: " #op); }
#define VISIT_INS(op) virtual void visit##op(L##op *) { MOZ_CRASH("NYI: " #op); }
LIR_OPCODE_LIST(VISIT_INS)
#undef VISIT_INS
};

Просмотреть файл

@ -260,14 +260,18 @@ IonBuilder::inlineNativeGetter(CallInfo &callInfo, JSFunction *target)
Scalar::Type type;
type = thisTypes->getTypedArrayType();
if (type != Scalar::TypeMax && TypedArrayObject::isOriginalLengthGetter(native)) {
if (type != Scalar::MaxTypedArrayViewType &&
TypedArrayObject::isOriginalLengthGetter(native))
{
MInstruction *length = addTypedArrayLength(callInfo.thisArg());
current->push(length);
return InliningStatus_Inlined;
}
type = thisTypes->getSharedTypedArrayType();
if (type != Scalar::TypeMax && SharedTypedArrayObject::isOriginalLengthGetter(type, native)) {
if (type != Scalar::MaxTypedArrayViewType &&
SharedTypedArrayObject::isOriginalLengthGetter(type, native))
{
MInstruction *length = addTypedArrayLength(callInfo.thisArg());
current->push(length);
return InliningStatus_Inlined;

Просмотреть файл

@ -3977,10 +3977,10 @@ jit::ElementAccessIsAnyTypedArray(MDefinition *obj, MDefinition *id,
return false;
*arrayType = types->getTypedArrayType();
if (*arrayType != Scalar::TypeMax)
if (*arrayType != Scalar::MaxTypedArrayViewType)
return true;
*arrayType = types->getSharedTypedArrayType();
return *arrayType != Scalar::TypeMax;
return *arrayType != Scalar::MaxTypedArrayViewType;
}
bool

Просмотреть файл

@ -8487,7 +8487,7 @@ class MLoadTypedArrayElement
setMovable();
MOZ_ASSERT(IsValidElementsType(elements, offsetAdjustment));
MOZ_ASSERT(index->type() == MIRType_Int32);
MOZ_ASSERT(arrayType >= 0 && arrayType < Scalar::TypeMax);
MOZ_ASSERT(arrayType >= 0 && arrayType < Scalar::MaxTypedArrayViewType);
}
public:
@ -8565,7 +8565,7 @@ class MLoadTypedArrayElementHole
setResultType(MIRType_Value);
setMovable();
MOZ_ASSERT(index->type() == MIRType_Int32);
MOZ_ASSERT(arrayType >= 0 && arrayType < Scalar::TypeMax);
MOZ_ASSERT(arrayType >= 0 && arrayType < Scalar::MaxTypedArrayViewType);
}
public:
@ -8689,7 +8689,7 @@ class MStoreTypedArrayElement
setMovable();
MOZ_ASSERT(IsValidElementsType(elements, offsetAdjustment));
MOZ_ASSERT(index->type() == MIRType_Int32);
MOZ_ASSERT(arrayType >= 0 && arrayType < Scalar::TypeMax);
MOZ_ASSERT(arrayType >= 0 && arrayType < Scalar::MaxTypedArrayViewType);
}
public:
@ -8767,7 +8767,7 @@ class MStoreTypedArrayElementHole
MOZ_ASSERT(elements->type() == MIRType_Elements);
MOZ_ASSERT(length->type() == MIRType_Int32);
MOZ_ASSERT(index->type() == MIRType_Int32);
MOZ_ASSERT(arrayType >= 0 && arrayType < Scalar::TypeMax);
MOZ_ASSERT(arrayType >= 0 && arrayType < Scalar::MaxTypedArrayViewType);
}
public:
@ -12151,19 +12151,15 @@ class MAsmJSNeg : public MUnaryInstruction
class MAsmJSHeapAccess
{
protected:
typedef AsmJSHeapAccess::ViewType ViewType;
private:
ViewType viewType_;
Scalar::Type viewType_;
bool needsBoundsCheck_;
public:
MAsmJSHeapAccess(ViewType vt, bool needsBoundsCheck)
MAsmJSHeapAccess(Scalar::Type vt, bool needsBoundsCheck)
: viewType_(vt), needsBoundsCheck_(needsBoundsCheck)
{}
ViewType viewType() const { return viewType_; }
Scalar::Type viewType() const { return viewType_; }
bool needsBoundsCheck() const { return needsBoundsCheck_; }
void removeBoundsCheck() { needsBoundsCheck_ = false; }
};
@ -12173,7 +12169,7 @@ class MAsmJSLoadHeap : public MUnaryInstruction, public MAsmJSHeapAccess
MemoryBarrierBits barrierBefore_;
MemoryBarrierBits barrierAfter_;
MAsmJSLoadHeap(ViewType vt, MDefinition *ptr, bool needsBoundsCheck,
MAsmJSLoadHeap(Scalar::Type vt, MDefinition *ptr, bool needsBoundsCheck,
MemoryBarrierBits before, MemoryBarrierBits after)
: MUnaryInstruction(ptr),
MAsmJSHeapAccess(vt, needsBoundsCheck),
@ -12186,27 +12182,28 @@ class MAsmJSLoadHeap : public MUnaryInstruction, public MAsmJSHeapAccess
setMovable();
switch (vt) {
case AsmJSHeapAccess::Int8:
case AsmJSHeapAccess::Uint8:
case AsmJSHeapAccess::Int16:
case AsmJSHeapAccess::Uint16:
case AsmJSHeapAccess::Int32:
case AsmJSHeapAccess::Uint32:
case Scalar::Int8:
case Scalar::Uint8:
case Scalar::Int16:
case Scalar::Uint16:
case Scalar::Int32:
case Scalar::Uint32:
setResultType(MIRType_Int32);
break;
case AsmJSHeapAccess::Float32:
case Scalar::Float32:
setResultType(MIRType_Float32);
break;
case AsmJSHeapAccess::Float64:
case Scalar::Float64:
setResultType(MIRType_Double);
break;
case AsmJSHeapAccess::Float32x4:
case Scalar::Float32x4:
setResultType(MIRType_Float32x4);
break;
case AsmJSHeapAccess::Int32x4:
case Scalar::Int32x4:
setResultType(MIRType_Int32x4);
break;
case AsmJSHeapAccess::Uint8Clamped:
case Scalar::Uint8Clamped:
case Scalar::MaxTypedArrayViewType:
MOZ_CRASH("unexpected uint8clamped load heap in asm.js");
}
}
@ -12214,7 +12211,7 @@ class MAsmJSLoadHeap : public MUnaryInstruction, public MAsmJSHeapAccess
public:
INSTRUCTION_HEADER(AsmJSLoadHeap);
static MAsmJSLoadHeap *New(TempAllocator &alloc, ViewType vt,
static MAsmJSLoadHeap *New(TempAllocator &alloc, Scalar::Type vt,
MDefinition *ptr, bool needsBoundsCheck,
MemoryBarrierBits barrierBefore = MembarNobits,
MemoryBarrierBits barrierAfter = MembarNobits)
@ -12238,7 +12235,7 @@ class MAsmJSStoreHeap : public MBinaryInstruction, public MAsmJSHeapAccess
MemoryBarrierBits barrierBefore_;
MemoryBarrierBits barrierAfter_;
MAsmJSStoreHeap(ViewType vt, MDefinition *ptr, MDefinition *v, bool needsBoundsCheck,
MAsmJSStoreHeap(Scalar::Type vt, MDefinition *ptr, MDefinition *v, bool needsBoundsCheck,
MemoryBarrierBits before, MemoryBarrierBits after)
: MBinaryInstruction(ptr, v),
MAsmJSHeapAccess(vt, needsBoundsCheck),
@ -12252,7 +12249,7 @@ class MAsmJSStoreHeap : public MBinaryInstruction, public MAsmJSHeapAccess
public:
INSTRUCTION_HEADER(AsmJSStoreHeap);
static MAsmJSStoreHeap *New(TempAllocator &alloc, ViewType vt,
static MAsmJSStoreHeap *New(TempAllocator &alloc, Scalar::Type vt,
MDefinition *ptr, MDefinition *v, bool needsBoundsCheck,
MemoryBarrierBits barrierBefore = MembarNobits,
MemoryBarrierBits barrierAfter = MembarNobits)
@ -12273,7 +12270,7 @@ class MAsmJSStoreHeap : public MBinaryInstruction, public MAsmJSHeapAccess
class MAsmJSCompareExchangeHeap : public MTernaryInstruction, public MAsmJSHeapAccess
{
MAsmJSCompareExchangeHeap(ViewType vt, MDefinition *ptr, MDefinition *oldv, MDefinition *newv,
MAsmJSCompareExchangeHeap(Scalar::Type vt, MDefinition *ptr, MDefinition *oldv, MDefinition *newv,
bool needsBoundsCheck)
: MTernaryInstruction(ptr, oldv, newv),
MAsmJSHeapAccess(vt, needsBoundsCheck)
@ -12285,7 +12282,7 @@ class MAsmJSCompareExchangeHeap : public MTernaryInstruction, public MAsmJSHeapA
public:
INSTRUCTION_HEADER(AsmJSCompareExchangeHeap);
static MAsmJSCompareExchangeHeap *New(TempAllocator &alloc, ViewType vt,
static MAsmJSCompareExchangeHeap *New(TempAllocator &alloc, Scalar::Type vt,
MDefinition *ptr, MDefinition *oldv,
MDefinition *newv, bool needsBoundsCheck)
{
@ -12305,7 +12302,7 @@ class MAsmJSAtomicBinopHeap : public MBinaryInstruction, public MAsmJSHeapAccess
{
AtomicOp op_;
MAsmJSAtomicBinopHeap(AtomicOp op, ViewType vt, MDefinition *ptr, MDefinition *v,
MAsmJSAtomicBinopHeap(AtomicOp op, Scalar::Type vt, MDefinition *ptr, MDefinition *v,
bool needsBoundsCheck)
: MBinaryInstruction(ptr, v),
MAsmJSHeapAccess(vt, needsBoundsCheck),
@ -12318,7 +12315,7 @@ class MAsmJSAtomicBinopHeap : public MBinaryInstruction, public MAsmJSHeapAccess
public:
INSTRUCTION_HEADER(AsmJSAtomicBinopHeap);
static MAsmJSAtomicBinopHeap *New(TempAllocator &alloc, AtomicOp op, ViewType vt,
static MAsmJSAtomicBinopHeap *New(TempAllocator &alloc, AtomicOp op, Scalar::Type vt,
MDefinition *ptr, MDefinition *v, bool needsBoundsCheck)
{
return new(alloc) MAsmJSAtomicBinopHeap(op, vt, ptr, v, needsBoundsCheck);

Просмотреть файл

@ -134,6 +134,15 @@ MacroAssembler::guardTypeSet(const Source &address, const TypeSet *types, Barrie
if (kind != BarrierKind::TypeTagOnly) {
Register obj = extractObject(address, scratch);
guardObjectType(obj, types, scratch, miss);
} else {
#ifdef DEBUG
Label fail;
Register obj = extractObject(address, scratch);
guardObjectType(obj, types, scratch, &fail);
jump(&matched);
bind(&fail);
assumeUnreachable("Unexpected object type");
#endif
}
bind(&matched);

Просмотреть файл

@ -697,13 +697,12 @@ RecoverWriter::startRecover(uint32_t instructionCount, bool resumeAfter)
return recoverOffset;
}
bool
void
RecoverWriter::writeInstruction(const MNode *rp)
{
if (!rp->writeRecoverData(writer_))
return false;
writer_.setOOM();
instructionsWritten_++;
return true;
}
void

Просмотреть файл

@ -398,7 +398,7 @@ class RecoverWriter
public:
SnapshotOffset startRecover(uint32_t instructionCount, bool resumeAfter);
bool writeInstruction(const MNode *rp);
void writeInstruction(const MNode *rp);
void endRecover();

Просмотреть файл

@ -1295,10 +1295,10 @@ Assembler::oom() const
preBarriers_.oom();
}
bool
void
Assembler::addCodeLabel(CodeLabel label)
{
return codeLabels_.append(label);
propagateOOM(codeLabels_.append(label));
}
// Size of the instruction stream, in bytes. Including pools. This function

Просмотреть файл

@ -1275,7 +1275,7 @@ class Assembler : public AssemblerShared
void copyDataRelocationTable(uint8_t *dest);
void copyPreBarrierTable(uint8_t *dest);
bool addCodeLabel(CodeLabel label);
void addCodeLabel(CodeLabel label);
size_t numCodeLabels() const {
return codeLabels_.length();
}

Разница между файлами не показана из-за своего большого размера Загрузить разницу

Просмотреть файл

@ -45,32 +45,32 @@ class CodeGeneratorARM : public CodeGeneratorShared
MoveOperand toMoveOperand(const LAllocation *a) const;
bool bailoutIf(Assembler::Condition condition, LSnapshot *snapshot);
bool bailoutFrom(Label *label, LSnapshot *snapshot);
bool bailout(LSnapshot *snapshot);
void bailoutIf(Assembler::Condition condition, LSnapshot *snapshot);
void bailoutFrom(Label *label, LSnapshot *snapshot);
void bailout(LSnapshot *snapshot);
template <typename T1, typename T2>
bool bailoutCmpPtr(Assembler::Condition c, T1 lhs, T2 rhs, LSnapshot *snapshot) {
void bailoutCmpPtr(Assembler::Condition c, T1 lhs, T2 rhs, LSnapshot *snapshot) {
masm.cmpPtr(lhs, rhs);
return bailoutIf(c, snapshot);
bailoutIf(c, snapshot);
}
bool bailoutTestPtr(Assembler::Condition c, Register lhs, Register rhs, LSnapshot *snapshot) {
void bailoutTestPtr(Assembler::Condition c, Register lhs, Register rhs, LSnapshot *snapshot) {
masm.testPtr(lhs, rhs);
return bailoutIf(c, snapshot);
bailoutIf(c, snapshot);
}
template <typename T1, typename T2>
bool bailoutCmp32(Assembler::Condition c, T1 lhs, T2 rhs, LSnapshot *snapshot) {
void bailoutCmp32(Assembler::Condition c, T1 lhs, T2 rhs, LSnapshot *snapshot) {
masm.cmp32(lhs, rhs);
return bailoutIf(c, snapshot);
bailoutIf(c, snapshot);
}
template <typename T1, typename T2>
bool bailoutTest32(Assembler::Condition c, T1 lhs, T2 rhs, LSnapshot *snapshot) {
void bailoutTest32(Assembler::Condition c, T1 lhs, T2 rhs, LSnapshot *snapshot) {
masm.test32(lhs, rhs);
return bailoutIf(c, snapshot);
bailoutIf(c, snapshot);
}
bool bailoutIfFalseBool(Register reg, LSnapshot *snapshot) {
void bailoutIfFalseBool(Register reg, LSnapshot *snapshot) {
masm.test32(reg, Imm32(0xFF));
return bailoutIf(Assembler::Zero, snapshot);
bailoutIf(Assembler::Zero, snapshot);
}
protected:
@ -103,70 +103,70 @@ class CodeGeneratorARM : public CodeGeneratorShared
emitBranch(cond, ifTrue, ifFalse);
}
bool emitTableSwitchDispatch(MTableSwitch *mir, Register index, Register base);
void emitTableSwitchDispatch(MTableSwitch *mir, Register index, Register base);
public:
// Instruction visitors.
virtual bool visitMinMaxD(LMinMaxD *ins);
virtual bool visitMinMaxF(LMinMaxF *ins);
virtual bool visitAbsD(LAbsD *ins);
virtual bool visitAbsF(LAbsF *ins);
virtual bool visitSqrtD(LSqrtD *ins);
virtual bool visitSqrtF(LSqrtF *ins);
virtual bool visitAddI(LAddI *ins);
virtual bool visitSubI(LSubI *ins);
virtual bool visitBitNotI(LBitNotI *ins);
virtual bool visitBitOpI(LBitOpI *ins);
virtual void visitMinMaxD(LMinMaxD *ins);
virtual void visitMinMaxF(LMinMaxF *ins);
virtual void visitAbsD(LAbsD *ins);
virtual void visitAbsF(LAbsF *ins);
virtual void visitSqrtD(LSqrtD *ins);
virtual void visitSqrtF(LSqrtF *ins);
virtual void visitAddI(LAddI *ins);
virtual void visitSubI(LSubI *ins);
virtual void visitBitNotI(LBitNotI *ins);
virtual void visitBitOpI(LBitOpI *ins);
virtual bool visitMulI(LMulI *ins);
virtual void visitMulI(LMulI *ins);
virtual bool visitDivI(LDivI *ins);
virtual bool visitSoftDivI(LSoftDivI *ins);
virtual bool visitDivPowTwoI(LDivPowTwoI *ins);
virtual bool visitModI(LModI *ins);
virtual bool visitSoftModI(LSoftModI *ins);
virtual bool visitModPowTwoI(LModPowTwoI *ins);
virtual bool visitModMaskI(LModMaskI *ins);
virtual bool visitPowHalfD(LPowHalfD *ins);
virtual bool visitShiftI(LShiftI *ins);
virtual bool visitUrshD(LUrshD *ins);
virtual void visitDivI(LDivI *ins);
virtual void visitSoftDivI(LSoftDivI *ins);
virtual void visitDivPowTwoI(LDivPowTwoI *ins);
virtual void visitModI(LModI *ins);
virtual void visitSoftModI(LSoftModI *ins);
virtual void visitModPowTwoI(LModPowTwoI *ins);
virtual void visitModMaskI(LModMaskI *ins);
virtual void visitPowHalfD(LPowHalfD *ins);
virtual void visitShiftI(LShiftI *ins);
virtual void visitUrshD(LUrshD *ins);
virtual bool visitClzI(LClzI *ins);
virtual void visitClzI(LClzI *ins);
virtual bool visitTestIAndBranch(LTestIAndBranch *test);
virtual bool visitCompare(LCompare *comp);
virtual bool visitCompareAndBranch(LCompareAndBranch *comp);
virtual bool visitTestDAndBranch(LTestDAndBranch *test);
virtual bool visitTestFAndBranch(LTestFAndBranch *test);
virtual bool visitCompareD(LCompareD *comp);
virtual bool visitCompareF(LCompareF *comp);
virtual bool visitCompareDAndBranch(LCompareDAndBranch *comp);
virtual bool visitCompareFAndBranch(LCompareFAndBranch *comp);
virtual bool visitCompareB(LCompareB *lir);
virtual bool visitCompareBAndBranch(LCompareBAndBranch *lir);
virtual bool visitCompareV(LCompareV *lir);
virtual bool visitCompareVAndBranch(LCompareVAndBranch *lir);
virtual bool visitBitAndAndBranch(LBitAndAndBranch *baab);
virtual bool visitAsmJSUInt32ToDouble(LAsmJSUInt32ToDouble *lir);
virtual bool visitAsmJSUInt32ToFloat32(LAsmJSUInt32ToFloat32 *lir);
virtual bool visitNotI(LNotI *ins);
virtual bool visitNotD(LNotD *ins);
virtual bool visitNotF(LNotF *ins);
virtual void visitTestIAndBranch(LTestIAndBranch *test);
virtual void visitCompare(LCompare *comp);
virtual void visitCompareAndBranch(LCompareAndBranch *comp);
virtual void visitTestDAndBranch(LTestDAndBranch *test);
virtual void visitTestFAndBranch(LTestFAndBranch *test);
virtual void visitCompareD(LCompareD *comp);
virtual void visitCompareF(LCompareF *comp);
virtual void visitCompareDAndBranch(LCompareDAndBranch *comp);
virtual void visitCompareFAndBranch(LCompareFAndBranch *comp);
virtual void visitCompareB(LCompareB *lir);
virtual void visitCompareBAndBranch(LCompareBAndBranch *lir);
virtual void visitCompareV(LCompareV *lir);
virtual void visitCompareVAndBranch(LCompareVAndBranch *lir);
virtual void visitBitAndAndBranch(LBitAndAndBranch *baab);
virtual void visitAsmJSUInt32ToDouble(LAsmJSUInt32ToDouble *lir);
virtual void visitAsmJSUInt32ToFloat32(LAsmJSUInt32ToFloat32 *lir);
virtual void visitNotI(LNotI *ins);
virtual void visitNotD(LNotD *ins);
virtual void visitNotF(LNotF *ins);
virtual bool visitMathD(LMathD *math);
virtual bool visitMathF(LMathF *math);
virtual bool visitFloor(LFloor *lir);
virtual bool visitFloorF(LFloorF *lir);
virtual bool visitCeil(LCeil *lir);
virtual bool visitCeilF(LCeilF *lir);
virtual bool visitRound(LRound *lir);
virtual bool visitRoundF(LRoundF *lir);
virtual bool visitTruncateDToInt32(LTruncateDToInt32 *ins);
virtual bool visitTruncateFToInt32(LTruncateFToInt32 *ins);
virtual void visitMathD(LMathD *math);
virtual void visitMathF(LMathF *math);
virtual void visitFloor(LFloor *lir);
virtual void visitFloorF(LFloorF *lir);
virtual void visitCeil(LCeil *lir);
virtual void visitCeilF(LCeilF *lir);
virtual void visitRound(LRound *lir);
virtual void visitRoundF(LRoundF *lir);
virtual void visitTruncateDToInt32(LTruncateDToInt32 *ins);
virtual void visitTruncateFToInt32(LTruncateFToInt32 *ins);
// Out of line visitors.
bool visitOutOfLineBailout(OutOfLineBailout *ool);
bool visitOutOfLineTableSwitch(OutOfLineTableSwitch *ool);
void visitOutOfLineBailout(OutOfLineBailout *ool);
void visitOutOfLineTableSwitch(OutOfLineTableSwitch *ool);
protected:
ValueOperand ToValue(LInstruction *ins, size_t pos);
@ -176,9 +176,9 @@ class CodeGeneratorARM : public CodeGeneratorShared
// Functions for LTestVAndBranch.
Register splitTagForTest(const ValueOperand &value);
bool divICommon(MDiv *mir, Register lhs, Register rhs, Register output, LSnapshot *snapshot,
void divICommon(MDiv *mir, Register lhs, Register rhs, Register output, LSnapshot *snapshot,
Label &done);
bool modICommon(MMod *mir, Register lhs, Register rhs, Register output, LSnapshot *snapshot,
void modICommon(MMod *mir, Register lhs, Register rhs, Register output, LSnapshot *snapshot,
Label &done);
void memoryBarrier(MemoryBarrierBits barrier);
@ -187,60 +187,60 @@ class CodeGeneratorARM : public CodeGeneratorShared
CodeGeneratorARM(MIRGenerator *gen, LIRGraph *graph, MacroAssembler *masm);
public:
bool visitBox(LBox *box);
bool visitBoxFloatingPoint(LBoxFloatingPoint *box);
bool visitUnbox(LUnbox *unbox);
bool visitValue(LValue *value);
bool visitDouble(LDouble *ins);
bool visitFloat32(LFloat32 *ins);
void visitBox(LBox *box);
void visitBoxFloatingPoint(LBoxFloatingPoint *box);
void visitUnbox(LUnbox *unbox);
void visitValue(LValue *value);
void visitDouble(LDouble *ins);
void visitFloat32(LFloat32 *ins);
bool visitGuardShape(LGuardShape *guard);
bool visitGuardObjectType(LGuardObjectType *guard);
bool visitGuardClass(LGuardClass *guard);
void visitGuardShape(LGuardShape *guard);
void visitGuardObjectType(LGuardObjectType *guard);
void visitGuardClass(LGuardClass *guard);
bool visitNegI(LNegI *lir);
bool visitNegD(LNegD *lir);
bool visitNegF(LNegF *lir);
bool visitLoadTypedArrayElementStatic(LLoadTypedArrayElementStatic *ins);
bool visitStoreTypedArrayElementStatic(LStoreTypedArrayElementStatic *ins);
bool visitAsmJSCall(LAsmJSCall *ins);
bool visitAsmJSLoadHeap(LAsmJSLoadHeap *ins);
bool visitAsmJSStoreHeap(LAsmJSStoreHeap *ins);
bool visitAsmJSCompareExchangeHeap(LAsmJSCompareExchangeHeap *ins);
bool visitAsmJSAtomicBinopHeap(LAsmJSAtomicBinopHeap *ins);
bool visitAsmJSLoadGlobalVar(LAsmJSLoadGlobalVar *ins);
bool visitAsmJSStoreGlobalVar(LAsmJSStoreGlobalVar *ins);
bool visitAsmJSLoadFuncPtr(LAsmJSLoadFuncPtr *ins);
bool visitAsmJSLoadFFIFunc(LAsmJSLoadFFIFunc *ins);
bool visitAsmJSPassStackArg(LAsmJSPassStackArg *ins);
void visitNegI(LNegI *lir);
void visitNegD(LNegD *lir);
void visitNegF(LNegF *lir);
void visitLoadTypedArrayElementStatic(LLoadTypedArrayElementStatic *ins);
void visitStoreTypedArrayElementStatic(LStoreTypedArrayElementStatic *ins);
void visitAsmJSCall(LAsmJSCall *ins);
void visitAsmJSLoadHeap(LAsmJSLoadHeap *ins);
void visitAsmJSStoreHeap(LAsmJSStoreHeap *ins);
void visitAsmJSCompareExchangeHeap(LAsmJSCompareExchangeHeap *ins);
void visitAsmJSAtomicBinopHeap(LAsmJSAtomicBinopHeap *ins);
void visitAsmJSLoadGlobalVar(LAsmJSLoadGlobalVar *ins);
void visitAsmJSStoreGlobalVar(LAsmJSStoreGlobalVar *ins);
void visitAsmJSLoadFuncPtr(LAsmJSLoadFuncPtr *ins);
void visitAsmJSLoadFFIFunc(LAsmJSLoadFFIFunc *ins);
void visitAsmJSPassStackArg(LAsmJSPassStackArg *ins);
bool visitForkJoinGetSlice(LForkJoinGetSlice *ins);
void visitForkJoinGetSlice(LForkJoinGetSlice *ins);
bool visitMemoryBarrier(LMemoryBarrier *ins);
void visitMemoryBarrier(LMemoryBarrier *ins);
bool generateInvalidateEpilogue();
void generateInvalidateEpilogue();
protected:
bool visitEffectiveAddress(LEffectiveAddress *ins);
bool visitUDiv(LUDiv *ins);
bool visitUMod(LUMod *ins);
bool visitSoftUDivOrMod(LSoftUDivOrMod *ins);
void visitEffectiveAddress(LEffectiveAddress *ins);
void visitUDiv(LUDiv *ins);
void visitUMod(LUMod *ins);
void visitSoftUDivOrMod(LSoftUDivOrMod *ins);
public:
// Unimplemented SIMD instructions
bool visitSimdSplatX4(LSimdSplatX4 *lir) { MOZ_CRASH("NYI"); }
bool visitInt32x4(LInt32x4 *ins) { MOZ_CRASH("NYI"); }
bool visitFloat32x4(LFloat32x4 *ins) { MOZ_CRASH("NYI"); }
bool visitSimdExtractElementI(LSimdExtractElementI *ins) { MOZ_CRASH("NYI"); }
bool visitSimdExtractElementF(LSimdExtractElementF *ins) { MOZ_CRASH("NYI"); }
bool visitSimdSignMaskX4(LSimdSignMaskX4 *ins) { MOZ_CRASH("NYI"); }
bool visitSimdSwizzleI(LSimdSwizzleI *lir) { MOZ_CRASH("NYI"); }
bool visitSimdSwizzleF(LSimdSwizzleF *lir) { MOZ_CRASH("NYI"); }
bool visitSimdBinaryCompIx4(LSimdBinaryCompIx4 *lir) { MOZ_CRASH("NYI"); }
bool visitSimdBinaryCompFx4(LSimdBinaryCompFx4 *lir) { MOZ_CRASH("NYI"); }
bool visitSimdBinaryArithIx4(LSimdBinaryArithIx4 *lir) { MOZ_CRASH("NYI"); }
bool visitSimdBinaryArithFx4(LSimdBinaryArithFx4 *lir) { MOZ_CRASH("NYI"); }
bool visitSimdBinaryBitwiseX4(LSimdBinaryBitwiseX4 *lir) { MOZ_CRASH("NYI"); }
void visitSimdSplatX4(LSimdSplatX4 *lir) { MOZ_CRASH("NYI"); }
void visitInt32x4(LInt32x4 *ins) { MOZ_CRASH("NYI"); }
void visitFloat32x4(LFloat32x4 *ins) { MOZ_CRASH("NYI"); }
void visitSimdExtractElementI(LSimdExtractElementI *ins) { MOZ_CRASH("NYI"); }
void visitSimdExtractElementF(LSimdExtractElementF *ins) { MOZ_CRASH("NYI"); }
void visitSimdSignMaskX4(LSimdSignMaskX4 *ins) { MOZ_CRASH("NYI"); }
void visitSimdSwizzleI(LSimdSwizzleI *lir) { MOZ_CRASH("NYI"); }
void visitSimdSwizzleF(LSimdSwizzleF *lir) { MOZ_CRASH("NYI"); }
void visitSimdBinaryCompIx4(LSimdBinaryCompIx4 *lir) { MOZ_CRASH("NYI"); }
void visitSimdBinaryCompFx4(LSimdBinaryCompFx4 *lir) { MOZ_CRASH("NYI"); }
void visitSimdBinaryArithIx4(LSimdBinaryArithIx4 *lir) { MOZ_CRASH("NYI"); }
void visitSimdBinaryArithFx4(LSimdBinaryArithFx4 *lir) { MOZ_CRASH("NYI"); }
void visitSimdBinaryBitwiseX4(LSimdBinaryBitwiseX4 *lir) { MOZ_CRASH("NYI"); }
};
typedef CodeGeneratorARM CodeGeneratorSpecific;
@ -258,7 +258,7 @@ class OutOfLineBailout : public OutOfLineCodeBase<CodeGeneratorARM>
frameSize_(frameSize)
{ }
bool accept(CodeGeneratorARM *codegen);
void accept(CodeGeneratorARM *codegen);
LSnapshot *snapshot() const {
return snapshot_;

Просмотреть файл

@ -651,7 +651,7 @@ LIRGeneratorARM::visitCompareExchangeTypedArrayElement(MCompareExchangeTypedArra
bool
LIRGeneratorARM::visitAsmJSCompareExchangeHeap(MAsmJSCompareExchangeHeap *ins)
{
MOZ_ASSERT(ins->viewType() < AsmJSHeapAccess::Float32);
MOZ_ASSERT(ins->viewType() < Scalar::Float32);
MDefinition *ptr = ins->ptr();
MOZ_ASSERT(ptr->type() == MIRType_Int32);
@ -667,7 +667,7 @@ LIRGeneratorARM::visitAsmJSCompareExchangeHeap(MAsmJSCompareExchangeHeap *ins)
bool
LIRGeneratorARM::visitAsmJSAtomicBinopHeap(MAsmJSAtomicBinopHeap *ins)
{
MOZ_ASSERT(ins->viewType() < AsmJSHeapAccess::Float32);
MOZ_ASSERT(ins->viewType() < Scalar::Float32);
MDefinition *ptr = ins->ptr();
MOZ_ASSERT(ptr->type() == MIRType_Int32);

Просмотреть файл

@ -1766,7 +1766,7 @@ MacroAssemblerARM::ma_vstr(VFPRegister src, Register base, Register index, int32
return ma_vstr(src, Operand(ScratchRegister, 0), cc);
}
bool
void
MacroAssemblerARMCompat::buildFakeExitFrame(Register scratch, uint32_t *offset)
{
DebugOnly<uint32_t> initialDepth = framePushed();
@ -1789,7 +1789,6 @@ MacroAssemblerARMCompat::buildFakeExitFrame(Register scratch, uint32_t *offset)
MOZ_ASSERT(pseudoReturnOffset - offsetBeforePush == 8);
*offset = pseudoReturnOffset;
return true;
}
bool

Просмотреть файл

@ -1284,7 +1284,7 @@ class MacroAssemblerARMCompat : public MacroAssemblerARM
// Builds an exit frame on the stack, with a return address to an internal
// non-function. Returns offset to be passed to markSafepointAt().
bool buildFakeExitFrame(Register scratch, uint32_t *offset);
void buildFakeExitFrame(Register scratch, uint32_t *offset);
void callWithExitFrame(Label *target);
void callWithExitFrame(JitCode *target);

Просмотреть файл

@ -479,10 +479,10 @@ Assembler::oom() const
preBarriers_.oom();
}
bool
void
Assembler::addCodeLabel(CodeLabel label)
{
return codeLabels_.append(label);
propagateOOM(codeLabels_.append(label));
}
// Size of the instruction stream, in bytes.

Просмотреть файл

@ -790,7 +790,7 @@ class Assembler : public AssemblerShared
void copyDataRelocationTable(uint8_t *dest);
void copyPreBarrierTable(uint8_t *dest);
bool addCodeLabel(CodeLabel label);
void addCodeLabel(CodeLabel label);
size_t numCodeLabels() const {
return codeLabels_.length();
}

Разница между файлами не показана из-за своего большого размера Загрузить разницу

Просмотреть файл

@ -61,45 +61,44 @@ class CodeGeneratorMIPS : public CodeGeneratorShared
MoveOperand toMoveOperand(const LAllocation *a) const;
template <typename T1, typename T2>
bool bailoutCmp32(Assembler::Condition c, T1 lhs, T2 rhs, LSnapshot *snapshot) {
bool goodBailout;
void bailoutCmp32(Assembler::Condition c, T1 lhs, T2 rhs, LSnapshot *snapshot) {
Label skip;
masm.ma_b(lhs, rhs, &skip, Assembler::InvertCondition(c), ShortJump);
goodBailout = bailout(snapshot);
bailout(snapshot);
masm.bind(&skip);
return goodBailout;
}
template<typename T>
bool bailoutCmp32(Assembler::Condition c, Operand lhs, T rhs, LSnapshot *snapshot) {
void bailoutCmp32(Assembler::Condition c, Operand lhs, T rhs, LSnapshot *snapshot) {
if (lhs.getTag() == Operand::REG)
return bailoutCmp32(c, lhs.toReg(), rhs, snapshot);
if (lhs.getTag() == Operand::MEM)
return bailoutCmp32(c, lhs.toAddress(), rhs, snapshot);
MOZ_CRASH("Invalid operand tag.");
bailoutCmp32(c, lhs.toReg(), rhs, snapshot);
else if (lhs.getTag() == Operand::MEM)
bailoutCmp32(c, lhs.toAddress(), rhs, snapshot);
else
MOZ_CRASH("Invalid operand tag.");
}
template<typename T>
bool bailoutTest32(Assembler::Condition c, Register lhs, T rhs, LSnapshot *snapshot) {
void bailoutTest32(Assembler::Condition c, Register lhs, T rhs, LSnapshot *snapshot) {
Label bail;
masm.branchTest32(c, lhs, rhs, &bail);
return bailoutFrom(&bail, snapshot);
bailoutFrom(&bail, snapshot);
}
template <typename T1, typename T2>
bool bailoutCmpPtr(Assembler::Condition c, T1 lhs, T2 rhs, LSnapshot *snapshot) {
return bailoutCmp32(c, lhs, rhs, snapshot);
void bailoutCmpPtr(Assembler::Condition c, T1 lhs, T2 rhs, LSnapshot *snapshot) {
bailoutCmp32(c, lhs, rhs, snapshot);
}
bool bailoutTestPtr(Assembler::Condition c, Register lhs, Register rhs, LSnapshot *snapshot) {
void bailoutTestPtr(Assembler::Condition c, Register lhs, Register rhs, LSnapshot *snapshot) {
Label bail;
masm.branchTestPtr(c, lhs, rhs, &bail);
return bailoutFrom(&bail, snapshot);
bailoutFrom(&bail, snapshot);
}
bool bailoutIfFalseBool(Register reg, LSnapshot *snapshot) {
void bailoutIfFalseBool(Register reg, LSnapshot *snapshot) {
Label bail;
masm.branchTest32(Assembler::Zero, reg, Imm32(0xFF), &bail);
return bailoutFrom(&bail, snapshot);
bailoutFrom(&bail, snapshot);
}
bool bailoutFrom(Label *label, LSnapshot *snapshot);
bool bailout(LSnapshot *snapshot);
void bailoutFrom(Label *label, LSnapshot *snapshot);
void bailout(LSnapshot *snapshot);
protected:
bool generatePrologue();
@ -162,68 +161,68 @@ class CodeGeneratorMIPS : public CodeGeneratorShared
emitBranch(value.typeReg(), (Imm32)ImmType(JSVAL_TYPE_OBJECT), cond, ifTrue, ifFalse);
}
bool emitTableSwitchDispatch(MTableSwitch *mir, Register index, Register base);
void emitTableSwitchDispatch(MTableSwitch *mir, Register index, Register base);
public:
// Instruction visitors.
virtual bool visitMinMaxD(LMinMaxD *ins);
virtual bool visitMinMaxF(LMinMaxF *ins);
virtual bool visitAbsD(LAbsD *ins);
virtual bool visitAbsF(LAbsF *ins);
virtual bool visitSqrtD(LSqrtD *ins);
virtual bool visitSqrtF(LSqrtF *ins);
virtual bool visitAddI(LAddI *ins);
virtual bool visitSubI(LSubI *ins);
virtual bool visitBitNotI(LBitNotI *ins);
virtual bool visitBitOpI(LBitOpI *ins);
virtual void visitMinMaxD(LMinMaxD *ins);
virtual void visitMinMaxF(LMinMaxF *ins);
virtual void visitAbsD(LAbsD *ins);
virtual void visitAbsF(LAbsF *ins);
virtual void visitSqrtD(LSqrtD *ins);
virtual void visitSqrtF(LSqrtF *ins);
virtual void visitAddI(LAddI *ins);
virtual void visitSubI(LSubI *ins);
virtual void visitBitNotI(LBitNotI *ins);
virtual void visitBitOpI(LBitOpI *ins);
virtual bool visitMulI(LMulI *ins);
virtual void visitMulI(LMulI *ins);
virtual bool visitDivI(LDivI *ins);
virtual bool visitDivPowTwoI(LDivPowTwoI *ins);
virtual bool visitModI(LModI *ins);
virtual bool visitModPowTwoI(LModPowTwoI *ins);
virtual bool visitModMaskI(LModMaskI *ins);
virtual bool visitPowHalfD(LPowHalfD *ins);
virtual bool visitShiftI(LShiftI *ins);
virtual bool visitUrshD(LUrshD *ins);
virtual void visitDivI(LDivI *ins);
virtual void visitDivPowTwoI(LDivPowTwoI *ins);
virtual void visitModI(LModI *ins);
virtual void visitModPowTwoI(LModPowTwoI *ins);
virtual void visitModMaskI(LModMaskI *ins);
virtual void visitPowHalfD(LPowHalfD *ins);
virtual void visitShiftI(LShiftI *ins);
virtual void visitUrshD(LUrshD *ins);
virtual bool visitClzI(LClzI *ins);
virtual void visitClzI(LClzI *ins);
virtual bool visitTestIAndBranch(LTestIAndBranch *test);
virtual bool visitCompare(LCompare *comp);
virtual bool visitCompareAndBranch(LCompareAndBranch *comp);
virtual bool visitTestDAndBranch(LTestDAndBranch *test);
virtual bool visitTestFAndBranch(LTestFAndBranch *test);
virtual bool visitCompareD(LCompareD *comp);
virtual bool visitCompareF(LCompareF *comp);
virtual bool visitCompareDAndBranch(LCompareDAndBranch *comp);
virtual bool visitCompareFAndBranch(LCompareFAndBranch *comp);
virtual bool visitCompareB(LCompareB *lir);
virtual bool visitCompareBAndBranch(LCompareBAndBranch *lir);
virtual bool visitCompareV(LCompareV *lir);
virtual bool visitCompareVAndBranch(LCompareVAndBranch *lir);
virtual bool visitBitAndAndBranch(LBitAndAndBranch *lir);
virtual bool visitAsmJSUInt32ToDouble(LAsmJSUInt32ToDouble *lir);
virtual bool visitAsmJSUInt32ToFloat32(LAsmJSUInt32ToFloat32 *lir);
virtual bool visitNotI(LNotI *ins);
virtual bool visitNotD(LNotD *ins);
virtual bool visitNotF(LNotF *ins);
virtual void visitTestIAndBranch(LTestIAndBranch *test);
virtual void visitCompare(LCompare *comp);
virtual void visitCompareAndBranch(LCompareAndBranch *comp);
virtual void visitTestDAndBranch(LTestDAndBranch *test);
virtual void visitTestFAndBranch(LTestFAndBranch *test);
virtual void visitCompareD(LCompareD *comp);
virtual void visitCompareF(LCompareF *comp);
virtual void visitCompareDAndBranch(LCompareDAndBranch *comp);
virtual void visitCompareFAndBranch(LCompareFAndBranch *comp);
virtual void visitCompareB(LCompareB *lir);
virtual void visitCompareBAndBranch(LCompareBAndBranch *lir);
virtual void visitCompareV(LCompareV *lir);
virtual void visitCompareVAndBranch(LCompareVAndBranch *lir);
virtual void visitBitAndAndBranch(LBitAndAndBranch *lir);
virtual void visitAsmJSUInt32ToDouble(LAsmJSUInt32ToDouble *lir);
virtual void visitAsmJSUInt32ToFloat32(LAsmJSUInt32ToFloat32 *lir);
virtual void visitNotI(LNotI *ins);
virtual void visitNotD(LNotD *ins);
virtual void visitNotF(LNotF *ins);
virtual bool visitMathD(LMathD *math);
virtual bool visitMathF(LMathF *math);
virtual bool visitFloor(LFloor *lir);
virtual bool visitFloorF(LFloorF *lir);
virtual bool visitCeil(LCeil *lir);
virtual bool visitCeilF(LCeilF *lir);
virtual bool visitRound(LRound *lir);
virtual bool visitRoundF(LRoundF *lir);
virtual bool visitTruncateDToInt32(LTruncateDToInt32 *ins);
virtual bool visitTruncateFToInt32(LTruncateFToInt32 *ins);
virtual void visitMathD(LMathD *math);
virtual void visitMathF(LMathF *math);
virtual void visitFloor(LFloor *lir);
virtual void visitFloorF(LFloorF *lir);
virtual void visitCeil(LCeil *lir);
virtual void visitCeilF(LCeilF *lir);
virtual void visitRound(LRound *lir);
virtual void visitRoundF(LRoundF *lir);
virtual void visitTruncateDToInt32(LTruncateDToInt32 *ins);
virtual void visitTruncateFToInt32(LTruncateFToInt32 *ins);
// Out of line visitors.
bool visitOutOfLineBailout(OutOfLineBailout *ool);
bool visitOutOfLineTableSwitch(OutOfLineTableSwitch *ool);
void visitOutOfLineBailout(OutOfLineBailout *ool);
void visitOutOfLineTableSwitch(OutOfLineTableSwitch *ool);
protected:
ValueOperand ToValue(LInstruction *ins, size_t pos);
@ -237,56 +236,56 @@ class CodeGeneratorMIPS : public CodeGeneratorShared
CodeGeneratorMIPS(MIRGenerator *gen, LIRGraph *graph, MacroAssembler *masm);
public:
bool visitBox(LBox *box);
bool visitBoxFloatingPoint(LBoxFloatingPoint *box);
bool visitUnbox(LUnbox *unbox);
bool visitValue(LValue *value);
bool visitDouble(LDouble *ins);
bool visitFloat32(LFloat32 *ins);
void visitBox(LBox *box);
void visitBoxFloatingPoint(LBoxFloatingPoint *box);
void visitUnbox(LUnbox *unbox);
void visitValue(LValue *value);
void visitDouble(LDouble *ins);
void visitFloat32(LFloat32 *ins);
bool visitGuardShape(LGuardShape *guard);
bool visitGuardObjectType(LGuardObjectType *guard);
bool visitGuardClass(LGuardClass *guard);
void visitGuardShape(LGuardShape *guard);
void visitGuardObjectType(LGuardObjectType *guard);
void visitGuardClass(LGuardClass *guard);
bool visitNegI(LNegI *lir);
bool visitNegD(LNegD *lir);
bool visitNegF(LNegF *lir);
bool visitLoadTypedArrayElementStatic(LLoadTypedArrayElementStatic *ins);
bool visitStoreTypedArrayElementStatic(LStoreTypedArrayElementStatic *ins);
bool visitAsmJSCall(LAsmJSCall *ins);
bool visitAsmJSLoadHeap(LAsmJSLoadHeap *ins);
bool visitAsmJSStoreHeap(LAsmJSStoreHeap *ins);
bool visitAsmJSCompareExchangeHeap(LAsmJSCompareExchangeHeap *ins);
bool visitAsmJSAtomicBinopHeap(LAsmJSAtomicBinopHeap *ins);
bool visitAsmJSLoadGlobalVar(LAsmJSLoadGlobalVar *ins);
bool visitAsmJSStoreGlobalVar(LAsmJSStoreGlobalVar *ins);
bool visitAsmJSLoadFuncPtr(LAsmJSLoadFuncPtr *ins);
bool visitAsmJSLoadFFIFunc(LAsmJSLoadFFIFunc *ins);
void visitNegI(LNegI *lir);
void visitNegD(LNegD *lir);
void visitNegF(LNegF *lir);
void visitLoadTypedArrayElementStatic(LLoadTypedArrayElementStatic *ins);
void visitStoreTypedArrayElementStatic(LStoreTypedArrayElementStatic *ins);
void visitAsmJSCall(LAsmJSCall *ins);
void visitAsmJSLoadHeap(LAsmJSLoadHeap *ins);
void visitAsmJSStoreHeap(LAsmJSStoreHeap *ins);
void visitAsmJSCompareExchangeHeap(LAsmJSCompareExchangeHeap *ins);
void visitAsmJSAtomicBinopHeap(LAsmJSAtomicBinopHeap *ins);
void visitAsmJSLoadGlobalVar(LAsmJSLoadGlobalVar *ins);
void visitAsmJSStoreGlobalVar(LAsmJSStoreGlobalVar *ins);
void visitAsmJSLoadFuncPtr(LAsmJSLoadFuncPtr *ins);
void visitAsmJSLoadFFIFunc(LAsmJSLoadFFIFunc *ins);
bool visitAsmJSPassStackArg(LAsmJSPassStackArg *ins);
void visitAsmJSPassStackArg(LAsmJSPassStackArg *ins);
bool visitForkJoinGetSlice(LForkJoinGetSlice *ins);
void visitForkJoinGetSlice(LForkJoinGetSlice *ins);
bool generateInvalidateEpilogue();
void generateInvalidateEpilogue();
protected:
bool visitEffectiveAddress(LEffectiveAddress *ins);
bool visitUDiv(LUDiv *ins);
bool visitUMod(LUMod *ins);
void visitEffectiveAddress(LEffectiveAddress *ins);
void visitUDiv(LUDiv *ins);
void visitUMod(LUMod *ins);
public:
// Unimplemented SIMD instructions
bool visitSimdSplatX4(LSimdSplatX4 *lir) { MOZ_CRASH("NYI"); }
bool visitInt32x4(LInt32x4 *ins) { MOZ_CRASH("NYI"); }
bool visitFloat32x4(LFloat32x4 *ins) { MOZ_CRASH("NYI"); }
bool visitSimdExtractElementI(LSimdExtractElementI *ins) { MOZ_CRASH("NYI"); }
bool visitSimdExtractElementF(LSimdExtractElementF *ins) { MOZ_CRASH("NYI"); }
bool visitSimdSignMaskX4(LSimdSignMaskX4 *ins) { MOZ_CRASH("NYI"); }
bool visitSimdBinaryCompIx4(LSimdBinaryCompIx4 *lir) { MOZ_CRASH("NYI"); }
bool visitSimdBinaryCompFx4(LSimdBinaryCompFx4 *lir) { MOZ_CRASH("NYI"); }
bool visitSimdBinaryArithIx4(LSimdBinaryArithIx4 *lir) { MOZ_CRASH("NYI"); }
bool visitSimdBinaryArithFx4(LSimdBinaryArithFx4 *lir) { MOZ_CRASH("NYI"); }
bool visitSimdBinaryBitwiseX4(LSimdBinaryBitwiseX4 *lir) { MOZ_CRASH("NYI"); }
void visitSimdSplatX4(LSimdSplatX4 *lir) { MOZ_CRASH("NYI"); }
void visitInt32x4(LInt32x4 *ins) { MOZ_CRASH("NYI"); }
void visitFloat32x4(LFloat32x4 *ins) { MOZ_CRASH("NYI"); }
void visitSimdExtractElementI(LSimdExtractElementI *ins) { MOZ_CRASH("NYI"); }
void visitSimdExtractElementF(LSimdExtractElementF *ins) { MOZ_CRASH("NYI"); }
void visitSimdSignMaskX4(LSimdSignMaskX4 *ins) { MOZ_CRASH("NYI"); }
void visitSimdBinaryCompIx4(LSimdBinaryCompIx4 *lir) { MOZ_CRASH("NYI"); }
void visitSimdBinaryCompFx4(LSimdBinaryCompFx4 *lir) { MOZ_CRASH("NYI"); }
void visitSimdBinaryArithIx4(LSimdBinaryArithIx4 *lir) { MOZ_CRASH("NYI"); }
void visitSimdBinaryArithFx4(LSimdBinaryArithFx4 *lir) { MOZ_CRASH("NYI"); }
void visitSimdBinaryBitwiseX4(LSimdBinaryBitwiseX4 *lir) { MOZ_CRASH("NYI"); }
};
typedef CodeGeneratorMIPS CodeGeneratorSpecific;
@ -303,7 +302,7 @@ class OutOfLineBailout : public OutOfLineCodeBase<CodeGeneratorMIPS>
frameSize_(frameSize)
{ }
bool accept(CodeGeneratorMIPS *codegen);
void accept(CodeGeneratorMIPS *codegen);
LSnapshot *snapshot() const {
return snapshot_;

Просмотреть файл

@ -1475,7 +1475,7 @@ MacroAssemblerMIPS::ma_bc1d(FloatRegister lhs, FloatRegister rhs, Label *label,
branchWithCode(getBranchCode(testKind, fcc), label, jumpKind);
}
bool
void
MacroAssemblerMIPSCompat::buildFakeExitFrame(Register scratch, uint32_t *offset)
{
mozilla::DebugOnly<uint32_t> initialDepth = framePushed();
@ -1491,7 +1491,7 @@ MacroAssemblerMIPSCompat::buildFakeExitFrame(Register scratch, uint32_t *offset)
*offset = currentOffset();
MOZ_ASSERT(framePushed() == initialDepth + ExitFrameLayout::Size());
return addCodeLabel(cl);
addCodeLabel(cl);
}
bool

Некоторые файлы не были показаны из-за слишком большого количества измененных файлов Показать больше