summaryrefslogtreecommitdiff
path: root/Source/JavaScriptCore/dfg/DFGVariableAccessData.h
diff options
context:
space:
mode:
Diffstat (limited to 'Source/JavaScriptCore/dfg/DFGVariableAccessData.h')
-rw-r--r--Source/JavaScriptCore/dfg/DFGVariableAccessData.h105
1 files changed, 92 insertions, 13 deletions
diff --git a/Source/JavaScriptCore/dfg/DFGVariableAccessData.h b/Source/JavaScriptCore/dfg/DFGVariableAccessData.h
index bd626f9fb..1d99ed516 100644
--- a/Source/JavaScriptCore/dfg/DFGVariableAccessData.h
+++ b/Source/JavaScriptCore/dfg/DFGVariableAccessData.h
@@ -1,5 +1,5 @@
/*
- * Copyright (C) 2011 Apple Inc. All rights reserved.
+ * Copyright (C) 2011, 2012 Apple Inc. All rights reserved.
*
* Redistribution and use in source and binary forms, with or without
* modification, are permitted provided that the following conditions
@@ -26,11 +26,14 @@
#ifndef DFGVariableAccessData_h
#define DFGVariableAccessData_h
-#include "DFGOperands.h"
+#include "DFGDoubleFormatState.h"
+#include "DFGNodeFlags.h"
+#include "Operands.h"
#include "PredictedType.h"
#include "VirtualRegister.h"
#include <wtf/Platform.h>
#include <wtf/UnionFind.h>
+#include <wtf/Vector.h>
namespace JSC { namespace DFG {
@@ -41,7 +44,9 @@ public:
VariableAccessData()
: m_local(static_cast<VirtualRegister>(std::numeric_limits<int>::min()))
, m_prediction(PredictNone)
- , m_shouldUseDoubleFormat(false)
+ , m_argumentAwarePrediction(PredictNone)
+ , m_flags(0)
+ , m_doubleFormatState(EmptyDoubleFormatState)
{
clearVotes();
}
@@ -49,7 +54,9 @@ public:
VariableAccessData(VirtualRegister local)
: m_local(local)
, m_prediction(PredictNone)
- , m_shouldUseDoubleFormat(false)
+ , m_argumentAwarePrediction(PredictNone)
+ , m_flags(0)
+ , m_doubleFormatState(EmptyDoubleFormatState)
{
clearVotes();
}
@@ -67,7 +74,11 @@ public:
bool predict(PredictedType prediction)
{
- return mergePrediction(find()->m_prediction, prediction);
+ VariableAccessData* self = find();
+ bool result = mergePrediction(self->m_prediction, prediction);
+ if (result)
+ mergePrediction(m_argumentAwarePrediction, m_prediction);
+ return result;
}
PredictedType nonUnifiedPrediction()
@@ -80,6 +91,16 @@ public:
return find()->m_prediction;
}
+ PredictedType argumentAwarePrediction()
+ {
+ return find()->m_argumentAwarePrediction;
+ }
+
+ bool mergeArgumentAwarePrediction(PredictedType prediction)
+ {
+ return mergePrediction(find()->m_argumentAwarePrediction, prediction);
+ }
+
void clearVotes()
{
ASSERT(find() == this);
@@ -101,19 +122,51 @@ public:
bool shouldUseDoubleFormatAccordingToVote()
{
+ // We don't support this facility for arguments, yet.
// FIXME: make this work for arguments.
- return !operandIsArgument(operand()) && ((isNumberPrediction(prediction()) && doubleVoteRatio() >= Options::doubleVoteRatioForDoubleFormat) || isDoublePrediction(prediction()));
+ if (operandIsArgument(operand()))
+ return false;
+
+ // If the variable is not a number prediction, then this doesn't
+ // make any sense.
+ if (!isNumberPrediction(prediction()))
+ return false;
+
+ // If the variable is predicted to hold only doubles, then it's a
+ // no-brainer: it should be formatted as a double.
+ if (isDoublePrediction(prediction()))
+ return true;
+
+ // If the variable is known to be used as an integer, then be safe -
+ // don't force it to be a double.
+ if (flags() & NodeUsedAsInt)
+ return false;
+
+ // If the variable has been voted to become a double, then make it a
+ // double.
+ if (doubleVoteRatio() >= Options::doubleVoteRatioForDoubleFormat)
+ return true;
+
+ return false;
+ }
+
+ DoubleFormatState doubleFormatState()
+ {
+ return find()->m_doubleFormatState;
}
bool shouldUseDoubleFormat()
{
- ASSERT(find() == this);
- return m_shouldUseDoubleFormat;
+ ASSERT(isRoot());
+ return m_doubleFormatState == UsingDoubleFormat;
}
bool tallyVotesForShouldUseDoubleFormat()
{
- ASSERT(find() == this);
+ ASSERT(isRoot());
+
+ if (m_doubleFormatState == CantUseDoubleFormat)
+ return false;
bool newValueOfShouldUseDoubleFormat = shouldUseDoubleFormatAccordingToVote();
if (!newValueOfShouldUseDoubleFormat) {
@@ -122,11 +175,35 @@ public:
return false;
}
- if (m_shouldUseDoubleFormat)
+ if (m_doubleFormatState == UsingDoubleFormat)
return false;
- m_shouldUseDoubleFormat = true;
- mergePrediction(m_prediction, PredictDouble);
+ return DFG::mergeDoubleFormatState(m_doubleFormatState, UsingDoubleFormat);
+ }
+
+ bool mergeDoubleFormatState(DoubleFormatState doubleFormatState)
+ {
+ return DFG::mergeDoubleFormatState(find()->m_doubleFormatState, doubleFormatState);
+ }
+
+ bool makePredictionForDoubleFormat()
+ {
+ ASSERT(isRoot());
+
+ if (m_doubleFormatState != UsingDoubleFormat)
+ return false;
+
+ return mergePrediction(m_prediction, PredictDouble);
+ }
+
+ NodeFlags flags() const { return m_flags; }
+
+ bool mergeFlags(NodeFlags newFlags)
+ {
+ newFlags |= m_flags;
+ if (newFlags == m_flags)
+ return false;
+ m_flags = newFlags;
return true;
}
@@ -138,9 +215,11 @@ private:
VirtualRegister m_local;
PredictedType m_prediction;
+ PredictedType m_argumentAwarePrediction;
+ NodeFlags m_flags;
float m_votes[2];
- bool m_shouldUseDoubleFormat;
+ DoubleFormatState m_doubleFormatState;
};
} } // namespace JSC::DFG