Browse Source

import changes from `dev' branch of rmottola/Arctic-Fox:

- Bug 1167823 - Begin rewriting CheckSideEffects to work by kind, not arity. r=shu (3dbb147c1)
- Bug 1167823 - Handle various nullary/unary nodes in BytecodeEmitter::checkSideEffects. r=shu (16db94f34)
- Bug 1167823 - Handle more nodes by kind in BytecodeEmitter::checkSideEffects. r=shu (2c994828f)
- Bug 1167823 - Handle more nodes by kind when checking for side effects. r=shu (8726e98c5)
- Bug 1167823 - Check various binary operators for side effects, by node kind. r=shu (da2a42a59)
- Bug 1173969 - Add ARM64 Trampoline and MoveEmitter. r=jandem (78df8ad3a)
- Bug 1167823 - Handle more nodes by kind when checking for side effects. r=shu (6ae74fc89)
- Bug 1182936 part 1 - IonMonkey: MIPS32: Rename mips to mips32. r=nbp (6c47d3ac3)
- Bug 1167823 - Handle more nodes by kind when checking for side effects. r=shu (008192c61)
- Bug 1155618 - Fix OOM issues related to AsmJS compilation r=terrence r=luke (4fa2b1875)
- Bug 1167823 - Handle try/catch by kind when checking for side effects. r=shu (18aea1680)
- Bug 1167823 - Handle various list-ful nodes by kind when checking for side effects. r=shu (b23e01874)
- pointer style (f9dbf7554)
- Bug 1178770 - Move MacroAssemblerSpecific::call to the MacroAssembler. r=h4writer (27701ec78)
- Bug 1167823 - Handle various other nodes by kind when checking for side effects. r=shu (85448267d)
- Bug 1167823 - Handle functions by kind when checking for side effects. r=shu (1c6eae1da)
- pointer style (e18f6e8fd)
- Bug 1164121 - Add |mach| command to run jsapi-tests. r=sfink (28b9e99ce)
- Bug 1167823 - Handle more nodes by kind when checking for side effects. r=shu (cdbcaf264)
- Bug 1167823 - Handle more nodes by kind when checking for side effects. r=shu (5d8ca8fac)
- bug 1125394 - launch runtime executable stub from test app bundle on Mac; r=jmaher,marco (7f4d2f685)
- Bug 1155338 - Move mach command arguments into mochitest harness, r=chmanchester,gbrown (e25c02087)
- bug 1125394 - launch runtime executable stub from test app bundle on Mac; r=jmaher,marco (c7ecbf9ec)
- Bug 1164597 - Consolidate all mochitest mach commands into single |mach mochitest|, r=chmanchester (042d5b97e)
- Bug 1169410 Add support for web-platform-tests to |mach test| r=gps (7c8cd4917)
- Bug 1169799 - Update |mach test| suites to reflect new |mach mochitest| command, r=chmanchester (9d33ab17c)
- Bug 1149670 - Add a mach command to find tests in specified directories and prepare a commit to push them to try.;r=ahal (2d2145c35)
- Bug 1154006 - [mach] Ability to lazy load parsers passed in via the @command decorator, r=gps (eac0b362a)
- Bug 1138581 - Support wildcard expansion in mach file-info; r=glandium (a4b9a973d)
- Bug 1168607 - Make `mach file-info` work with Mercurial repos; r=glandium (0a6e69591)
- Bug 1173633 - Print docstrings of mach command handlers in help output; r=ahal (0080c50a6)
- Bug 1090957 - IonMonkey: MIPS32: Implement atomicExchange operations temporary. r=nbp (4b51a4fad)
- Pointer style (c16016361)
- add LastFrameCheck in ::Compile lost for some reason (dd9689746)
- Bug 1155185 - IonMonkey MIPS: Fix build failure on MIPS; implement MacroAssemblerMIPS::convertInt32ToDouble(const BaseIndex& src, FloatRegister dest). r=rankov (64eb0d71c)
- Bug 1194072 - IonMonkey: MIPS32: Add an option to mark JIT pages as non-writable. r=nbp CLOSED TREE (ecc0c19c7)
- Bug 1173622 - Add a thorough docstring and clean up comments on the |mach try| command.;r=ahal (ae1f0e534)
- Bug 1107534 - Using audio channels type to capture different stream. r=roc (17fd7fa15)
- Bug 1014355 - Init X with thread-safe mode in child processes. r=karlt (3d150507f)
kmeleon76
roytam1 1 year ago
parent
commit
77b85633c5
  1. 1
      build/mach_bootstrap.py
  2. 21
      dom/html/HTMLMediaElement.cpp
  3. 9
      dom/html/HTMLMediaElement.h
  4. 44
      dom/media/DOMMediaStream.cpp
  5. 24
      dom/media/DOMMediaStream.h
  6. 1
      dom/media/MediaStreamGraph.cpp
  7. 3
      dom/media/webaudio/AudioContext.cpp
  8. 6
      js/src/asmjs/AsmJSFrameIterator.cpp
  9. 49
      js/src/asmjs/AsmJSValidate.cpp
  10. 30
      js/src/ds/LifoAlloc.h
  11. 422
      js/src/frontend/BytecodeEmitter.cpp
  12. 2
      js/src/jit/AtomicOperations-inl.h
  13. 2
      js/src/jit/BaselineBailouts.cpp
  14. 2
      js/src/jit/BaselineCompiler.h
  15. 2
      js/src/jit/CodeGenerator.h
  16. 2
      js/src/jit/ExecutableAllocator.h
  17. 2
      js/src/jit/IonCaches.h
  18. 2
      js/src/jit/JitCommon.h
  19. 2
      js/src/jit/LIR.h
  20. 2
      js/src/jit/LOpcodes.h
  21. 12
      js/src/jit/Label.h
  22. 2
      js/src/jit/Lowering.h
  23. 2
      js/src/jit/MacroAssembler-inl.h
  24. 16
      js/src/jit/MacroAssembler.h
  25. 4
      js/src/jit/MoveEmitter.h
  26. 2
      js/src/jit/Registers.h
  27. 2
      js/src/jit/SharedICHelpers.h
  28. 2
      js/src/jit/SharedICRegisters.h
  29. 2
      js/src/jit/VMFunctions.cpp
  30. 3
      js/src/jit/arm/Assembler-arm.h
  31. 74
      js/src/jit/arm/MacroAssembler-arm.cpp
  32. 38
      js/src/jit/arm/MacroAssembler-arm.h
  33. 67
      js/src/jit/arm64/Bailouts-arm64.cpp
  34. 81
      js/src/jit/arm64/MacroAssembler-arm64.cpp
  35. 64
      js/src/jit/arm64/MacroAssembler-arm64.h
  36. 289
      js/src/jit/arm64/MoveEmitter-arm64.cpp
  37. 92
      js/src/jit/arm64/MoveEmitter-arm64.h
  38. 1193
      js/src/jit/arm64/Trampoline-arm64.cpp
  39. 2
      js/src/jit/mips32/Architecture-mips32.cpp
  40. 0
      js/src/jit/mips32/Architecture-mips32.h
  41. 5
      js/src/jit/mips32/Assembler-mips32.cpp
  42. 5
      js/src/jit/mips32/Assembler-mips32.h
  43. 0
      js/src/jit/mips32/AtomicOperations-mips32.h
  44. 2
      js/src/jit/mips32/Bailouts-mips32.cpp
  45. 0
      js/src/jit/mips32/Bailouts-mips32.h
  46. 2
      js/src/jit/mips32/BaselineCompiler-mips32.cpp
  47. 0
      js/src/jit/mips32/BaselineCompiler-mips32.h
  48. 0
      js/src/jit/mips32/BaselineIC-mips32.cpp
  49. 2
      js/src/jit/mips32/CodeGenerator-mips32.cpp
  50. 2
      js/src/jit/mips32/CodeGenerator-mips32.h
  51. 0
      js/src/jit/mips32/LIR-mips32.h
  52. 0
      js/src/jit/mips32/LOpcodes-mips32.h
  53. 2
      js/src/jit/mips32/Lowering-mips32.cpp
  54. 0
      js/src/jit/mips32/Lowering-mips32.h
  55. 71
      js/src/jit/mips32/MacroAssembler-mips32.cpp
  56. 57
      js/src/jit/mips32/MacroAssembler-mips32.h
  57. 2
      js/src/jit/mips32/MoveEmitter-mips32.cpp
  58. 0
      js/src/jit/mips32/MoveEmitter-mips32.h
  59. 0
      js/src/jit/mips32/SharedICHelpers-mips32.h
  60. 0
      js/src/jit/mips32/SharedICRegisters-mips32.h
  61. 4
      js/src/jit/mips32/Simulator-mips32.cpp
  62. 0
      js/src/jit/mips32/Simulator-mips32.h
  63. 4
      js/src/jit/mips32/Trampoline-mips32.cpp
  64. 16
      js/src/jit/x64/MacroAssembler-x64.cpp
  65. 8
      js/src/jit/x64/MacroAssembler-x64.h
  66. 4
      js/src/jit/x64/SharedICHelpers-x64.h
  67. 2
      js/src/jit/x86-shared/CodeGenerator-x86-shared.cpp
  68. 65
      js/src/jit/x86-shared/MacroAssembler-x86-shared.cpp
  69. 16
      js/src/jit/x86-shared/MacroAssembler-x86-shared.h
  70. 10
      js/src/jit/x86/MacroAssembler-x86.cpp
  71. 4
      js/src/jit/x86/SharedICHelpers-x86.h
  72. 2
      js/src/jit/x86/Trampoline-x86.cpp
  73. 2
      js/src/jsapi-tests/moz.build
  74. 6
      js/src/jsapi-tests/testJitMoveEmitterCycles-mips32.cpp
  75. 82
      js/src/jsapi.cpp
  76. 22
      js/src/moz.build
  77. 9
      js/src/vm/HelperThreads.cpp
  78. 2
      js/src/vm/Runtime.cpp
  79. 18
      python/mach/mach/base.py
  80. 9
      python/mach/mach/decorators.py
  81. 60
      python/mach/mach/dispatcher.py
  82. 7
      python/mozbuild/mozbuild/frontend/context.py
  83. 62
      python/mozbuild/mozbuild/frontend/emitter.py
  84. 100
      python/mozbuild/mozbuild/frontend/mach_commands.py
  85. 6
      python/mozbuild/mozbuild/testing.py
  86. 13
      testing/config/mozharness/android_arm_config.py
  87. 9
      testing/config/mozharness/android_panda_config.py
  88. 3
      testing/config/mozharness/android_x86_config.py
  89. 3
      testing/config/mozharness/b2g_desktop_config.py
  90. 2
      testing/config/mozharness/b2g_emulator_config.py
  91. 3
      testing/config/mozharness/linux_config.py
  92. 3
      testing/config/mozharness/mac_config.py
  93. 3
      testing/config/mozharness/taskcluster_linux_config.py
  94. 3
      testing/config/mozharness/windows_config.py
  95. 185
      testing/mach_commands.py
  96. 1312
      testing/mochitest/mach_commands.py
  97. 962
      testing/mochitest/mochitest_options.py
  98. 53
      testing/mochitest/runtests.py
  99. 39
      testing/mochitest/runtestsb2g.py
  100. 17
      testing/mochitest/runtestsremote.py

1
build/mach_bootstrap.py

@ -45,6 +45,7 @@ SEARCH_PATHS = [
'other-licenses/ply',
'xpcom/idl-parser',
'testing',
'testing/tools/autotry',
'testing/taskcluster',
'testing/xpcshell',
'testing/web-platform',

21
dom/html/HTMLMediaElement.cpp

@ -1855,14 +1855,15 @@ NS_IMETHODIMP HTMLMediaElement::SetMuted(bool aMuted)
}
already_AddRefed<DOMMediaStream>
HTMLMediaElement::CaptureStreamInternal(bool aFinishWhenEnded)
HTMLMediaElement::CaptureStreamInternal(bool aFinishWhenEnded,
MediaStreamGraph* aGraph)
{
nsIDOMWindow* window = OwnerDoc()->GetInnerWindow();
if (!window) {
return nullptr;
}
OutputMediaStream* out = mOutputStreams.AppendElement();
out->mStream = DOMMediaStream::CreateTrackUnionStream(window);
out->mStream = DOMMediaStream::CreateTrackUnionStream(window, aGraph);
nsRefPtr<nsIPrincipal> principal = GetCurrentPrincipal();
out->mStream->CombineWithPrincipal(principal);
out->mStream->SetCORSMode(mCORSMode);
@ -1874,8 +1875,8 @@ HTMLMediaElement::CaptureStreamInternal(bool aFinishWhenEnded)
// back into the output stream.
out->mStream->GetStream()->ChangeExplicitBlockerCount(1);
if (mDecoder) {
mDecoder->AddOutputStream(
out->mStream->GetStream()->AsProcessedStream(), aFinishWhenEnded);
mDecoder->AddOutputStream(out->mStream->GetStream()->AsProcessedStream(),
aFinishWhenEnded);
if (mReadyState >= HAVE_METADATA) {
// Expose the tracks to JS directly.
if (HasAudio()) {
@ -1893,9 +1894,10 @@ HTMLMediaElement::CaptureStreamInternal(bool aFinishWhenEnded)
}
already_AddRefed<DOMMediaStream>
HTMLMediaElement::MozCaptureStream(ErrorResult& aRv)
HTMLMediaElement::MozCaptureStream(ErrorResult& aRv,
MediaStreamGraph* aGraph)
{
nsRefPtr<DOMMediaStream> stream = CaptureStreamInternal(false);
nsRefPtr<DOMMediaStream> stream = CaptureStreamInternal(false, aGraph);
if (!stream) {
aRv.Throw(NS_ERROR_FAILURE);
return nullptr;
@ -1905,9 +1907,10 @@ HTMLMediaElement::MozCaptureStream(ErrorResult& aRv)
}
already_AddRefed<DOMMediaStream>
HTMLMediaElement::MozCaptureStreamUntilEnded(ErrorResult& aRv)
HTMLMediaElement::MozCaptureStreamUntilEnded(ErrorResult& aRv,
MediaStreamGraph* aGraph)
{
nsRefPtr<DOMMediaStream> stream = CaptureStreamInternal(true);
nsRefPtr<DOMMediaStream> stream = CaptureStreamInternal(true, aGraph);
if (!stream) {
aRv.Throw(NS_ERROR_FAILURE);
return nullptr;
@ -2820,7 +2823,7 @@ nsresult HTMLMediaElement::FinishDecoderSetup(MediaDecoder* aDecoder,
for (uint32_t i = 0; i < mOutputStreams.Length(); ++i) {
OutputMediaStream* ms = &mOutputStreams[i];
aDecoder->AddOutputStream(ms->mStream->GetStream()->AsProcessedStream(),
ms->mFinishWhenEnded);
ms->mFinishWhenEnded);
}
// Decoder successfully created, the decoder now owns the MediaResource

9
dom/html/HTMLMediaElement.h

@ -555,9 +555,11 @@ public:
return mAutoplayEnabled;
}
already_AddRefed<DOMMediaStream> MozCaptureStream(ErrorResult& aRv);
already_AddRefed<DOMMediaStream> MozCaptureStream(ErrorResult& aRv,
MediaStreamGraph* aGraph = nullptr);
already_AddRefed<DOMMediaStream> MozCaptureStreamUntilEnded(ErrorResult& aRv);
already_AddRefed<DOMMediaStream> MozCaptureStreamUntilEnded(ErrorResult& aRv,
MediaStreamGraph* aGraph = nullptr);
bool MozAudioCaptured() const
{
@ -709,7 +711,8 @@ protected:
* When aFinishWhenEnded is false, ending playback does not finish the stream.
* The stream will never finish.
*/
already_AddRefed<DOMMediaStream> CaptureStreamInternal(bool aFinishWhenEnded);
already_AddRefed<DOMMediaStream> CaptureStreamInternal(bool aFinishWhenEnded,
MediaStreamGraph* aGraph = nullptr);
/**
* Initialize a decoder as a clone of an existing decoder in another

44
dom/media/DOMMediaStream.cpp

@ -274,19 +274,26 @@ DOMMediaStream::IsFinished()
}
void
DOMMediaStream::InitSourceStream(nsIDOMWindow* aWindow)
DOMMediaStream::InitSourceStream(nsIDOMWindow* aWindow,
MediaStreamGraph* aGraph)
{
mWindow = aWindow;
MediaStreamGraph* gm = MediaStreamGraph::GetInstance();
InitStreamCommon(gm->CreateSourceStream(this));
if (!aGraph) {
aGraph = MediaStreamGraph::GetInstance();
}
InitStreamCommon(aGraph->CreateSourceStream(this));
}
void
DOMMediaStream::InitTrackUnionStream(nsIDOMWindow* aWindow)
DOMMediaStream::InitTrackUnionStream(nsIDOMWindow* aWindow,
MediaStreamGraph* aGraph)
{
mWindow = aWindow;
MediaStreamGraph* gm = MediaStreamGraph::GetInstance();
InitStreamCommon(gm->CreateTrackUnionStream(this));
if (!aGraph) {
aGraph = MediaStreamGraph::GetInstance();
}
InitStreamCommon(aGraph->CreateTrackUnionStream(this));
}
void
@ -300,18 +307,20 @@ DOMMediaStream::InitStreamCommon(MediaStream* aStream)
}
already_AddRefed<DOMMediaStream>
DOMMediaStream::CreateSourceStream(nsIDOMWindow* aWindow)
DOMMediaStream::CreateSourceStream(nsIDOMWindow* aWindow,
MediaStreamGraph* aGraph)
{
nsRefPtr<DOMMediaStream> stream = new DOMMediaStream();
stream->InitSourceStream(aWindow);
stream->InitSourceStream(aWindow, aGraph);
return stream.forget();
}
already_AddRefed<DOMMediaStream>
DOMMediaStream::CreateTrackUnionStream(nsIDOMWindow* aWindow)
DOMMediaStream::CreateTrackUnionStream(nsIDOMWindow* aWindow,
MediaStreamGraph* aGraph)
{
nsRefPtr<DOMMediaStream> stream = new DOMMediaStream();
stream->InitTrackUnionStream(aWindow);
stream->InitTrackUnionStream(aWindow, aGraph);
return stream.forget();
}
@ -623,18 +632,20 @@ DOMLocalMediaStream::Stop()
}
already_AddRefed<DOMLocalMediaStream>
DOMLocalMediaStream::CreateSourceStream(nsIDOMWindow* aWindow)
DOMLocalMediaStream::CreateSourceStream(nsIDOMWindow* aWindow,
MediaStreamGraph* aGraph)
{
nsRefPtr<DOMLocalMediaStream> stream = new DOMLocalMediaStream();
stream->InitSourceStream(aWindow);
stream->InitSourceStream(aWindow, aGraph);
return stream.forget();
}
already_AddRefed<DOMLocalMediaStream>
DOMLocalMediaStream::CreateTrackUnionStream(nsIDOMWindow* aWindow)
DOMLocalMediaStream::CreateTrackUnionStream(nsIDOMWindow* aWindow,
MediaStreamGraph* aGraph)
{
nsRefPtr<DOMLocalMediaStream> stream = new DOMLocalMediaStream();
stream->InitTrackUnionStream(aWindow);
stream->InitTrackUnionStream(aWindow, aGraph);
return stream.forget();
}
@ -649,9 +660,10 @@ DOMAudioNodeMediaStream::~DOMAudioNodeMediaStream()
already_AddRefed<DOMAudioNodeMediaStream>
DOMAudioNodeMediaStream::CreateTrackUnionStream(nsIDOMWindow* aWindow,
AudioNode* aNode)
AudioNode* aNode,
MediaStreamGraph* aGraph)
{
nsRefPtr<DOMAudioNodeMediaStream> stream = new DOMAudioNodeMediaStream(aNode);
stream->InitTrackUnionStream(aWindow);
stream->InitTrackUnionStream(aWindow, aGraph);
return stream.forget();
}

24
dom/media/DOMMediaStream.h

@ -32,6 +32,7 @@ namespace mozilla {
class DOMLocalMediaStream;
class MediaStream;
class MediaEngineSource;
class MediaStreamGraph;
namespace dom {
class AudioNode;
@ -178,14 +179,14 @@ public:
/**
* Create an nsDOMMediaStream whose underlying stream is a SourceMediaStream.
*/
static already_AddRefed<DOMMediaStream>
CreateSourceStream(nsIDOMWindow* aWindow);
static already_AddRefed<DOMMediaStream> CreateSourceStream(nsIDOMWindow* aWindow,
MediaStreamGraph* aGraph = nullptr);
/**
* Create an nsDOMMediaStream whose underlying stream is a TrackUnionStream.
*/
static already_AddRefed<DOMMediaStream>
CreateTrackUnionStream(nsIDOMWindow* aWindow);
static already_AddRefed<DOMMediaStream> CreateTrackUnionStream(nsIDOMWindow* aWindow,
MediaStreamGraph* aGraph = nullptr);
void SetLogicalStreamStartTime(StreamTime aTime)
{
@ -247,8 +248,10 @@ protected:
virtual ~DOMMediaStream();
void Destroy();
void InitSourceStream(nsIDOMWindow* aWindow);
void InitTrackUnionStream(nsIDOMWindow* aWindow);
void InitSourceStream(nsIDOMWindow* aWindow,
MediaStreamGraph* aGraph = nullptr);
void InitTrackUnionStream(nsIDOMWindow* aWindow,
MediaStreamGraph* aGraph = nullptr);
void InitStreamCommon(MediaStream* aStream);
already_AddRefed<AudioTrack> CreateAudioTrack(AudioStreamTrack* aStreamTrack);
already_AddRefed<VideoTrack> CreateVideoTrack(VideoStreamTrack* aStreamTrack);
@ -329,13 +332,15 @@ public:
* Create an nsDOMLocalMediaStream whose underlying stream is a SourceMediaStream.
*/
static already_AddRefed<DOMLocalMediaStream>
CreateSourceStream(nsIDOMWindow* aWindow);
CreateSourceStream(nsIDOMWindow* aWindow,
MediaStreamGraph* aGraph = nullptr);
/**
* Create an nsDOMLocalMediaStream whose underlying stream is a TrackUnionStream.
*/
static already_AddRefed<DOMLocalMediaStream>
CreateTrackUnionStream(nsIDOMWindow* aWindow);
CreateTrackUnionStream(nsIDOMWindow* aWindow,
MediaStreamGraph* aGraph = nullptr);
protected:
virtual ~DOMLocalMediaStream();
@ -358,7 +363,8 @@ public:
*/
static already_AddRefed<DOMAudioNodeMediaStream>
CreateTrackUnionStream(nsIDOMWindow* aWindow,
AudioNode* aNode);
AudioNode* aNode,
MediaStreamGraph* aGraph = nullptr);
protected:
~DOMAudioNodeMediaStream();

1
dom/media/MediaStreamGraph.cpp

@ -2012,6 +2012,7 @@ MediaStream::SetGraphImpl(MediaStreamGraphImpl* aGraph)
{
MOZ_ASSERT(!mGraph, "Should only be called once");
mGraph = aGraph;
mAudioChannelType = static_cast<AudioChannel>(aGraph->AudioChannel());
mBuffer.InitGraphRate(aGraph->GraphRate());
}

3
dom/media/webaudio/AudioContext.cpp

@ -335,7 +335,8 @@ AudioContext::CreateMediaElementSource(HTMLMediaElement& aMediaElement,
return nullptr;
}
nsRefPtr<DOMMediaStream> stream = aMediaElement.MozCaptureStream(aRv);
nsRefPtr<DOMMediaStream> stream = aMediaElement.MozCaptureStream(aRv,
mDestination->Stream()->Graph());
if (aRv.Failed()) {
return nullptr;
}

6
js/src/asmjs/AsmJSFrameIterator.cpp

@ -194,14 +194,14 @@ GenerateProfilingPrologue(MacroAssembler& masm, unsigned framePushed, AsmJSExit:
masm.bind(begin);
PushRetAddr(masm);
MOZ_ASSERT(PushedRetAddr == masm.currentOffset() - offsetAtBegin);
MOZ_ASSERT_IF(!masm.oom(), PushedRetAddr == masm.currentOffset() - offsetAtBegin);
masm.loadAsmJSActivation(scratch);
masm.push(Address(scratch, AsmJSActivation::offsetOfFP()));
MOZ_ASSERT(PushedFP == masm.currentOffset() - offsetAtBegin);
MOZ_ASSERT_IF(!masm.oom(), PushedFP == masm.currentOffset() - offsetAtBegin);
masm.storePtr(masm.getStackPointer(), Address(scratch, AsmJSActivation::offsetOfFP()));
MOZ_ASSERT(StoredFP == masm.currentOffset() - offsetAtBegin);
MOZ_ASSERT_IF(!masm.oom(), StoredFP == masm.currentOffset() - offsetAtBegin);
}
if (reason != AsmJSExit::None)

49
js/src/asmjs/AsmJSValidate.cpp

@ -3221,19 +3221,15 @@ class FunctionCompiler
labeledContinues_.init();
}
~FunctionCompiler()
void checkPostconditions()
{
#ifdef DEBUG
if (!m().hasError() && cx()->isJSContext() && !cx()->asJSContext()->isExceptionPending()) {
MOZ_ASSERT(loopStack_.empty());
MOZ_ASSERT(unlabeledBreaks_.empty());
MOZ_ASSERT(unlabeledContinues_.empty());
MOZ_ASSERT(labeledBreaks_.empty());
MOZ_ASSERT(labeledContinues_.empty());
MOZ_ASSERT(inDeadCode());
MOZ_ASSERT(pc_ == func_.size(), "all bytecode must be consumed");
}
#endif
MOZ_ASSERT(loopStack_.empty());
MOZ_ASSERT(unlabeledBreaks_.empty());
MOZ_ASSERT(unlabeledContinues_.empty());
MOZ_ASSERT(labeledBreaks_.empty());
MOZ_ASSERT(labeledContinues_.empty());
MOZ_ASSERT(inDeadCode());
MOZ_ASSERT(pc_ == func_.size(), "all bytecode must be consumed");
}
/************************* Read-only interface (after local scope setup) */
@ -4248,11 +4244,17 @@ class FunctionCompiler
// Prepare data structures
alloc_ = lifo_.new_<TempAllocator>(&lifo_);
if (!alloc_)
return false;
jitContext_.emplace(m_.cx(), alloc_);
MOZ_ASSERT(numLocals == argTypes.length() + varInitializers.length());
graph_ = lifo_.new_<MIRGraph>(alloc_);
if (!graph_)
return false;
info_ = lifo_.new_<CompileInfo>(numLocals);
if (!info_)
return false;
const OptimizationInfo* optimizationInfo = js_IonOptimizations.get(Optimization_AsmJS);
const JitCompileOptions options;
mirGen_ = lifo_.new_<MIRGenerator>(CompileCompartment::get(cx()->compartment()),
@ -4261,6 +4263,8 @@ class FunctionCompiler
&m().onOutOfBoundsLabel(),
&m().onConversionErrorLabel(),
m().usesSignalHandlersForOOB());
if (!mirGen_)
return false;
if (!newBlock(/* pred = */ nullptr, 0, &curBlock_))
return false;
@ -10269,6 +10273,7 @@ EmitMIR(ModuleCompiler& m, const AsmFunction& function, LifoAlloc& lifo,
jit::SpewBeginFunction(mir, nullptr);
f.checkPostconditions();
return mir;
}
@ -11090,7 +11095,7 @@ GenerateEntry(ModuleCompiler& m, unsigned exportIndex)
masm.move32(Imm32(true), ReturnReg);
masm.ret();
return m.finishGeneratingEntry(exportIndex, &begin) && !masm.oom();
return !masm.oom() && m.finishGeneratingEntry(exportIndex, &begin);
}
static void
@ -11244,7 +11249,7 @@ GenerateFFIInterpExit(ModuleCompiler& m, const ModuleCompiler::ExitDescriptor& e
Label profilingReturn;
GenerateAsmJSExitEpilogue(masm, framePushed, AsmJSExit::SlowFFI, &profilingReturn);
return m.finishGeneratingInterpExit(exitIndex, &begin, &profilingReturn) && !masm.oom();
return !masm.oom() && m.finishGeneratingInterpExit(exitIndex, &begin, &profilingReturn);
}
#if defined(JS_CODEGEN_ARM) || defined(JS_CODEGEN_MIPS)
@ -11538,7 +11543,7 @@ GenerateFFIIonExit(ModuleCompiler& m, const ModuleCompiler::ExitDescriptor& exit
MOZ_ASSERT(masm.framePushed() == 0);
return m.finishGeneratingJitExit(exitIndex, &begin, &profilingReturn) && !masm.oom();
return !masm.oom() && m.finishGeneratingJitExit(exitIndex, &begin, &profilingReturn);
}
// See "asm.js FFI calls" comment above.
@ -11660,7 +11665,7 @@ GenerateBuiltinThunk(ModuleCompiler& m, AsmJSExit::BuiltinKind builtin)
Label profilingReturn;
GenerateAsmJSExitEpilogue(masm, framePushed, AsmJSExit::Builtin(builtin), &profilingReturn);
return m.finishGeneratingBuiltinThunk(builtin, &begin, &profilingReturn) && !masm.oom();
return !masm.oom() && m.finishGeneratingBuiltinThunk(builtin, &begin, &profilingReturn);
}
static bool
@ -11668,7 +11673,7 @@ GenerateStackOverflowExit(ModuleCompiler& m, Label* throwLabel)
{
MacroAssembler& masm = m.masm();
GenerateAsmJSStackOverflowExit(masm, &m.stackOverflowLabel(), throwLabel);
return m.finishGeneratingInlineStub(&m.stackOverflowLabel()) && !masm.oom();
return !masm.oom() && m.finishGeneratingInlineStub(&m.stackOverflowLabel());
}
static bool
@ -11682,7 +11687,7 @@ GenerateOnDetachedLabelExit(ModuleCompiler& m, Label* throwLabel)
masm.call(AsmJSImmPtr(AsmJSImm_OnDetached));
masm.jump(throwLabel);
return m.finishGeneratingInlineStub(&m.onDetachedLabel()) && !masm.oom();
return !masm.oom() && m.finishGeneratingInlineStub(&m.onDetachedLabel());
}
static bool
@ -11700,7 +11705,7 @@ GenerateExceptionLabelExit(ModuleCompiler& m, Label* throwLabel, Label* exit, As
masm.call(AsmJSImmPtr(func));
masm.jump(throwLabel);
return m.finishGeneratingInlineStub(exit) && !masm.oom();
return !masm.oom() && m.finishGeneratingInlineStub(exit);
}
static const LiveRegisterSet AllRegsExceptSP(
@ -11866,7 +11871,7 @@ GenerateAsyncInterruptExit(ModuleCompiler& m, Label* throwLabel)
# error "Unknown architecture!"
#endif
return m.finishGeneratingInlineStub(&m.asyncInterruptLabel()) && !masm.oom();
return !masm.oom() && m.finishGeneratingInlineStub(&m.asyncInterruptLabel());
}
static bool
@ -11885,7 +11890,7 @@ GenerateSyncInterruptExit(ModuleCompiler& m, Label* throwLabel)
Label profilingReturn;
GenerateAsmJSExitEpilogue(masm, framePushed, AsmJSExit::Interrupt, &profilingReturn);
return m.finishGeneratingInterrupt(&m.syncInterruptLabel(), &profilingReturn) && !masm.oom();
return !masm.oom() && m.finishGeneratingInterrupt(&m.syncInterruptLabel(), &profilingReturn);
}
// If an exception is thrown, simply pop all frames (since asm.js does not
@ -11916,7 +11921,7 @@ GenerateThrowStub(ModuleCompiler& m, Label* throwLabel)
masm.mov(ImmWord(0), ReturnReg);
masm.ret();
return m.finishGeneratingInlineStub(throwLabel) && !masm.oom();
return !masm.oom() && m.finishGeneratingInlineStub(throwLabel);
}
static bool

30
js/src/ds/LifoAlloc.h

@ -214,6 +214,21 @@ class LifoAlloc
curSize_ -= size;
}
MOZ_ALWAYS_INLINE
void* allocImpl(size_t n) {
void* result;
if (latest && (result = latest->tryAlloc(n)))
return result;
if (!getOrCreateChunk(n))
return nullptr;
// Since we just created a large enough chunk, this can't fail.
result = latest->tryAlloc(n);
MOZ_ASSERT(result);
return result;
}
public:
explicit LifoAlloc(size_t defaultChunkSize)
: peakSize_(0)
@ -257,23 +272,12 @@ class LifoAlloc
MOZ_ALWAYS_INLINE
void* alloc(size_t n) {
JS_OOM_POSSIBLY_FAIL();
void* result;
if (latest && (result = latest->tryAlloc(n)))
return result;
if (!getOrCreateChunk(n))
return nullptr;
// Since we just created a large enough chunk, this can't fail.
result = latest->tryAlloc(n);
MOZ_ASSERT(result);
return result;
return allocImpl(n);
}
MOZ_ALWAYS_INLINE
void* allocInfallible(size_t n) {
if (void* result = alloc(n))
if (void* result = allocImpl(n))
return result;
CrashAtUnhandlableOOM("LifoAlloc::allocInfallible");
return nullptr;

422
js/src/frontend/BytecodeEmitter.cpp

@ -1902,9 +1902,431 @@ BytecodeEmitter::bindNameToSlot(ParseNode* pn)
bool
BytecodeEmitter::checkSideEffects(ParseNode* pn, bool* answer)
{
JS_CHECK_RECURSION(cx, return false);
if (!pn || *answer)
return true;
switch (pn->getKind()) {
// Trivial cases with no side effects.
case PNK_NEWTARGET:
case PNK_NOP:
case PNK_STRING:
case PNK_TEMPLATE_STRING:
case PNK_REGEXP:
case PNK_TRUE:
case PNK_FALSE:
case PNK_NULL:
case PNK_THIS:
case PNK_ELISION:
case PNK_GENERATOR:
case PNK_NUMBER:
case PNK_OBJECT_PROPERTY_NAME:
MOZ_ASSERT(pn->isArity(PN_NULLARY));
*answer = false;
return true;
case PNK_BREAK:
case PNK_CONTINUE:
case PNK_DEBUGGER:
MOZ_ASSERT(pn->isArity(PN_NULLARY));
*answer = true;
return true;
// Watch out for getters!
case PNK_SUPERPROP:
MOZ_ASSERT(pn->isArity(PN_NULLARY));
*answer = true;
return true;
// Again, getters.
case PNK_DOT:
MOZ_ASSERT(pn->isArity(PN_NAME));
*answer = true;
return true;
// Unary cases with side effects only if the child has them.
case PNK_TYPEOFEXPR:
case PNK_VOID:
case PNK_NOT:
case PNK_COMPUTED_NAME:
MOZ_ASSERT(pn->isArity(PN_UNARY));
return checkSideEffects(pn->pn_kid, answer);
// Looking up or evaluating the associated name could throw.
case PNK_TYPEOFNAME:
MOZ_ASSERT(pn->isArity(PN_UNARY));
*answer = true;
return true;
// These unary cases have side effects on the enclosing object/array,
// sure. But that's not the question this function answers: it's
// whether the operation may have a side effect on something *other* than
// the result of the overall operation in which it's embedded. The
// answer to that is no, for an object literal having a mutated prototype
// and an array comprehension containing no other effectful operations
// only produce a value, without affecting anything else.
case PNK_MUTATEPROTO:
case PNK_ARRAYPUSH:
MOZ_ASSERT(pn->isArity(PN_UNARY));
return checkSideEffects(pn->pn_kid, answer);
// Unary cases with obvious side effects.
case PNK_PREINCREMENT:
case PNK_POSTINCREMENT:
case PNK_PREDECREMENT:
case PNK_POSTDECREMENT:
case PNK_THROW:
MOZ_ASSERT(pn->isArity(PN_UNARY));
*answer = true;
return true;
// These might invoke valueOf/toString, even with a subexpression without
// side effects! Consider |+{ valueOf: null, toString: null }|.
case PNK_BITNOT:
case PNK_POS:
case PNK_NEG:
MOZ_ASSERT(pn->isArity(PN_UNARY));
*answer = true;
return true;
// This invokes the (user-controllable) iterator protocol.
case PNK_SPREAD:
MOZ_ASSERT(pn->isArity(PN_UNARY));
*answer = true;
return true;
case PNK_YIELD_STAR:
case PNK_YIELD:
MOZ_ASSERT(pn->isArity(PN_BINARY));
*answer = true;
return true;
// Deletion generally has side effects, even if isolated cases have none.
case PNK_DELETENAME:
case PNK_DELETEPROP:
case PNK_DELETESUPERPROP:
case PNK_DELETEELEM:
case PNK_DELETESUPERELEM:
MOZ_ASSERT(pn->isArity(PN_UNARY));
*answer = true;
return true;
// Deletion of a non-Reference expression has side effects only through
// evaluating the expression.
case PNK_DELETEEXPR: {
MOZ_ASSERT(pn->isArity(PN_UNARY));
ParseNode* expr = pn->pn_kid;
return checkSideEffects(expr, answer);
}
case PNK_SEMI:
MOZ_ASSERT(pn->isArity(PN_UNARY));
if (ParseNode* expr = pn->pn_kid)
return checkSideEffects(expr, answer);
*answer = false;
return true;
// Binary cases with obvious side effects.
case PNK_ASSIGN:
case PNK_ADDASSIGN:
case PNK_SUBASSIGN:
case PNK_BITORASSIGN:
case PNK_BITXORASSIGN:
case PNK_BITANDASSIGN:
case PNK_LSHASSIGN:
case PNK_RSHASSIGN:
case PNK_URSHASSIGN:
case PNK_MULASSIGN:
case PNK_DIVASSIGN:
case PNK_MODASSIGN:
MOZ_ASSERT(pn->isArity(PN_BINARY));
*answer = true;
return true;
case PNK_STATEMENTLIST:
case PNK_CATCHLIST:
// Strict equality operations and logical operators are well-behaved and
// perform no conversions.
case PNK_OR:
case PNK_AND:
case PNK_STRICTEQ:
case PNK_STRICTNE:
// Any subexpression of a comma expression could be effectful.
case PNK_COMMA:
MOZ_ASSERT(pn->pn_count > 0);
// Subcomponents of a literal may be effectful.
case PNK_ARRAY:
case PNK_OBJECT:
MOZ_ASSERT(pn->isArity(PN_LIST));
for (ParseNode* item = pn->pn_head; item; item = item->pn_next) {
if (!checkSideEffects(item, answer))
return false;
if (*answer)
return true;
}
return true;
// Most other binary operations (parsed as lists in SpiderMonkey) may
// perform conversions triggering side effects. Math operations perform
// ToNumber and may fail invoking invalid user-defined toString/valueOf:
// |5 < { toString: null }|. |instanceof| throws if provided a
// non-object constructor: |null instanceof null|. |in| throws if given
// a non-object RHS: |5 in null|.
case PNK_BITOR:
case PNK_BITXOR:
case PNK_BITAND:
case PNK_EQ:
case PNK_NE:
case PNK_LT:
case PNK_LE:
case PNK_GT:
case PNK_GE:
case PNK_INSTANCEOF:
case PNK_IN:
case PNK_LSH:
case PNK_RSH:
case PNK_URSH:
case PNK_ADD:
case PNK_SUB:
case PNK_STAR:
case PNK_DIV:
case PNK_MOD:
MOZ_ASSERT(pn->isArity(PN_LIST));
MOZ_ASSERT(pn->pn_count >= 2);
*answer = true;
return true;
case PNK_DEFAULT:
case PNK_COLON:
case PNK_CASE:
MOZ_ASSERT(pn->isArity(PN_BINARY));
if (!checkSideEffects(pn->pn_left, answer))
return false;
if (*answer)
return true;
return checkSideEffects(pn->pn_right, answer);
// More getters.
case PNK_ELEM:
MOZ_ASSERT(pn->isArity(PN_BINARY));
*answer = true;
return true;
// Again, getters.
case PNK_SUPERELEM:
MOZ_ASSERT(pn->isArity(PN_UNARY));
*answer = true;
return true;
// These affect visible names in this code, or in other code.
case PNK_IMPORT:
case PNK_EXPORT_FROM:
case PNK_EXPORT_DEFAULT:
MOZ_ASSERT(pn->isArity(PN_BINARY));
*answer = true;
return true;
// Likewise.
case PNK_EXPORT:
MOZ_ASSERT(pn->isArity(PN_UNARY));
*answer = true;
return true;
// Every part of a loop might be effect-free, but looping infinitely *is*
// an effect. (Language lawyer trivia: C++ says threads can be assumed
// to exit or have side effects, C++14 [intro.multithread]p27, so a C++
// implementation's equivalent of the below could set |*answer = false;|
// if all loop sub-nodes set |*answer = false|!)
case PNK_DOWHILE:
case PNK_WHILE:
case PNK_FOR:
MOZ_ASSERT(pn->isArity(PN_BINARY));
*answer = true;
return true;
// Declarations affect the name set of the relevant scope.
case PNK_VAR:
case PNK_CONST:
case PNK_LET:
case PNK_GLOBALCONST:
MOZ_ASSERT(pn->isArity(PN_LIST));
*answer = true;
return true;
case PNK_CONDITIONAL:
MOZ_ASSERT(pn->isArity(PN_TERNARY));
if (!checkSideEffects(pn->pn_kid1, answer))
return false;
if (*answer)
return true;
if (!checkSideEffects(pn->pn_kid2, answer))
return false;
if (*answer)
return true;
return checkSideEffects(pn->pn_kid3, answer);
case PNK_IF:
MOZ_ASSERT(pn->isArity(PN_TERNARY));
if (!checkSideEffects(pn->pn_kid1, answer))
return false;
if (*answer)
return true;
if (!checkSideEffects(pn->pn_kid2, answer))
return false;
if (*answer)
return true;
if (ParseNode* elseNode = pn->pn_kid3) {
if (!checkSideEffects(elseNode, answer))
return false;
}
return true;
// Function calls can invoke non-local code.
case PNK_NEW:
case PNK_CALL:
case PNK_TAGGED_TEMPLATE:
MOZ_ASSERT(pn->isArity(PN_LIST));
*answer = true;
return true;
// Classes typically introduce names. Even if no name is introduced,
// the heritage and/or class body (through computed property names)
// usually have effects.
case PNK_CLASS:
MOZ_ASSERT(pn->isArity(PN_TERNARY));
*answer = true;
return true;
// |with| calls |ToObject| on its expression and so throws if that value
// is null/undefined.
case PNK_WITH:
MOZ_ASSERT(pn->isArity(PN_BINARY));
*answer = true;
return true;
case PNK_RETURN:
MOZ_ASSERT(pn->isArity(PN_BINARY));
*answer = true;
return true;
case PNK_NAME:
MOZ_ASSERT(pn->isArity(PN_NAME));
*answer = true;
return true;
// Shorthands could trigger getters: the |x| in the object literal in
// |with ({ get x() { throw 42; } }) ({ x });|, for example, triggers
// one. (Of course, it isn't necessary to use |with| for a shorthand to
// trigger a getter.)
case PNK_SHORTHAND:
MOZ_ASSERT(pn->isArity(PN_BINARY));
*answer = true;
return true;
case PNK_FUNCTION:
MOZ_ASSERT(pn->isArity(PN_CODE));
/*
* A named function, contrary to ES3, is no longer effectful, because
* we bind its name lexically (using JSOP_CALLEE) instead of creating
* an Object instance and binding a readonly, permanent property in it
* (the object and binding can be detected and hijacked or captured).
* This is a bug fix to ES3; it is fixed in ES3.1 drafts.
*/
*answer = false;
return true;
// Generator expressions have no side effects on their own.
case PNK_GENEXP:
MOZ_ASSERT(pn->isArity(PN_LIST));
*answer = false;
return true;
case PNK_TRY:
MOZ_ASSERT(pn->isArity(PN_TERNARY));
if (!checkSideEffects(pn->pn_kid1, answer))
return false;
if (*answer)
return true;
if (ParseNode* catchList = pn->pn_kid2) {
MOZ_ASSERT(catchList->isKind(PNK_CATCHLIST));
if (!checkSideEffects(catchList, answer))
return false;
if (*answer)
return true;
}
if (ParseNode* finallyBlock = pn->pn_kid3) {
if (!checkSideEffects(finallyBlock, answer))
return false;
}
return true;
case PNK_CATCH:
MOZ_ASSERT(pn->isArity(PN_TERNARY));
if (!checkSideEffects(pn->pn_kid1, answer))
return false;
if (*answer)
return true;
if (ParseNode* cond = pn->pn_kid2) {
if (!checkSideEffects(cond, answer))
return false;
if (*answer)
return true;
}
return checkSideEffects(pn->pn_kid3, answer);
case PNK_SWITCH:
case PNK_LETBLOCK:
MOZ_ASSERT(pn->isArity(PN_BINARY));
if (!checkSideEffects(pn->pn_left, answer))
return false;
return *answer || checkSideEffects(pn->pn_right, answer);
case PNK_LABEL:
case PNK_LEXICALSCOPE:
MOZ_ASSERT(pn->isArity(PN_NAME));
return checkSideEffects(pn->expr(), answer);
// We could methodically check every interpolated expression, but it's
// probably not worth the trouble. Treat template strings as effect-free
// only if they don't contain any substitutions.
case PNK_TEMPLATE_STRING_LIST:
MOZ_ASSERT(pn->isArity(PN_LIST));
MOZ_ASSERT(pn->pn_count > 0);
MOZ_ASSERT((pn->pn_count % 2) == 1,
"template strings must alternate template and substitution "
"parts");
*answer = pn->pn_count > 1;
return true;
case PNK_ARRAYCOMP:
MOZ_ASSERT(pn->isArity(PN_LIST));
MOZ_ASSERT(pn->pn_count == 1);
return checkSideEffects(pn->pn_head, answer);
case PNK_ARGSBODY:
*answer = true;
return true;
case PNK_FORIN: // by PNK_FOR
case PNK_FOROF: // by PNK_FOR
case PNK_FORHEAD: // by PNK_FOR
case PNK_FRESHENBLOCK: // by PNK_FOR
case PNK_CLASSMETHOD: // by PNK_CLASS
case PNK_CLASSNAMES: // by PNK_CLASS
case PNK_CLASSMETHODLIST: // by PNK_CLASS
case PNK_IMPORT_SPEC_LIST: // by PNK_IMPORT
case PNK_IMPORT_SPEC: // by PNK_IMPORT
case PNK_EXPORT_BATCH_SPEC:// by PNK_EXPORT
case PNK_EXPORT_SPEC_LIST: // by PNK_EXPORT
case PNK_EXPORT_SPEC: // by PNK_EXPORT
case PNK_CALLSITEOBJ: // by PNK_TAGGED_TEMPLATE
MOZ_CRASH("handled by parent nodes");
case PNK_LIMIT: // invalid sentinel value
MOZ_CRASH("invalid node kind");
}
switch (pn->getArity()) {
case PN_CODE:
/*

2
js/src/jit/AtomicOperations-inl.h

@ -12,7 +12,7 @@
#elif defined(JS_CODEGEN_ARM64)
# include "jit/arm64/AtomicOperations-arm64.h"
#elif defined(JS_CODEGEN_MIPS)
# include "jit/mips/AtomicOperations-mips.h"
# include "jit/mips32/AtomicOperations-mips32.h"
#elif defined(JS_CODEGEN_NONE)
# include "jit/none/AtomicOperations-none.h"
#elif defined(JS_CODEGEN_X86) || defined(JS_CODEGEN_X64)

2
js/src/jit/BaselineBailouts.cpp

@ -13,7 +13,7 @@
#include "jit/BaselineJIT.h"
#include "jit/CompileInfo.h"
#include "jit/JitSpewer.h"
#include "jit/mips/Simulator-mips.h"
#include "jit/mips32/Simulator-mips32.h"
#include "jit/Recover.h"
#include "jit/RematerializedFrame.h"

2
js/src/jit/BaselineCompiler.h

@ -17,7 +17,7 @@
#elif defined(JS_CODEGEN_ARM64)
# include "jit/arm64/BaselineCompiler-arm64.h"
#elif defined(JS_CODEGEN_MIPS)
# include "jit/mips/BaselineCompiler-mips.h"
# include "jit/mips32/BaselineCompiler-mips32.h"
#elif defined(JS_CODEGEN_NONE)
# include "jit/none/BaselineCompiler-none.h"
#else

2
js/src/jit/CodeGenerator.h

@ -21,7 +21,7 @@
#elif defined(JS_CODEGEN_ARM64)
# include "jit/arm64/CodeGenerator-arm64.h"
#elif defined(JS_CODEGEN_MIPS)
# include "jit/mips/CodeGenerator-mips.h"
# include "jit/mips32/CodeGenerator-mips32.h"
#elif defined(JS_CODEGEN_NONE)
# include "jit/none/CodeGenerator-none.h"
#else

2
js/src/jit/ExecutableAllocator.h

@ -34,7 +34,7 @@
#include "jsalloc.h"
#include "jit/arm/Simulator-arm.h"
#include "jit/mips/Simulator-mips.h"
#include "jit/mips32/Simulator-mips32.h"
#include "js/GCAPI.h"
#include "js/HashTable.h"
#include "js/Vector.h"

2
js/src/jit/IonCaches.h

@ -12,7 +12,7 @@
#elif defined(JS_CODEGEN_ARM64)
# include "jit/arm64/Assembler-arm64.h"
#elif defined(JS_CODEGEN_MIPS)
# include "jit/mips/Assembler-mips.h"
# include "jit/mips32/Assembler-mips32.h"
#endif
#include "jit/JitCompartment.h"
#include "jit/Registers.h"

2
js/src/jit/JitCommon.h

@ -14,7 +14,7 @@
#elif defined(JS_SIMULATOR_ARM64)
# include "jit/arm64/vixl/Simulator-vixl.h"
#elif defined(JS_SIMULATOR_MIPS)
#include "jit/mips/Simulator-mips.h"
#include "jit/mips32/Simulator-mips32.h"
#endif
#ifdef JS_SIMULATOR

2
js/src/jit/LIR.h

@ -1828,7 +1828,7 @@ LAllocation::toRegister() const
#elif defined(JS_CODEGEN_ARM64)
# include "jit/arm64/LIR-arm64.h"
#elif defined(JS_CODEGEN_MIPS)
# include "jit/mips/LIR-mips.h"
# include "jit/mips32/LIR-mips32.h"
#elif defined(JS_CODEGEN_NONE)
# include "jit/none/LIR-none.h"
#else

2
js/src/jit/LOpcodes.h

@ -363,7 +363,7 @@
#elif defined(JS_CODEGEN_ARM64)
# include "jit/arm64/LOpcodes-arm64.h"
#elif defined(JS_CODEGEN_MIPS)
# include "jit/mips/LOpcodes-mips.h"
# include "jit/mips32/LOpcodes-mips32.h"
#elif defined(JS_CODEGEN_NONE)
# include "jit/none/LOpcodes-none.h"
#else

12
js/src/jit/Label.h

@ -81,14 +81,10 @@ class Label : public LabelBase
{
#ifdef DEBUG
// The assertion below doesn't hold if an error occurred.
if (OOM_counter > OOM_maxAllocations)
return;
if (JitContext* context = MaybeGetJitContext()) {
if (context->runtime->hadOutOfMemory())
return;
}
MOZ_ASSERT(!used());
JitContext* context = MaybeGetJitContext();
bool hadError = OOM_counter >= OOM_maxAllocations ||
(context && context->runtime->hadOutOfMemory());
MOZ_ASSERT_IF(!hadError, !used());
#endif
}
};

2
js/src/jit/Lowering.h

@ -20,7 +20,7 @@
#elif defined(JS_CODEGEN_ARM64)
# include "jit/arm64/Lowering-arm64.h"
#elif defined(JS_CODEGEN_MIPS)
# include "jit/mips/Lowering-mips.h"
# include "jit/mips32/Lowering-mips32.h"
#elif defined(JS_CODEGEN_NONE)
# include "jit/none/Lowering-none.h"
#else

2
js/src/jit/MacroAssembler-inl.h

@ -57,7 +57,7 @@ MacroAssembler::PushWithPatch(ImmPtr imm)
}
// ===============================================================
// Call functions.
// Simple call functions.
void
MacroAssembler::call(const CallSiteDesc& desc, const Register reg)

16
js/src/jit/MacroAssembler.h

@ -20,7 +20,7 @@
#elif defined(JS_CODEGEN_ARM64)
# include "jit/arm64/MacroAssembler-arm64.h"
#elif defined(JS_CODEGEN_MIPS)
# include "jit/mips/MacroAssembler-mips.h"
# include "jit/mips32/MacroAssembler-mips32.h"
#elif defined(JS_CODEGEN_NONE)
# include "jit/none/MacroAssembler-none.h"
#else
@ -350,9 +350,17 @@ class MacroAssembler : public MacroAssemblerSpecific
public:
// ===============================================================
// Call functions.
using MacroAssemblerSpecific::call; // legacy
// Simple call functions.
void call(Register reg) PER_ARCH;
void call(const Address& addr) PER_ARCH ONLY_X86_X64;
void call(Label* label) PER_ARCH;
void call(ImmWord imm) PER_ARCH;
// Call a target native function, which is neither traceable nor movable.
void call(ImmPtr imm) PER_ARCH;
void call(AsmJSImmPtr imm) PER_ARCH;
// Call a target JitCode, which must be traceable, and may be movable.
void call(JitCode* c) PER_ARCH;
inline void call(const CallSiteDesc& desc, const Register reg);
inline void call(const CallSiteDesc& desc, Label* label);

4
js/src/jit/MoveEmitter.h

@ -12,9 +12,9 @@
#elif defined(JS_CODEGEN_ARM)
# include "jit/arm/MoveEmitter-arm.h"
#elif defined(JS_CODEGEN_ARM64)
// # include "jit/arm64/MoveEmitter-arm64.h"
# include "jit/arm64/MoveEmitter-arm64.h"
#elif defined(JS_CODEGEN_MIPS)
# include "jit/mips/MoveEmitter-mips.h"
# include "jit/mips32/MoveEmitter-mips32.h"
#elif defined(JS_CODEGEN_NONE)
# include "jit/none/MoveEmitter-none.h"
#else

2
js/src/jit/Registers.h

@ -17,7 +17,7 @@
#elif defined(JS_CODEGEN_ARM64)
# include "jit/arm64/Architecture-arm64.h"
#elif defined(JS_CODEGEN_MIPS)
# include "jit/mips/Architecture-mips.h"
# include "jit/mips32/Architecture-mips32.h"
#elif defined(JS_CODEGEN_NONE)
# include "jit/none/Architecture-none.h"
#else

2
js/src/jit/SharedICHelpers.h

@ -16,7 +16,7 @@
#elif defined(JS_CODEGEN_ARM64)
# include "jit/arm64/SharedICHelpers-arm64.h"
#elif defined(JS_CODEGEN_MIPS)
# include "jit/mips/SharedICHelpers-mips.h"
# include "jit/mips32/SharedICHelpers-mips32.h"
#elif defined(JS_CODEGEN_NONE)
# include "jit/none/SharedICHelpers-none.h"
#else

2
js/src/jit/SharedICRegisters.h

@ -16,7 +16,7 @@
#elif defined(JS_CODEGEN_ARM64)
# include "jit/arm64/SharedICRegisters-arm64.h"
#elif defined(JS_CODEGEN_MIPS)
# include "jit/mips/SharedICRegisters-mips.h"
# include "jit/mips32/SharedICRegisters-mips32.h"
#elif defined(JS_CODEGEN_NONE)
# include "jit/none/SharedICRegisters-none.h"
#else

2
js/src/jit/VMFunctions.cpp

@ -12,7 +12,7 @@
#include "jit/BaselineIC.h"
#include "jit/JitCompartment.h"
#include "jit/JitFrames.h"
#include "jit/mips/Simulator-mips.h"
#include "jit/mips32/Simulator-mips32.h"
#include "vm/ArrayObject.h"
#include "vm/Debugger.h"
#include "vm/Interpreter.h"

3
js/src/jit/arm/Assembler-arm.h

@ -1638,9 +1638,6 @@ class Assembler : public AssemblerShared
return actualOffset(offset);
}
void call(Label* label);
void call(void* target);
void as_bkpt();
public:

74
js/src/jit/arm/MacroAssembler-arm.cpp

@ -4122,7 +4122,7 @@ MacroAssemblerARMCompat::callWithABI(AsmJSImmPtr imm, MoveOp::Type result)
{
uint32_t stackAdjust;
callWithABIPre(&stackAdjust, /* callFromAsmJS = */ true);
call(imm);
asMasm().call(imm);
callWithABIPost(stackAdjust, result);
}
@ -4135,7 +4135,7 @@ MacroAssemblerARMCompat::callWithABI(const Address& fun, MoveOp::Type result)
ma_ldr(fun, r12);
uint32_t stackAdjust;
callWithABIPre(&stackAdjust);
call(r12);
asMasm().call(r12);
callWithABIPost(stackAdjust, result);
}
@ -4146,7 +4146,7 @@ MacroAssemblerARMCompat::callWithABI(Register fun, MoveOp::Type result)
ma_mov(fun, r12);
uint32_t stackAdjust;
callWithABIPre(&stackAdjust);
call(r12);
asMasm().call(r12);
callWithABIPost(stackAdjust, result);
}
@ -5162,16 +5162,24 @@ MacroAssemblerARMCompat::profilerExitFrame()
branch(GetJitContext()->runtime->jitRuntime()->getProfilerExitFrameTail());
}
MacroAssembler &
void
MacroAssemblerARMCompat::callAndPushReturnAddress(Label* label)
{
AutoForbidPools afp(this, 2);
ma_push(pc);
asMasm().call(label);
}
MacroAssembler&
MacroAssemblerARMCompat::asMasm()
{
return *static_cast<MacroAssembler *>(this);
return *static_cast<MacroAssembler*>(this);
}
const MacroAssembler &
const MacroAssembler&
MacroAssemblerARMCompat::asMasm() const
{
return *static_cast<const MacroAssembler *>(this);
return *static_cast<const MacroAssembler*>(this);
}
// ===============================================================
@ -5312,3 +5320,55 @@ MacroAssembler::reserveStack(uint32_t amount)
ma_sub(Imm32(amount), sp);
adjustFrame(amount);
}
// ===============================================================
// Simple call functions.
void
MacroAssembler::call(Register reg)
{
as_blx(reg);
}
void
MacroAssembler::call(Label* label)
{
// For now, assume that it'll be nearby?
as_bl(label, Always);
}
void
MacroAssembler::call(ImmWord imm)
{
call(ImmPtr((void*)imm.value));
}
void
MacroAssembler::call(ImmPtr imm)
{
BufferOffset bo = m_buffer.nextOffset();
addPendingJump(bo, imm, Relocation::HARDCODED);
ma_call(imm);
}
void
MacroAssembler::call(AsmJSImmPtr imm)
{
movePtr(imm, CallReg);
call(CallReg);
}
void
MacroAssembler::call(JitCode* c)
{
BufferOffset bo = m_buffer.nextOffset();
addPendingJump(bo, ImmPtr(c->raw()), Relocation::JITCODE);
RelocStyle rs;
if (HasMOVWT())
rs = L_MOVWT;
else
rs = L_LDR;
ma_movPatchable(ImmPtr(c->raw()), ScratchRegister, Always, rs);
ma_callJitHalfPush(ScratchRegister);
}

38
js/src/jit/arm/MacroAssembler-arm.h

@ -538,7 +538,6 @@ class MacroAssemblerARMCompat : public MacroAssemblerARM
{ }
public:
using MacroAssemblerARM::call;
// Jumps + other functions that should be called from non-arm specific
// code. Basically, an x86 front end on top of the ARM code.
@ -567,42 +566,7 @@ class MacroAssemblerARMCompat : public MacroAssemblerARM