From bf1fa2ccb5e7409910b99dc46b616e44c66ade68 Mon Sep 17 00:00:00 2001 From: Sebastien Hertz Date: Tue, 9 Jun 2015 14:09:14 +0200 Subject: [PATCH] Follow up on CL 151605 - Fixes return type of StackedShadowFrameRecord::GetType - Makes StackedShadowFrameType an enum class (scoped enum) - Moves DeoptimizationReturnValueRecord and StackedShadowFrameRecord to thread.cc file and use forward declaration in thread.h header - Fixes tools/generate-operator-out.py for scoped enum classes. Bug: 20845490 (cherry picked from commit f795869da0a1fa006fdcdacd8afb6149a63fc1a7) Change-Id: I6b67e288b1db563699161e58ec2e2330d42dd8f5 --- runtime/art_method.cc | 3 +- runtime/interpreter/interpreter_common.cc | 2 +- runtime/quick_exception_handler.cc | 7 +++-- runtime/thread.cc | 46 ++++++++++++++++++++++++++++- runtime/thread.h | 49 +++---------------------------- tools/generate-operator-out.py | 10 ++++--- 6 files changed, 62 insertions(+), 55 deletions(-) diff --git a/runtime/art_method.cc b/runtime/art_method.cc index 478a87ef7..16c099d31 100644 --- a/runtime/art_method.cc +++ b/runtime/art_method.cc @@ -424,7 +424,8 @@ void ArtMethod::Invoke(Thread* self, uint32_t* args, uint32_t args_size, JValue* // exception was thrown to force the activations to be removed from the // stack. Continue execution in the interpreter. self->ClearException(); - ShadowFrame* shadow_frame = self->PopStackedShadowFrame(kDeoptimizationShadowFrame); + ShadowFrame* shadow_frame = + self->PopStackedShadowFrame(StackedShadowFrameType::kDeoptimizationShadowFrame); result->SetJ(self->PopDeoptimizationReturnValue().GetJ()); self->SetTopOfStack(nullptr); self->SetTopOfShadowStack(shadow_frame); diff --git a/runtime/interpreter/interpreter_common.cc b/runtime/interpreter/interpreter_common.cc index 3f2e6db71..86a79cead 100644 --- a/runtime/interpreter/interpreter_common.cc +++ b/runtime/interpreter/interpreter_common.cc @@ -518,7 +518,7 @@ bool DoCall(ArtMethod* called_method, Thread* self, ShadowFrame& shadow_frame, // We might need to do class loading, which incurs a thread state change to kNative. So // register the shadow frame as under construction and allow suspension again. ScopedStackedShadowFramePusher pusher( - self, new_shadow_frame, kShadowFrameUnderConstruction); + self, new_shadow_frame, StackedShadowFrameType::kShadowFrameUnderConstruction); self->EndAssertNoThreadSuspension(old_cause); // We need to do runtime check on reference assignment. We need to load the shorty diff --git a/runtime/quick_exception_handler.cc b/runtime/quick_exception_handler.cc index a10c5c820..02baad758 100644 --- a/runtime/quick_exception_handler.cc +++ b/runtime/quick_exception_handler.cc @@ -178,7 +178,7 @@ class DeoptimizeStackVisitor FINAL : public StackVisitor { // In case there is no deoptimized shadow frame for this upcall, we still // need to push a nullptr to the stack since there is always a matching pop after // the long jump. - self_->PushStackedShadowFrame(nullptr, kDeoptimizationShadowFrame); + self_->PushStackedShadowFrame(nullptr, StackedShadowFrameType::kDeoptimizationShadowFrame); stacked_shadow_frame_pushed_ = true; } return false; // End stack walk. @@ -212,7 +212,8 @@ class DeoptimizeStackVisitor FINAL : public StackVisitor { CHECK(verifier_success) << PrettyMethod(m); ShadowFrame* new_frame = ShadowFrame::CreateDeoptimizedFrame(num_regs, nullptr, m, dex_pc); { - ScopedStackedShadowFramePusher pusher(self_, new_frame, kShadowFrameUnderConstruction); + ScopedStackedShadowFramePusher pusher(self_, new_frame, + StackedShadowFrameType::kShadowFrameUnderConstruction); const std::vector kinds(verifier.DescribeVRegs(dex_pc)); // Markers for dead values, used when the verifier knows a Dex register is undefined, @@ -318,7 +319,7 @@ class DeoptimizeStackVisitor FINAL : public StackVisitor { // Will be popped after the long jump after DeoptimizeStack(), // right before interpreter::EnterInterpreterFromDeoptimize(). stacked_shadow_frame_pushed_ = true; - self_->PushStackedShadowFrame(new_frame, kDeoptimizationShadowFrame); + self_->PushStackedShadowFrame(new_frame, StackedShadowFrameType::kDeoptimizationShadowFrame); } prev_shadow_frame_ = new_frame; return true; diff --git a/runtime/thread.cc b/runtime/thread.cc index e79c5e648..f314f6124 100644 --- a/runtime/thread.cc +++ b/runtime/thread.cc @@ -147,6 +147,50 @@ void Thread::ResetQuickAllocEntryPointsForThread() { ResetQuickAllocEntryPoints(&tlsPtr_.quick_entrypoints); } +class DeoptimizationReturnValueRecord { + public: + DeoptimizationReturnValueRecord(const JValue& ret_val, + bool is_reference, + DeoptimizationReturnValueRecord* link) + : ret_val_(ret_val), is_reference_(is_reference), link_(link) {} + + JValue GetReturnValue() const { return ret_val_; } + bool IsReference() const { return is_reference_; } + DeoptimizationReturnValueRecord* GetLink() const { return link_; } + mirror::Object** GetGCRoot() { + DCHECK(is_reference_); + return ret_val_.GetGCRoot(); + } + + private: + JValue ret_val_; + const bool is_reference_; + DeoptimizationReturnValueRecord* const link_; + + DISALLOW_COPY_AND_ASSIGN(DeoptimizationReturnValueRecord); +}; + +class StackedShadowFrameRecord { + public: + StackedShadowFrameRecord(ShadowFrame* shadow_frame, + StackedShadowFrameType type, + StackedShadowFrameRecord* link) + : shadow_frame_(shadow_frame), + type_(type), + link_(link) {} + + ShadowFrame* GetShadowFrame() const { return shadow_frame_; } + StackedShadowFrameType GetType() const { return type_; } + StackedShadowFrameRecord* GetLink() const { return link_; } + + private: + ShadowFrame* const shadow_frame_; + const StackedShadowFrameType type_; + StackedShadowFrameRecord* const link_; + + DISALLOW_COPY_AND_ASSIGN(StackedShadowFrameRecord); +}; + void Thread::PushAndClearDeoptimizationReturnValue() { DeoptimizationReturnValueRecord* record = new DeoptimizationReturnValueRecord( tls64_.deoptimization_return_value, @@ -174,7 +218,7 @@ void Thread::PushStackedShadowFrame(ShadowFrame* sf, StackedShadowFrameType type ShadowFrame* Thread::PopStackedShadowFrame(StackedShadowFrameType type) { StackedShadowFrameRecord* record = tlsPtr_.stacked_shadow_frame_record; DCHECK(record != nullptr); - DCHECK(record->GetType() == type); + DCHECK_EQ(record->GetType(), type); tlsPtr_.stacked_shadow_frame_record = record->GetLink(); ShadowFrame* shadow_frame = record->GetShadowFrame(); delete record; diff --git a/runtime/thread.h b/runtime/thread.h index 8eb92bcf9..0e71c08b0 100644 --- a/runtime/thread.h +++ b/runtime/thread.h @@ -74,6 +74,7 @@ class ClassLinker; class Closure; class Context; struct DebugInvokeReq; +class DeoptimizationReturnValueRecord; class DexFile; class JavaVMExt; struct JNIEnvExt; @@ -82,6 +83,7 @@ class Runtime; class ScopedObjectAccessAlreadyRunnable; class ShadowFrame; class SingleStepControl; +class StackedShadowFrameRecord; class Thread; class ThreadList; @@ -99,55 +101,11 @@ enum ThreadFlag { kCheckpointRequest = 2 // Request that the thread do some checkpoint work and then continue. }; -enum StackedShadowFrameType { +enum class StackedShadowFrameType { kShadowFrameUnderConstruction, kDeoptimizationShadowFrame }; -class StackedShadowFrameRecord { - public: - StackedShadowFrameRecord(ShadowFrame* shadow_frame, - StackedShadowFrameType type, - StackedShadowFrameRecord* link) - : shadow_frame_(shadow_frame), - type_(type), - link_(link) {} - - ShadowFrame* GetShadowFrame() const { return shadow_frame_; } - bool GetType() const { return type_; } - StackedShadowFrameRecord* GetLink() const { return link_; } - - private: - ShadowFrame* const shadow_frame_; - const StackedShadowFrameType type_; - StackedShadowFrameRecord* const link_; - - DISALLOW_COPY_AND_ASSIGN(StackedShadowFrameRecord); -}; - -class DeoptimizationReturnValueRecord { - public: - DeoptimizationReturnValueRecord(const JValue& ret_val, - bool is_reference, - DeoptimizationReturnValueRecord* link) - : ret_val_(ret_val), is_reference_(is_reference), link_(link) {} - - JValue GetReturnValue() const { return ret_val_; } - bool IsReference() const { return is_reference_; } - DeoptimizationReturnValueRecord* GetLink() const { return link_; } - mirror::Object** GetGCRoot() { - DCHECK(is_reference_); - return ret_val_.GetGCRoot(); - } - - private: - JValue ret_val_; - const bool is_reference_; - DeoptimizationReturnValueRecord* const link_; - - DISALLOW_COPY_AND_ASSIGN(DeoptimizationReturnValueRecord); -}; - static constexpr size_t kNumRosAllocThreadLocalSizeBrackets = 34; // Thread's stack layout for implicit stack overflow checks: @@ -1371,6 +1329,7 @@ class ScopedStackedShadowFramePusher { }; std::ostream& operator<<(std::ostream& os, const Thread& thread); +std::ostream& operator<<(std::ostream& os, const StackedShadowFrameType& thread); } // namespace art diff --git a/tools/generate-operator-out.py b/tools/generate-operator-out.py index 2b5722204..c74508d9c 100755 --- a/tools/generate-operator-out.py +++ b/tools/generate-operator-out.py @@ -154,10 +154,12 @@ def ProcessFile(filename): sys.stderr.write('%s\n' % (rest)) Confused(filename, line_number, raw_line) - if len(enclosing_classes) > 0: - if is_enum_class: - enum_value = enum_name + '::' + enum_value - else: + # If the enum is scoped, we must prefix enum value with enum name (which is already prefixed + # by enclosing classes). + if is_enum_class: + enum_value = enum_name + '::' + enum_value + else: + if len(enclosing_classes) > 0: enum_value = '::'.join(enclosing_classes) + '::' + enum_value _ENUMS[enum_name].append((enum_value, enum_text)) -- 2.11.0