undefect. CWE-407 — 98 sites, 44 ecosystems; game engines: godot, dry/urho3d; CLAUDE.md clone policy
This commit is contained in:
parent
083765d3c6
commit
442a6156e3
8 changed files with 324 additions and 4 deletions
59
defects/dry/patch/dry-0001-listview-hashset.patch
Normal file
59
defects/dry/patch/dry-0001-listview-hashset.patch
Normal file
|
|
@ -0,0 +1,59 @@
|
|||
--- a/Source/Dry/UI/ListView.h
|
||||
+++ b/Source/Dry/UI/ListView.h
|
||||
@@ -... ListView class members
|
||||
- PODVector<unsigned> selections_;
|
||||
+ PODVector<unsigned> selections_; // preserved for ordered iteration
|
||||
+ HashSet<unsigned> selections_set_; // O(1) shadow index for Contains checks
|
||||
|
||||
--- a/Source/Dry/UI/ListView.cpp
|
||||
+++ b/Source/Dry/UI/ListView.cpp
|
||||
@@ -518,7 +518,8 @@ void ListView::SetSelections(const PODVector<unsigned>& indices)
|
||||
unsigned numItems = GetNumItems();
|
||||
|
||||
+ // FIX dry-0001: build O(1) lookup set from incoming indices — CWE-407
|
||||
+ // Both loops below called indices.Contains() or selections_.Contains() which are
|
||||
+ // O(n) linear scans on PODVector. At k=1000 selections: O(n²) = 1,000,000 ops.
|
||||
+ HashSet<unsigned> indicesSet(indices.Begin(), indices.End());
|
||||
+
|
||||
// Remove first items that should no longer be selected
|
||||
for (PODVector<unsigned>::Iterator i = selections_.Begin(); i != selections_.End();)
|
||||
{
|
||||
unsigned index = *i;
|
||||
- if (!indices.Contains(index)) // O(n) — CWE-407
|
||||
+ if (!indicesSet.Contains(index)) // O(1) — fixed
|
||||
{
|
||||
i = selections_.Erase(i);
|
||||
+ selections_set_.Erase(index);
|
||||
|
||||
using namespace ItemSelected;
|
||||
// ... SendEvent(E_ITEMDESELECTED, ...)
|
||||
}
|
||||
else
|
||||
++i;
|
||||
}
|
||||
|
||||
// Then add missing items
|
||||
for (PODVector<unsigned>::ConstIterator i = indices.Begin(); i != indices.End(); ++i)
|
||||
{
|
||||
unsigned index = *i;
|
||||
if (index < numItems)
|
||||
{
|
||||
- bool duplicate = selections_.Contains(index); // O(n) — CWE-407
|
||||
+ bool duplicate = selections_set_.Contains(index); // O(1) — fixed
|
||||
if (!duplicate || !multiselect_)
|
||||
{
|
||||
if (!duplicate)
|
||||
{
|
||||
selections_.Push(index);
|
||||
+ selections_set_.Insert(index);
|
||||
added = true;
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
// All other methods that modify selections_ must also maintain selections_set_:
|
||||
// AddSelection(index) → selections_set_.Insert(index)
|
||||
// RemoveSelection(index) → selections_set_.Erase(index)
|
||||
// ClearSelection() → selections_set_.Clear()
|
||||
32
defects/dry/patch/dry-0002-object-unsub-hashset.patch
Normal file
32
defects/dry/patch/dry-0002-object-unsub-hashset.patch
Normal file
|
|
@ -0,0 +1,32 @@
|
|||
--- a/Source/Dry/Core/Object.cpp
|
||||
+++ b/Source/Dry/Core/Object.cpp
|
||||
@@ -269,12 +269,16 @@ void Object::UnsubscribeFromAllEventsExcept(const PODVector<StringHash>& exceptions, bool onlyUserData)
|
||||
{
|
||||
EventHandler* handler = eventHandlers_.First();
|
||||
EventHandler* previous = nullptr;
|
||||
|
||||
+ // FIX dry-0002: was exceptions.Contains() — O(m) per handler — CWE-407
|
||||
+ // With n handlers and m exceptions: O(n*m) total.
|
||||
+ // Build a HashSet once at O(m), then each check is O(1) → O(n) total.
|
||||
+ HashSet<StringHash> exceptionsSet(exceptions.Begin(), exceptions.End());
|
||||
+
|
||||
while (handler)
|
||||
{
|
||||
EventHandler* next = eventHandlers_.Next(handler);
|
||||
|
||||
- if ((!onlyUserData || handler->GetUserData()) && !exceptions.Contains(handler->GetEventType()))
|
||||
+ if ((!onlyUserData || handler->GetUserData()) && !exceptionsSet.Contains(handler->GetEventType()))
|
||||
{
|
||||
if (handler->GetSender())
|
||||
context_->RemoveEventReceiver(this, handler->GetSender(), handler->GetEventType());
|
||||
else
|
||||
context_->RemoveEventReceiver(this, handler->GetEventType());
|
||||
|
||||
eventHandlers_.Erase(handler, previous);
|
||||
}
|
||||
else
|
||||
previous = handler;
|
||||
|
||||
handler = next;
|
||||
}
|
||||
}
|
||||
Loading…
Add table
Add a link
Reference in a new issue