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

Unified Diff: runtime/vm/intermediate_language.cc

Issue 2897803002: VM: Constant fold more loads from constants in the optimizer. (Closed)
Patch Set: Created 3 years, 7 months 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/intermediate_language.h ('k') | runtime/vm/precompiler.cc » ('j') | no next file with comments »
Expand Comments ('e') | Collapse Comments ('c') | Show Comments Hide Comments ('s')
Index: runtime/vm/intermediate_language.cc
diff --git a/runtime/vm/intermediate_language.cc b/runtime/vm/intermediate_language.cc
index dd47a13e81509bf9dfd97d269e34b58a8cb4a5c4..6e0d2e7b2fa2ed25de0411ee017be15cd261cab6 100644
--- a/runtime/vm/intermediate_language.cc
+++ b/runtime/vm/intermediate_language.cc
@@ -2125,40 +2125,72 @@ Definition* MathUnaryInstr::Canonicalize(FlowGraph* flow_graph) {
}
+bool LoadFieldInstr::Evaluate(const Object& instance, Object* result) {
+ if (field() == NULL || !field()->is_final() || !instance.IsInstance()) {
+ return false;
+ }
+
+ // Check that instance really has the field which we
+ // are trying to load from.
+ Class& cls = Class::Handle(instance.clazz());
+ while (cls.raw() != Class::null() && cls.raw() != field()->Owner()) {
+ cls = cls.SuperClass();
+ }
+ if (cls.raw() != field()->Owner()) {
+ // Failed to find the field in class or its superclasses.
+ return false;
+ }
+
+ // Object has the field: execute the load.
+ *result = Instance::Cast(instance).GetField(*field());
+ return true;
+}
+
+
Definition* LoadFieldInstr::Canonicalize(FlowGraph* flow_graph) {
if (!HasUses()) return NULL;
- if (!IsImmutableLengthLoad()) return this;
-
- // For fixed length arrays if the array is the result of a known constructor
- // call we can replace the length load with the length argument passed to
- // the constructor.
- StaticCallInstr* call =
- instance()->definition()->OriginalDefinition()->AsStaticCall();
- if (call != NULL) {
- if (call->is_known_list_constructor() &&
- IsFixedLengthArrayCid(call->Type()->ToCid())) {
- return call->ArgumentAt(1);
+
+ if (IsImmutableLengthLoad()) {
+ // For fixed length arrays if the array is the result of a known constructor
+ // call we can replace the length load with the length argument passed to
+ // the constructor.
+ StaticCallInstr* call =
+ instance()->definition()->OriginalDefinition()->AsStaticCall();
+ if (call != NULL) {
+ if (call->is_known_list_constructor() &&
+ IsFixedLengthArrayCid(call->Type()->ToCid())) {
+ return call->ArgumentAt(1);
+ }
}
- }
- CreateArrayInstr* create_array =
- instance()->definition()->OriginalDefinition()->AsCreateArray();
- if ((create_array != NULL) &&
- (recognized_kind() == MethodRecognizer::kObjectArrayLength)) {
- return create_array->num_elements()->definition();
+ CreateArrayInstr* create_array =
+ instance()->definition()->OriginalDefinition()->AsCreateArray();
+ if ((create_array != NULL) &&
+ (recognized_kind() == MethodRecognizer::kObjectArrayLength)) {
+ return create_array->num_elements()->definition();
+ }
+
+ // For arrays with guarded lengths, replace the length load
+ // with a constant.
+ LoadFieldInstr* load_array =
+ instance()->definition()->OriginalDefinition()->AsLoadField();
+ if (load_array != NULL) {
+ const Field* field = load_array->field();
+ if ((field != NULL) && (field->guarded_list_length() >= 0)) {
+ return flow_graph->GetConstant(
+ Smi::Handle(Smi::New(field->guarded_list_length())));
+ }
+ }
}
- // For arrays with guarded lengths, replace the length load
- // with a constant.
- LoadFieldInstr* load_array =
- instance()->definition()->OriginalDefinition()->AsLoadField();
- if (load_array != NULL) {
- const Field* field = load_array->field();
- if ((field != NULL) && (field->guarded_list_length() >= 0)) {
- return flow_graph->GetConstant(
- Smi::Handle(Smi::New(field->guarded_list_length())));
+ // Try folding away loads from constant objects.
+ if (instance()->BindsToConstant()) {
+ Object& result = Object::Handle();
+ if (Evaluate(instance()->BoundConstant(), &result)) {
+ return flow_graph->GetConstant(result);
}
}
+
return this;
}
« no previous file with comments | « runtime/vm/intermediate_language.h ('k') | runtime/vm/precompiler.cc » ('j') | no next file with comments »

Powered by Google App Engine
This is Rietveld 408576698