diff options
Diffstat (limited to 'src/ir')
-rw-r--r-- | src/ir/ExpressionAnalyzer.cpp | 29 | ||||
-rw-r--r-- | src/ir/ExpressionManipulator.cpp | 1 | ||||
-rw-r--r-- | src/ir/hashed.h | 25 | ||||
-rw-r--r-- | src/ir/utils.h | 2 |
4 files changed, 26 insertions, 31 deletions
diff --git a/src/ir/ExpressionAnalyzer.cpp b/src/ir/ExpressionAnalyzer.cpp index a6f4b601f..cdbcd9ae0 100644 --- a/src/ir/ExpressionAnalyzer.cpp +++ b/src/ir/ExpressionAnalyzer.cpp @@ -408,9 +408,9 @@ bool ExpressionAnalyzer::flexibleEqual(Expression* left, } // hash an expression, ignoring superficial details like specific internal names -HashType ExpressionAnalyzer::hash(Expression* curr) { +size_t ExpressionAnalyzer::hash(Expression* curr) { struct Hasher { - HashType digest = 0; + size_t digest = wasm::hash(0); Index internalCounter = 0; // for each internal name, its unique id @@ -432,7 +432,7 @@ HashType ExpressionAnalyzer::hash(Expression* curr) { if (!curr) { continue; } - hash(curr->_id); + rehash(digest, curr->_id); // we often don't need to hash the type, as it is tied to other values // we are hashing anyhow, but there are exceptions: for example, a // local.get's type is determined by the function, so if we are @@ -441,7 +441,7 @@ HashType ExpressionAnalyzer::hash(Expression* curr) { // if we hash between modules, then we need to take int account // call_imports type, etc. The simplest thing is just to hash the // type for all of them. - hash(curr->type.getID()); + rehash(digest, curr->type.getID()); // Blocks and loops introduce scoping. if (auto* block = curr->dynCast<Block>()) { noteScopeName(block->name); @@ -459,15 +459,10 @@ HashType ExpressionAnalyzer::hash(Expression* curr) { } // Sometimes children are optional, e.g. return, so we must hash // their number as well. - hash(counter); + rehash(digest, counter); } } - void hash(HashType hash) { digest = rehash(digest, hash); } - void hash64(uint64_t hash) { - digest = rehash(rehash(digest, HashType(hash >> 32)), HashType(hash)); - } - void visitScopeName(Name curr) { // Names are relative, we give the same hash for // (block $x (br $x)) @@ -475,21 +470,21 @@ HashType ExpressionAnalyzer::hash(Expression* curr) { static_assert(sizeof(Index) == sizeof(int32_t), "wasm64 will need changes here"); assert(internalNames.find(curr) != internalNames.end()); - return hash(internalNames[curr]); + rehash(digest, internalNames[curr]); } - void visitNonScopeName(Name curr) { return hash64(uint64_t(curr.str)); } - void visitInt(int32_t curr) { hash(curr); } - void visitLiteral(Literal curr) { hash(std::hash<Literal>()(curr)); } - void visitType(Type curr) { hash(int32_t(curr.getSingle())); } + void visitNonScopeName(Name curr) { rehash(digest, uint64_t(curr.str)); } + void visitInt(int32_t curr) { rehash(digest, curr); } + void visitLiteral(Literal curr) { rehash(digest, curr); } + void visitType(Type curr) { rehash(digest, curr.getID()); } void visitIndex(Index curr) { static_assert(sizeof(Index) == sizeof(int32_t), "wasm64 will need changes here"); - hash(int32_t(curr)); + rehash(digest, curr); } void visitAddress(Address curr) { static_assert(sizeof(Address) == sizeof(int32_t), "wasm64 will need changes here"); - hash(int32_t(curr)); + rehash(digest, curr.addr); } }; diff --git a/src/ir/ExpressionManipulator.cpp b/src/ir/ExpressionManipulator.cpp index a9fd3c599..57048b9bd 100644 --- a/src/ir/ExpressionManipulator.cpp +++ b/src/ir/ExpressionManipulator.cpp @@ -16,7 +16,6 @@ #include "ir/load-utils.h" #include "ir/utils.h" -#include "support/hash.h" namespace wasm { diff --git a/src/ir/hashed.h b/src/ir/hashed.h index 563e3abfe..fe959936a 100644 --- a/src/ir/hashed.h +++ b/src/ir/hashed.h @@ -26,16 +26,18 @@ namespace wasm { // An expression with a cached hash value struct HashedExpression { Expression* expr; - HashType hash; + size_t digest; HashedExpression(Expression* expr) : expr(expr) { if (expr) { - hash = ExpressionAnalyzer::hash(expr); + digest = ExpressionAnalyzer::hash(expr); + } else { + digest = hash(0); } } HashedExpression(const HashedExpression& other) - : expr(other.expr), hash(other.hash) {} + : expr(other.expr), digest(other.digest) {} }; // A pass that hashes all functions @@ -43,7 +45,7 @@ struct HashedExpression { struct FunctionHasher : public WalkerPass<PostWalker<FunctionHasher>> { bool isFunctionParallel() override { return true; } - struct Map : public std::map<Function*, HashType> {}; + struct Map : public std::map<Function*, size_t> {}; FunctionHasher(Map* output) : output(output) {} @@ -54,22 +56,21 @@ struct FunctionHasher : public WalkerPass<PostWalker<FunctionHasher>> { for (auto& func : module->functions) { // ensure an entry for each function - we must not modify the map shape in // parallel, just the values - hashes[func.get()] = 0; + hashes[func.get()] = hash(0); } return hashes; } void doWalkFunction(Function* func) { output->at(func) = hashFunction(func); } - static HashType hashFunction(Function* func) { - HashType ret = 0; - ret = rehash(ret, (HashType)func->sig.params.getID()); - ret = rehash(ret, (HashType)func->sig.results.getID()); + static size_t hashFunction(Function* func) { + auto digest = hash(func->sig.params.getID()); + rehash(digest, func->sig.results.getID()); for (auto type : func->vars) { - ret = rehash(ret, (HashType)type.getID()); + rehash(digest, type.getID()); } - ret = rehash(ret, (HashType)ExpressionAnalyzer::hash(func->body)); - return ret; + hash_combine(digest, ExpressionAnalyzer::hash(func->body)); + return digest; } private: diff --git a/src/ir/utils.h b/src/ir/utils.h index a7f6f59bf..176699591 100644 --- a/src/ir/utils.h +++ b/src/ir/utils.h @@ -78,7 +78,7 @@ struct ExpressionAnalyzer { // hash an expression, ignoring superficial details like specific internal // names - static HashType hash(Expression* curr); + static size_t hash(Expression* curr); }; // Re-Finalizes all node types. This can be run after code was modified in |