mirror of
https://github.com/postgres/postgres.git
synced 2025-07-11 10:01:57 +03:00
Fix incorrect hash equality operator bug in Memoize
In v14, because we don't have a field in RestrictInfo to cache both the left and right type's hash equality operator, we just restrict the scope of Memoize to only when the left and right types of a RestrictInfo are the same. In master we add another field to RestrictInfo and cache both hash equality operators. Reported-by: Jaime Casanova Author: David Rowley Discussion: https://postgr.es/m/20210929185544.GB24346%40ahch-to Backpatch-through: 14
This commit is contained in:
@ -2711,15 +2711,16 @@ check_hashjoinable(RestrictInfo *restrictinfo)
|
||||
/*
|
||||
* check_memoizable
|
||||
* If the restrictinfo's clause is suitable to be used for a Memoize node,
|
||||
* set the hasheqoperator to the hash equality operator that will be needed
|
||||
* during caching.
|
||||
* set the lefthasheqoperator and righthasheqoperator to the hash equality
|
||||
* operator that will be needed during caching.
|
||||
*/
|
||||
static void
|
||||
check_memoizable(RestrictInfo *restrictinfo)
|
||||
{
|
||||
TypeCacheEntry *typentry;
|
||||
Expr *clause = restrictinfo->clause;
|
||||
Node *leftarg;
|
||||
Oid lefttype;
|
||||
Oid righttype;
|
||||
|
||||
if (restrictinfo->pseudoconstant)
|
||||
return;
|
||||
@ -2728,13 +2729,24 @@ check_memoizable(RestrictInfo *restrictinfo)
|
||||
if (list_length(((OpExpr *) clause)->args) != 2)
|
||||
return;
|
||||
|
||||
leftarg = linitial(((OpExpr *) clause)->args);
|
||||
lefttype = exprType(linitial(((OpExpr *) clause)->args));
|
||||
|
||||
typentry = lookup_type_cache(exprType(leftarg), TYPECACHE_HASH_PROC |
|
||||
typentry = lookup_type_cache(lefttype, TYPECACHE_HASH_PROC |
|
||||
TYPECACHE_EQ_OPR);
|
||||
|
||||
if (!OidIsValid(typentry->hash_proc) || !OidIsValid(typentry->eq_opr))
|
||||
return;
|
||||
if (OidIsValid(typentry->hash_proc) && OidIsValid(typentry->eq_opr))
|
||||
restrictinfo->left_hasheqoperator = typentry->eq_opr;
|
||||
|
||||
restrictinfo->hasheqoperator = typentry->eq_opr;
|
||||
righttype = exprType(lsecond(((OpExpr *) clause)->args));
|
||||
|
||||
/*
|
||||
* Lookup the right type, unless it's the same as the left type, in which
|
||||
* case typentry is already pointing to the required TypeCacheEntry.
|
||||
*/
|
||||
if (lefttype != righttype)
|
||||
typentry = lookup_type_cache(righttype, TYPECACHE_HASH_PROC |
|
||||
TYPECACHE_EQ_OPR);
|
||||
|
||||
if (OidIsValid(typentry->hash_proc) && OidIsValid(typentry->eq_opr))
|
||||
restrictinfo->right_hasheqoperator = typentry->eq_opr;
|
||||
}
|
||||
|
Reference in New Issue
Block a user