Commit f6331862 authored by Nektarios Paisios's avatar Nektarios Paisios Committed by Commit Bot

Checks if an aria-owned child has an owning parent before trying to retrieve its parent

When an object that is aria-owned by another object is re-parented as a layout object
we remove any aria-owned children mappings it may have in the AXRelationCache,
in addition to the mapping to its aria-owning parent.
However, we don't remove any mappings from its parent to the removed object from the AXRelationCache.
After the children of its parent will have been marked as requiring an update, the AXRelationCache will try and unmap the parent's existing owned children before adding the new ones.
During the unmap process, we check if any of the previous children are already owned by another object, in order to skip removing them from the cache if so.
However, we forget to check whether any of the previous children has been removed from the cached because it has been re-parented and
its AxID has been re-used because its the same DOM node that has been provided with a layout object.

R=dmazzoni@chromium.org, aleventhal@chromium.org

Bug: 934529
Change-Id: I298d396987f444d061a2f2324580726e987a739b
Reviewed-on: https://chromium-review.googlesource.com/c/1485064Reviewed-by: default avatarDominic Mazzoni <dmazzoni@chromium.org>
Commit-Queue: Nektarios Paisios <nektar@chromium.org>
Cr-Commit-Position: refs/heads/master@{#635187}
parent a580b6d6
......@@ -19,8 +19,13 @@ bool AXRelationCache::IsAriaOwned(const AXObject* child) const {
}
AXObject* AXRelationCache::GetAriaOwnedParent(const AXObject* child) const {
return ObjectFromAXID(
aria_owned_child_to_owner_mapping_.at(child->AXObjectID()));
// Child IDs may still be present in owning parents whose list of children
// have been marked as requiring an update, but have not been updated yet.
HashMap<AXID, AXID>::const_iterator iter =
aria_owned_child_to_owner_mapping_.find(child->AXObjectID());
if (iter == aria_owned_child_to_owner_mapping_.end())
return nullptr;
return ObjectFromAXID(iter->value);
}
// Update reverse relation map, where relation_source is related to target_ids.
......@@ -42,7 +47,6 @@ static bool ContainsCycle(AXObject* owner, AXObject* child) {
for (AXObject* parent = owner; parent; parent = parent->ParentObject()) {
if (parent == child)
return true;
;
}
return false;
}
......@@ -228,8 +232,7 @@ void AXRelationCache::UpdateRelatedText(Node* node) {
void AXRelationCache::RemoveAXID(AXID obj_id) {
if (aria_owner_to_children_mapping_.Contains(obj_id)) {
Vector<AXID> child_axids = aria_owner_to_children_mapping_.at(obj_id);
for (AXID child_axid : child_axids)
aria_owned_child_to_owner_mapping_.erase(child_axid);
aria_owned_child_to_owner_mapping_.RemoveAll(child_axids);
aria_owner_to_children_mapping_.erase(obj_id);
}
aria_owned_child_to_owner_mapping_.erase(obj_id);
......
......@@ -34,6 +34,15 @@ test(function(t)
futureParent.setAttribute("aria-owns", "future_child");
assert_equals(axFutureParent.childrenCount, 1);
child.style.visibility = 'hidden';
assert_equals(axFutureParent.childrenCount, 0);
child.style.visibility = 'visible';
assert_equals(axFutureParent.childrenCount, 1);
child.remove();
assert_equals(axFutureParent.childrenCount, 0);
}, "Aria-owns is dynamically recomputed.");
</script>
......
Markdown is supported
0%
or
You are about to add 0 people to the discussion. Proceed with caution.
Finish editing this message first!
Please register or to comment