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

Unified Diff: runtime/vm/object.cc

Issue 735543003: Range feedback for binary integer operations. (Closed) Base URL: https://dart.googlecode.com/svn/branches/bleeding_edge/dart
Patch Set: Address comments Created 6 years 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 side-by-side diff with in-line comments
Download patch
« no previous file with comments | « runtime/vm/object.h ('k') | runtime/vm/raw_object.h » ('j') | no next file with comments »
Expand Comments ('e') | Collapse Comments ('c') | Show Comments Hide Comments ('s')
Index: runtime/vm/object.cc
diff --git a/runtime/vm/object.cc b/runtime/vm/object.cc
index bbcb076cd129b99209ae0698eb5c3cde27ec67ba..515dc86ad4195e4e50ad0f82f516cf7b1cc44d62 100644
--- a/runtime/vm/object.cc
+++ b/runtime/vm/object.cc
@@ -11472,6 +11472,11 @@ bool ICData::MayCheckForJSWarning() const {
}
+void ICData::set_range_feedback(uint32_t feedback) {
+ StoreNonPointer(&raw_ptr()->range_feedback_, feedback);
+}
+
+
void ICData::set_state_bits(uint32_t bits) const {
StoreNonPointer(&raw_ptr()->state_bits_, bits);
}
@@ -11927,6 +11932,7 @@ RawICData* ICData::New(const Function& owner,
result.set_arguments_descriptor(arguments_descriptor);
result.set_deopt_id(deopt_id);
result.set_state_bits(0);
+ result.set_range_feedback(0);
result.SetNumArgsTested(num_args_tested);
// Number of array elements in one test entry.
intptr_t len = result.TestEntryLength();
@@ -11943,6 +11949,94 @@ void ICData::PrintJSONImpl(JSONStream* stream, bool ref) const {
}
+static Token::Kind RecognizeArithmeticOp(const String& name) {
+ ASSERT(name.IsSymbol());
+ if (name.raw() == Symbols::Plus().raw()) {
+ return Token::kADD;
+ } else if (name.raw() == Symbols::Minus().raw()) {
+ return Token::kSUB;
+ } else if (name.raw() == Symbols::Star().raw()) {
+ return Token::kMUL;
+ } else if (name.raw() == Symbols::Slash().raw()) {
+ return Token::kDIV;
+ } else if (name.raw() == Symbols::TruncDivOperator().raw()) {
+ return Token::kTRUNCDIV;
+ } else if (name.raw() == Symbols::Percent().raw()) {
+ return Token::kMOD;
+ } else if (name.raw() == Symbols::BitOr().raw()) {
+ return Token::kBIT_OR;
+ } else if (name.raw() == Symbols::Ampersand().raw()) {
+ return Token::kBIT_AND;
+ } else if (name.raw() == Symbols::Caret().raw()) {
+ return Token::kBIT_XOR;
+ } else if (name.raw() == Symbols::LeftShiftOperator().raw()) {
+ return Token::kSHL;
+ } else if (name.raw() == Symbols::RightShiftOperator().raw()) {
+ return Token::kSHR;
+ } else if (name.raw() == Symbols::Tilde().raw()) {
+ return Token::kBIT_NOT;
+ } else if (name.raw() == Symbols::UnaryMinus().raw()) {
+ return Token::kNEGATE;
+ }
+ return Token::kILLEGAL;
+}
+
+
+bool ICData::HasRangeFeedback() const {
+ const String& target = String::Handle(target_name());
+ const Token::Kind token_kind = RecognizeArithmeticOp(target);
+ if (!Token::IsBinaryArithmeticOperator(token_kind) &&
+ !Token::IsUnaryArithmeticOperator(token_kind)) {
+ return false;
+ }
+
+ bool initialized = false;
+ Function& t = Function::Handle();
+ const intptr_t len = NumberOfChecks();
+ GrowableArray<intptr_t> class_ids;
+ for (intptr_t i = 0; i < len; i++) {
+ if (IsUsedAt(i)) {
+ initialized = true;
+ GetCheckAt(i, &class_ids, &t);
+ for (intptr_t j = 0; j < class_ids.length(); j++) {
+ const intptr_t cid = class_ids[j];
+ if ((cid != kSmiCid) && (cid != kMintCid)) {
+ return false;
+ }
+ }
+ }
+ }
+
+ return initialized;
+}
+
+
+ICData::RangeFeedback ICData::DecodeRangeFeedbackAt(intptr_t idx) const {
+ ASSERT((0 <= idx) && (idx < 3));
+ const uint32_t feedback =
+ (range_feedback() >> (idx * kBitsPerRangeFeedback)) & kRangeFeedbackMask;
+ if ((feedback & kInt64RangeBit) != 0) {
+ return kInt64Range;
+ }
+
+ if ((feedback & kUint32RangeBit) != 0) {
+ if ((feedback & kSignedRangeBit) == 0) {
+ return kUint32Range;
+ }
+
+ // Check if Smi is large enough to accomodate Int33: a mixture of Uint32
+ // and negative Int32 values.
+ return (kSmiBits < 33) ? kInt64Range : kSmiRange;
+ }
+
+ if ((feedback & kInt32RangeBit) != 0) {
+ return kInt32Range;
+ }
+
+ return kSmiRange;
+}
+
+
Code::Comments& Code::Comments::New(intptr_t count) {
Comments* comments;
if (count < 0 || count > (kIntptrMax / kNumberOfEntries)) {
« no previous file with comments | « runtime/vm/object.h ('k') | runtime/vm/raw_object.h » ('j') | no next file with comments »

Powered by Google App Engine
This is Rietveld 408576698