Hi, Vicențiu! The patch is ok, please push. But given the time it took us to understand the issue, I'm afraid that simply stating that "HASH implementation shuffles elements around" is not enough. Better to explain how elements are shuffled around. For example: in this case the hash has 131 element, DROP ROLE removes the element [119]. Its [119]->next was element [129], so [129] is moved to [119]. Now we need to compact the hash, removing the last element [130]. It gets one bit off its hash value and becomes element [2]. The existing element [2] is moved to [129], and old [130] is moved to [2]. We cannot simply move [130] to [129] and make [2]->next=130, it won't work if [2] is itself in the collision list and doesn't belong in [2]. On Oct 15, Vicențiu Ciorbaru wrote:
revision-id: cd4cac2b95a (mariadb-10.2.40-91-gcd4cac2b95a) parent(s): 2bb8d7c2f36 author: Vicențiu Ciorbaru committer: Vicențiu Ciorbaru timestamp: 2021-10-13 13:28:50 +0300 message:
MDEV-17964: Assertion `status == 0' failed in add_role_user_mapping_action
This happens upon CREATE USER and DROP ROLE.
The underlying problem is that our HASH implementation shuffles elements around when performing an update or delete. This means that when doing a scan through the HASH table by index, in search of elements to delete or update one must restart the scan to make sure nothing is missed if at least one delete / update happened.
The handle_grant_struct code assumed that it is safe to continue by only reexamining the currently modified / deleted element index, but that is not true.
Missing to delete an element in the hash triggered the assertion in the test case. DROP ROLE would not clear all necessary role->role or role->user mappings.
To fix the problem we ensure that the scan is restarted, only if an element was deleted / updated, similar to how bubble-sort keeps sorting until it finds no more elements to swap.
Regards, Sergei VP of MariaDB Server Engineering and security@mariadb.org