Chromium Code Reviews
chromiumcodereview-hr@appspot.gserviceaccount.com (chromiumcodereview-hr) | Please choose your nickname with Settings | Help | Chromium Project | Gerrit Changes | Sign out
(1102)

Side by Side Diff: runtime/vm/intermediate_language_x64.cc

Issue 2466643002: AOT: Enable branch merging for checked smi comparisons (Closed)
Patch Set: addressed comments Created 4 years, 1 month ago
Use n/p to move between diff chunks; N/P to move between comments. Draft comments are only viewable by you.
Jump to:
View unified diff | Download patch
« no previous file with comments | « runtime/vm/intermediate_language_mips.cc ('k') | no next file » | no next file with comments »
Toggle Intra-line Diffs ('i') | Expand Comments ('e') | Collapse Comments ('c') | Show Comments Hide Comments ('s')
OLDNEW
1 // Copyright (c) 2013, the Dart project authors. Please see the AUTHORS file 1 // Copyright (c) 2013, the Dart project authors. Please see the AUTHORS file
2 // for details. All rights reserved. Use of this source code is governed by a 2 // for details. All rights reserved. Use of this source code is governed by a
3 // BSD-style license that can be found in the LICENSE file. 3 // BSD-style license that can be found in the LICENSE file.
4 4
5 #include "vm/globals.h" // Needed here to get TARGET_ARCH_X64. 5 #include "vm/globals.h" // Needed here to get TARGET_ARCH_X64.
6 #if defined(TARGET_ARCH_X64) 6 #if defined(TARGET_ARCH_X64)
7 7
8 #include "vm/intermediate_language.h" 8 #include "vm/intermediate_language.h"
9 9
10 #include "vm/compiler.h" 10 #include "vm/compiler.h"
(...skipping 2868 matching lines...) Expand 10 before | Expand all | Expand 10 after
2879 2879
2880 LocationSummary* CheckedSmiOpInstr::MakeLocationSummary(Zone* zone, 2880 LocationSummary* CheckedSmiOpInstr::MakeLocationSummary(Zone* zone,
2881 bool opt) const { 2881 bool opt) const {
2882 const intptr_t kNumInputs = 2; 2882 const intptr_t kNumInputs = 2;
2883 const intptr_t kNumTemps = 0; 2883 const intptr_t kNumTemps = 0;
2884 LocationSummary* summary = new(zone) LocationSummary( 2884 LocationSummary* summary = new(zone) LocationSummary(
2885 zone, kNumInputs, kNumTemps, LocationSummary::kCallOnSlowPath); 2885 zone, kNumInputs, kNumTemps, LocationSummary::kCallOnSlowPath);
2886 summary->set_in(0, Location::RequiresRegister()); 2886 summary->set_in(0, Location::RequiresRegister());
2887 summary->set_in(1, Location::RequiresRegister()); 2887 summary->set_in(1, Location::RequiresRegister());
2888 switch (op_kind()) { 2888 switch (op_kind()) {
2889 case Token::kEQ:
2890 case Token::kLT:
2891 case Token::kLTE:
2892 case Token::kGT:
2893 case Token::kGTE:
2894 case Token::kADD: 2889 case Token::kADD:
2895 case Token::kSUB: 2890 case Token::kSUB:
2896 case Token::kMUL: 2891 case Token::kMUL:
2897 summary->set_out(0, Location::RequiresRegister()); 2892 summary->set_out(0, Location::RequiresRegister());
2898 break; 2893 break;
2899 case Token::kBIT_OR: 2894 case Token::kBIT_OR:
2900 case Token::kBIT_AND: 2895 case Token::kBIT_AND:
2901 case Token::kBIT_XOR: 2896 case Token::kBIT_XOR:
2902 summary->set_out(0, Location::SameAsFirstInput()); 2897 summary->set_out(0, Location::SameAsFirstInput());
2903 break; 2898 break;
(...skipping 49 matching lines...) Expand 10 before | Expand all | Expand 10 after
2953 __ orq(result, right); 2948 __ orq(result, right);
2954 break; 2949 break;
2955 case Token::kBIT_AND: 2950 case Token::kBIT_AND:
2956 ASSERT(left == result); 2951 ASSERT(left == result);
2957 __ andq(result, right); 2952 __ andq(result, right);
2958 break; 2953 break;
2959 case Token::kBIT_XOR: 2954 case Token::kBIT_XOR:
2960 ASSERT(left == result); 2955 ASSERT(left == result);
2961 __ xorq(result, right); 2956 __ xorq(result, right);
2962 break; 2957 break;
2963 case Token::kEQ:
2964 case Token::kLT:
2965 case Token::kLTE:
2966 case Token::kGT:
2967 case Token::kGTE: {
2968 Label true_label, false_label, done;
2969 BranchLabels labels = { &true_label, &false_label, &false_label };
2970 Condition true_condition =
2971 EmitInt64ComparisonOp(compiler, *locs(), op_kind());
2972 EmitBranchOnCondition(compiler, true_condition, labels);
2973 __ Bind(&false_label);
2974 __ LoadObject(result, Bool::False());
2975 __ jmp(&done);
2976 __ Bind(&true_label);
2977 __ LoadObject(result, Bool::True());
2978 __ Bind(&done);
2979 break;
2980 }
2981 default: 2958 default:
2982 UNIMPLEMENTED(); 2959 UNIMPLEMENTED();
2983 } 2960 }
2984 __ Bind(slow_path->exit_label()); 2961 __ Bind(slow_path->exit_label());
2985 } 2962 }
2986 2963
2987 2964
2965 class CheckedSmiComparisonSlowPath : public SlowPathCode {
2966 public:
2967 CheckedSmiComparisonSlowPath(CheckedSmiComparisonInstr* instruction,
2968 intptr_t try_index,
2969 BranchLabels labels,
2970 bool merged = false)
2971 : instruction_(instruction),
2972 try_index_(try_index),
2973 labels_(labels),
2974 merged_(merged) { }
2975
2976 virtual void EmitNativeCode(FlowGraphCompiler* compiler) {
2977 if (Assembler::EmittingComments()) {
2978 __ Comment("slow path smi comparison");
2979 }
2980 __ Bind(entry_label());
2981 LocationSummary* locs = instruction_->locs();
2982 Register result = merged_ ? locs->temp(0).reg() : locs->out(0).reg();
2983 locs->live_registers()->Remove(Location::RegisterLocation(result));
2984
2985 compiler->SaveLiveRegisters(locs);
2986 __ pushq(locs->in(0).reg());
2987 __ pushq(locs->in(1).reg());
2988 compiler->EmitMegamorphicInstanceCall(
2989 *instruction_->call()->ic_data(),
2990 instruction_->call()->ArgumentCount(),
2991 instruction_->call()->deopt_id(),
2992 instruction_->call()->token_pos(),
2993 locs,
2994 try_index_,
2995 /* slow_path_argument_count = */ 2);
2996 __ MoveRegister(result, RAX);
2997 compiler->RestoreLiveRegisters(locs);
2998 if (merged_) {
2999 __ CompareObject(result, Bool::True());
3000 __ j(EQUAL, instruction_->is_negated()
3001 ? labels_.false_label : labels_.true_label);
3002 __ jmp(instruction_->is_negated()
3003 ? labels_.true_label : labels_.false_label);
3004 } else {
3005 __ jmp(exit_label());
3006 }
3007 }
3008
3009 private:
3010 CheckedSmiComparisonInstr* instruction_;
3011 intptr_t try_index_;
3012 BranchLabels labels_;
3013 bool merged_;
3014 };
3015
3016
3017 LocationSummary* CheckedSmiComparisonInstr::MakeLocationSummary(
3018 Zone* zone, bool opt) const {
3019 const intptr_t kNumInputs = 2;
3020 const intptr_t kNumTemps = 1;
3021 LocationSummary* summary = new(zone) LocationSummary(
3022 zone, kNumInputs, kNumTemps, LocationSummary::kCallOnSlowPath);
3023 summary->set_in(0, Location::RequiresRegister());
3024 summary->set_in(1, Location::RequiresRegister());
3025 summary->set_temp(0, Location::RequiresRegister());
3026 summary->set_out(0, Location::RequiresRegister());
3027 return summary;
3028 }
3029
3030
3031 Condition CheckedSmiComparisonInstr::EmitComparisonCode(
3032 FlowGraphCompiler* compiler, BranchLabels labels) {
3033 return EmitInt64ComparisonOp(compiler, *locs(), kind());
3034 }
3035
3036
3037 #define EMIT_SMI_CHECK \
3038 intptr_t left_cid = left()->Type()->ToCid(); \
3039 intptr_t right_cid = right()->Type()->ToCid(); \
3040 Register left = locs()->in(0).reg(); \
3041 Register right = locs()->in(1).reg(); \
3042 if (this->left()->definition() == this->right()->definition()) { \
3043 __ testq(left, Immediate(kSmiTagMask)); \
3044 } else if (left_cid == kSmiCid) { \
3045 __ testq(right, Immediate(kSmiTagMask)); \
3046 } else if (right_cid == kSmiCid) { \
3047 __ testq(left, Immediate(kSmiTagMask)); \
3048 } else { \
3049 __ movq(TMP, left); \
3050 __ orq(TMP, right); \
3051 __ testq(TMP, Immediate(kSmiTagMask)); \
3052 } \
3053 __ j(NOT_ZERO, slow_path->entry_label())
3054
3055
3056 void CheckedSmiComparisonInstr::EmitBranchCode(FlowGraphCompiler* compiler,
3057 BranchInstr* branch) {
3058 BranchLabels labels = compiler->CreateBranchLabels(branch);
3059 CheckedSmiComparisonSlowPath* slow_path =
3060 new CheckedSmiComparisonSlowPath(this,
3061 compiler->CurrentTryIndex(),
3062 labels,
3063 /* merged = */ true);
3064 compiler->AddSlowPathCode(slow_path);
3065 EMIT_SMI_CHECK;
3066 Condition true_condition = EmitComparisonCode(compiler, labels);
3067 EmitBranchOnCondition(compiler, true_condition, labels);
3068 __ Bind(slow_path->exit_label());
3069 }
3070
3071
3072 void CheckedSmiComparisonInstr::EmitNativeCode(FlowGraphCompiler* compiler) {
3073 Label true_label, false_label, done;
3074 BranchLabels labels = { &true_label, &false_label, &false_label };
3075 CheckedSmiComparisonSlowPath* slow_path =
3076 new CheckedSmiComparisonSlowPath(this,
3077 compiler->CurrentTryIndex(),
3078 labels,
3079 /* merged = */ false);
3080 compiler->AddSlowPathCode(slow_path);
3081 EMIT_SMI_CHECK;
3082 Condition true_condition = EmitComparisonCode(compiler, labels);
3083 EmitBranchOnCondition(compiler, true_condition, labels);
3084 Register result = locs()->out(0).reg();
3085 __ Bind(&false_label);
3086 __ LoadObject(result, Bool::False());
3087 __ jmp(&done);
3088 __ Bind(&true_label);
3089 __ LoadObject(result, Bool::True());
3090 __ Bind(&done);
3091 __ Bind(slow_path->exit_label());
3092 }
3093
3094
2988 static bool CanBeImmediate(const Object& constant) { 3095 static bool CanBeImmediate(const Object& constant) {
2989 return constant.IsSmi() && 3096 return constant.IsSmi() &&
2990 Immediate(reinterpret_cast<int64_t>(constant.raw())).is_int32(); 3097 Immediate(reinterpret_cast<int64_t>(constant.raw())).is_int32();
2991 } 3098 }
2992 3099
2993 static bool IsSmiValue(const Object& constant, intptr_t value) { 3100 static bool IsSmiValue(const Object& constant, intptr_t value) {
2994 return constant.IsSmi() && (Smi::Cast(constant).Value() == value); 3101 return constant.IsSmi() && (Smi::Cast(constant).Value() == value);
2995 } 3102 }
2996 3103
2997 3104
(...skipping 3708 matching lines...) Expand 10 before | Expand all | Expand 10 after
6706 __ Drop(1); 6813 __ Drop(1);
6707 __ popq(result); 6814 __ popq(result);
6708 } 6815 }
6709 6816
6710 6817
6711 } // namespace dart 6818 } // namespace dart
6712 6819
6713 #undef __ 6820 #undef __
6714 6821
6715 #endif // defined TARGET_ARCH_X64 6822 #endif // defined TARGET_ARCH_X64
OLDNEW
« no previous file with comments | « runtime/vm/intermediate_language_mips.cc ('k') | no next file » | no next file with comments »

Powered by Google App Engine
This is Rietveld 408576698