Merge pull request #3027 from lioncash/lookup

shader_ir: Use std::array with std::pair instead of std::unordered_map
merge-requests/60/head
Rodrigo Locatti 2019-10-26 05:49:15 +07:00 committed by GitHub
commit a0d79085c4
No known key found for this signature in database
GPG Key ID: 4AEE18F83AFDEB23
1 changed files with 64 additions and 50 deletions

@ -2,8 +2,9 @@
// Licensed under GPLv2 or any later version // Licensed under GPLv2 or any later version
// Refer to the license.txt file included. // Refer to the license.txt file included.
#include <algorithm>
#include <array>
#include <cmath> #include <cmath>
#include <unordered_map>
#include "common/assert.h" #include "common/assert.h"
#include "common/common_types.h" #include "common/common_types.h"
@ -271,21 +272,24 @@ Node ShaderIR::GetSaturatedHalfFloat(Node value, bool saturate) {
} }
Node ShaderIR::GetPredicateComparisonFloat(PredCondition condition, Node op_a, Node op_b) { Node ShaderIR::GetPredicateComparisonFloat(PredCondition condition, Node op_a, Node op_b) {
const std::unordered_map<PredCondition, OperationCode> PredicateComparisonTable = { static constexpr std::array comparison_table{
{PredCondition::LessThan, OperationCode::LogicalFLessThan}, std::pair{PredCondition::LessThan, OperationCode::LogicalFLessThan},
{PredCondition::Equal, OperationCode::LogicalFEqual}, std::pair{PredCondition::Equal, OperationCode::LogicalFEqual},
{PredCondition::LessEqual, OperationCode::LogicalFLessEqual}, std::pair{PredCondition::LessEqual, OperationCode::LogicalFLessEqual},
{PredCondition::GreaterThan, OperationCode::LogicalFGreaterThan}, std::pair{PredCondition::GreaterThan, OperationCode::LogicalFGreaterThan},
{PredCondition::NotEqual, OperationCode::LogicalFNotEqual}, std::pair{PredCondition::NotEqual, OperationCode::LogicalFNotEqual},
{PredCondition::GreaterEqual, OperationCode::LogicalFGreaterEqual}, std::pair{PredCondition::GreaterEqual, OperationCode::LogicalFGreaterEqual},
{PredCondition::LessThanWithNan, OperationCode::LogicalFLessThan}, std::pair{PredCondition::LessThanWithNan, OperationCode::LogicalFLessThan},
{PredCondition::NotEqualWithNan, OperationCode::LogicalFNotEqual}, std::pair{PredCondition::NotEqualWithNan, OperationCode::LogicalFNotEqual},
{PredCondition::LessEqualWithNan, OperationCode::LogicalFLessEqual}, std::pair{PredCondition::LessEqualWithNan, OperationCode::LogicalFLessEqual},
{PredCondition::GreaterThanWithNan, OperationCode::LogicalFGreaterThan}, std::pair{PredCondition::GreaterThanWithNan, OperationCode::LogicalFGreaterThan},
{PredCondition::GreaterEqualWithNan, OperationCode::LogicalFGreaterEqual}}; std::pair{PredCondition::GreaterEqualWithNan, OperationCode::LogicalFGreaterEqual},
};
const auto comparison{PredicateComparisonTable.find(condition)}; const auto comparison =
UNIMPLEMENTED_IF_MSG(comparison == PredicateComparisonTable.end(), std::find_if(comparison_table.cbegin(), comparison_table.cend(),
[condition](const auto entry) { return condition == entry.first; });
UNIMPLEMENTED_IF_MSG(comparison == comparison_table.cend(),
"Unknown predicate comparison operation"); "Unknown predicate comparison operation");
Node predicate = Operation(comparison->second, NO_PRECISE, op_a, op_b); Node predicate = Operation(comparison->second, NO_PRECISE, op_a, op_b);
@ -306,21 +310,24 @@ Node ShaderIR::GetPredicateComparisonFloat(PredCondition condition, Node op_a, N
Node ShaderIR::GetPredicateComparisonInteger(PredCondition condition, bool is_signed, Node op_a, Node ShaderIR::GetPredicateComparisonInteger(PredCondition condition, bool is_signed, Node op_a,
Node op_b) { Node op_b) {
const std::unordered_map<PredCondition, OperationCode> PredicateComparisonTable = { static constexpr std::array comparison_table{
{PredCondition::LessThan, OperationCode::LogicalILessThan}, std::pair{PredCondition::LessThan, OperationCode::LogicalILessThan},
{PredCondition::Equal, OperationCode::LogicalIEqual}, std::pair{PredCondition::Equal, OperationCode::LogicalIEqual},
{PredCondition::LessEqual, OperationCode::LogicalILessEqual}, std::pair{PredCondition::LessEqual, OperationCode::LogicalILessEqual},
{PredCondition::GreaterThan, OperationCode::LogicalIGreaterThan}, std::pair{PredCondition::GreaterThan, OperationCode::LogicalIGreaterThan},
{PredCondition::NotEqual, OperationCode::LogicalINotEqual}, std::pair{PredCondition::NotEqual, OperationCode::LogicalINotEqual},
{PredCondition::GreaterEqual, OperationCode::LogicalIGreaterEqual}, std::pair{PredCondition::GreaterEqual, OperationCode::LogicalIGreaterEqual},
{PredCondition::LessThanWithNan, OperationCode::LogicalILessThan}, std::pair{PredCondition::LessThanWithNan, OperationCode::LogicalILessThan},
{PredCondition::NotEqualWithNan, OperationCode::LogicalINotEqual}, std::pair{PredCondition::NotEqualWithNan, OperationCode::LogicalINotEqual},
{PredCondition::LessEqualWithNan, OperationCode::LogicalILessEqual}, std::pair{PredCondition::LessEqualWithNan, OperationCode::LogicalILessEqual},
{PredCondition::GreaterThanWithNan, OperationCode::LogicalIGreaterThan}, std::pair{PredCondition::GreaterThanWithNan, OperationCode::LogicalIGreaterThan},
{PredCondition::GreaterEqualWithNan, OperationCode::LogicalIGreaterEqual}}; std::pair{PredCondition::GreaterEqualWithNan, OperationCode::LogicalIGreaterEqual},
};
const auto comparison{PredicateComparisonTable.find(condition)}; const auto comparison =
UNIMPLEMENTED_IF_MSG(comparison == PredicateComparisonTable.end(), std::find_if(comparison_table.cbegin(), comparison_table.cend(),
[condition](const auto entry) { return condition == entry.first; });
UNIMPLEMENTED_IF_MSG(comparison == comparison_table.cend(),
"Unknown predicate comparison operation"); "Unknown predicate comparison operation");
Node predicate = SignedOperation(comparison->second, is_signed, NO_PRECISE, std::move(op_a), Node predicate = SignedOperation(comparison->second, is_signed, NO_PRECISE, std::move(op_a),
@ -337,36 +344,43 @@ Node ShaderIR::GetPredicateComparisonInteger(PredCondition condition, bool is_si
Node ShaderIR::GetPredicateComparisonHalf(Tegra::Shader::PredCondition condition, Node op_a, Node ShaderIR::GetPredicateComparisonHalf(Tegra::Shader::PredCondition condition, Node op_a,
Node op_b) { Node op_b) {
const std::unordered_map<PredCondition, OperationCode> PredicateComparisonTable = { static constexpr std::array comparison_table{
{PredCondition::LessThan, OperationCode::Logical2HLessThan}, std::pair{PredCondition::LessThan, OperationCode::Logical2HLessThan},
{PredCondition::Equal, OperationCode::Logical2HEqual}, std::pair{PredCondition::Equal, OperationCode::Logical2HEqual},
{PredCondition::LessEqual, OperationCode::Logical2HLessEqual}, std::pair{PredCondition::LessEqual, OperationCode::Logical2HLessEqual},
{PredCondition::GreaterThan, OperationCode::Logical2HGreaterThan}, std::pair{PredCondition::GreaterThan, OperationCode::Logical2HGreaterThan},
{PredCondition::NotEqual, OperationCode::Logical2HNotEqual}, std::pair{PredCondition::NotEqual, OperationCode::Logical2HNotEqual},
{PredCondition::GreaterEqual, OperationCode::Logical2HGreaterEqual}, std::pair{PredCondition::GreaterEqual, OperationCode::Logical2HGreaterEqual},
{PredCondition::LessThanWithNan, OperationCode::Logical2HLessThanWithNan}, std::pair{PredCondition::LessThanWithNan, OperationCode::Logical2HLessThanWithNan},
{PredCondition::NotEqualWithNan, OperationCode::Logical2HNotEqualWithNan}, std::pair{PredCondition::NotEqualWithNan, OperationCode::Logical2HNotEqualWithNan},
{PredCondition::LessEqualWithNan, OperationCode::Logical2HLessEqualWithNan}, std::pair{PredCondition::LessEqualWithNan, OperationCode::Logical2HLessEqualWithNan},
{PredCondition::GreaterThanWithNan, OperationCode::Logical2HGreaterThanWithNan}, std::pair{PredCondition::GreaterThanWithNan, OperationCode::Logical2HGreaterThanWithNan},
{PredCondition::GreaterEqualWithNan, OperationCode::Logical2HGreaterEqualWithNan}}; std::pair{PredCondition::GreaterEqualWithNan, OperationCode::Logical2HGreaterEqualWithNan},
};
const auto comparison{PredicateComparisonTable.find(condition)}; const auto comparison =
UNIMPLEMENTED_IF_MSG(comparison == PredicateComparisonTable.end(), std::find_if(comparison_table.cbegin(), comparison_table.cend(),
[condition](const auto entry) { return condition == entry.first; });
UNIMPLEMENTED_IF_MSG(comparison == comparison_table.cend(),
"Unknown predicate comparison operation"); "Unknown predicate comparison operation");
return Operation(comparison->second, NO_PRECISE, std::move(op_a), std::move(op_b)); return Operation(comparison->second, NO_PRECISE, std::move(op_a), std::move(op_b));
} }
OperationCode ShaderIR::GetPredicateCombiner(PredOperation operation) { OperationCode ShaderIR::GetPredicateCombiner(PredOperation operation) {
const std::unordered_map<PredOperation, OperationCode> PredicateOperationTable = { static constexpr std::array operation_table{
{PredOperation::And, OperationCode::LogicalAnd}, OperationCode::LogicalAnd,
{PredOperation::Or, OperationCode::LogicalOr}, OperationCode::LogicalOr,
{PredOperation::Xor, OperationCode::LogicalXor}, OperationCode::LogicalXor,
}; };
const auto op = PredicateOperationTable.find(operation); const auto index = static_cast<std::size_t>(operation);
UNIMPLEMENTED_IF_MSG(op == PredicateOperationTable.end(), "Unknown predicate operation"); if (index >= operation_table.size()) {
return op->second; UNIMPLEMENTED_MSG("Unknown predicate operation.");
return {};
}
return operation_table[index];
} }
Node ShaderIR::GetConditionCode(Tegra::Shader::ConditionCode cc) const { Node ShaderIR::GetConditionCode(Tegra::Shader::ConditionCode cc) const {