java-topology/whitepaper/outreach/cocos2d-0003.md
russell@unturf.com aeb084c9ae feat: add 30 outreach docs (batches 9-10)
Batch 9 (15): bun, bzflag (3), cake_wallet (4), calligra, caprice32 (2),
  cataclysm (3), cemu
Batch 10 (15): cemu-0002, citra, clickhouse-java, cmake (3), cocos2d (3),
  conduit, cura (2), curaengine, clamav, contiki
2026-04-14 19:51:36 -04:00

2.6 KiB
Raw Blame History

Cocos2d-x — CWE-407 Disclosure Brief (cocos2d-0003)

2026-04-13 · Patch available — awaiting upstream merge

Finding

One O(n²) defect in Cocos2d-x in the skeletal animation bone node system. _boneSkins.contains() (O(S) linear scan over a Vector<SkinNode*>) fires per child per frame during visit() traversal. Patched.

The Defects

cocos2d-0003 (PATCHED — HIGH): cocos/editor-support/cocostudio/ActionTimeline/CCBoneNode.cpp:341

// In BoneNode::visit — fires per child per frame:
for (; i < _children.size(); i++)
{
    auto node = _children.at(i);
    if (_rootSkeleton != nullptr && _boneSkins.contains(node))  // O(S) linear scan
        continue;
    ...
}

_boneSkins is Vector<SkinNode*> (Cocos2d's custom vector). .contains() is a linear scan over all skins. This check fires for every child node during visit() — the scene graph traversal that runs every frame. For a bone with C children and S skins: O(C × S) per bone per frame.

For an animated character with B bones, each with C children and S skins: O(B × C × S) per frame.

Complexity Proof

At B=30 bones, C=5 children per bone, S=10 skins per bone:

  • Defective: 30 × 5 × 10 = 1,500 comparisons per frame
  • Fixed: 30 × 5 × 1 = 150 hash lookups
  • 10× op reduction per frame. Multiple animated characters multiply this.

Impact

Cocos2d-x skeletal animation drives character animation in thousands of mobile games. Games with multiple animated characters on screen (action games, RPGs, strategy games) multiply the per-frame cost by character count. At 60 fps with 10 animated characters: 900,000 comparisons/sec eliminated.

The Fix

Add an std::unordered_set<Node*> shadow cache for _boneSkins:

// Before
cocos2d::Vector<SkinNode*> _boneSkins;
_boneSkins.contains(node)  // O(S)

// After — O(1) lookup via shadow set
std::unordered_set<cocos2d::Node*> _boneSkinSet;
_boneSkinSet.count(node)  // O(1)
// Rebuild _boneSkinSet in addSkin / removeSkin.

Patch

Fix available: defects/cocos2d-0003/patch/cocos2d-0003.patch

Two-file patch across CCBoneNode.h and CCBoneNode.cpp.

Unit test: pass. 10× op reduction per frame per character.

What We Ask

A patch is ready for review.

  1. Confirm receipt and assign a GitHub issue reference (cocos2d/cocos2d-x).
  2. Assess severity — fires per bone per child per frame during skeletal animation rendering.
  3. Coordinate a disclosure date — we are targeting 90 days from first contact.
  4. We will credit the Cocos2d-x team in the public disclosure. Preferred acknowledgment format welcome.

Contact: see cover email. This brief is confidential until coordinated disclosure.