cleanup: remove duplicate hibernate-0007/quarkus-0003 patches; correct camel/rabbitmq UNDF stamps

This commit is contained in:
russell@unturf.com 2026-03-29 18:34:26 -04:00
parent 919d3f2a57
commit 651aaa7e7b
8 changed files with 6 additions and 210 deletions

View file

@ -1,110 +0,0 @@
# UNDF: (pending)
# hibernate-0007: InFlightMetadataCollectorImpl.buildRecursiveOrderedFkSecondPasses — O(2^D) diamond + O(N²) list scan
## CWE-407 — Algorithmic Complexity: O(2^D) diamond re-traversal + O(N) List.contains in FK ordering
| Field | Value |
|--------------|-------|
| ID | hibernate-0007 |
| Severity | HIGH |
| Ecosystem | hibernate |
| Package | hibernate-core |
| File | `hibernate-core/src/main/java/org/hibernate/boot/internal/InFlightMetadataCollectorImpl.java` |
| Lines | 18351853 |
| Complexity | O(2^D) on diamond FK dependency graphs; O(N) dedup guard |
| Hot path | Called during schema bootstrap: `processSecondPasses()` → FK ordering phase |
## Defect
`buildRecursiveOrderedFkSecondPasses` recursively traverses the FK dependency graph
to produce a topologically-ordered list of `FkSecondPass` operations. It uses `startTable`
as a cycle guard (skips re-entering the starting table), but has no guard for diamond
re-traversal of intermediate shared tables:
```java
// InFlightMetadataCollectorImpl.java:1835-1853 (DEFECT)
private void buildRecursiveOrderedFkSecondPasses(
List<FkSecondPass> orderedFkSecondPasses,
Map<String, Set<FkSecondPass>> isADependencyOf,
String startTable,
String currentTable) {
final Set<FkSecondPass> dependencies = isADependencyOf.get( currentTable );
if ( dependencies != null ) {
for ( var fkSecondPass : dependencies ) {
final String dependentTable = fkSecondPass.getValue().getTable()...render();
if ( dependentTable.compareTo( startTable ) != 0 ) {
buildRecursiveOrderedFkSecondPasses( // recurse — only guards startTable cycle,
orderedFkSecondPasses, isADependencyOf, startTable, dependentTable ); // NOT diamond
}
if ( !orderedFkSecondPasses.contains( fkSecondPass ) ) { // O(N) List.contains!
orderedFkSecondPasses.add( 0, fkSecondPass );
}
}
}
}
```
Two distinct defects:
1. **Diamond re-traversal O(2^D):** On a diamond FK dependency graph
(T1 depends on T2 and T3; both T2 and T3 depend on T4), T4 is visited twice, 2^D times
at depth D. The `startTable` guard only prevents cycles back to T1, not intermediate diamonds.
2. **O(N) List.contains dedup guard:** `orderedFkSecondPasses.contains(fkSecondPass)` is an
O(N) scan of the already-ordered list. With N FK passes and diamond re-traversal,
total cost: O(2^D × N). Even without diamonds, N passes each potentially visiting N
already-ordered entries: O(N²).
## Fix
Add a `Set<String> visited` parameter to track globally-visited tables; replace
`List.contains` with a `LinkedHashSet` for O(1) dedup:
```java
// Call site — line 1804-1806
final LinkedHashSet<FkSecondPass> orderedFkSecondPasses = new LinkedHashSet<>( fkSecondPassList.size() );
for ( String tableName : isADependencyOf.keySet() ) {
buildRecursiveOrderedFkSecondPasses( orderedFkSecondPasses, isADependencyOf, tableName, tableName, new HashSet<>() );
}
// process the ordered passes (LinkedHashSet preserves insertion order)
for ( var sp : orderedFkSecondPasses ) {
sp.doSecondPass( getEntityBindingMap() );
}
// AFTER — O(N+E) total
private void buildRecursiveOrderedFkSecondPasses(
LinkedHashSet<FkSecondPass> orderedFkSecondPasses, // O(1) add/contains
Map<String, Set<FkSecondPass>> isADependencyOf,
String startTable,
String currentTable,
Set<String> visited) { // diamond guard
if ( !visited.add( currentTable ) ) {
return; // already traversed this table in this pass
}
final Set<FkSecondPass> dependencies = isADependencyOf.get( currentTable );
if ( dependencies != null ) {
for ( var fkSecondPass : dependencies ) {
final String dependentTable = fkSecondPass.getValue().getTable().getQualifiedTableName().render();
if ( dependentTable.compareTo( startTable ) != 0 ) {
buildRecursiveOrderedFkSecondPasses( orderedFkSecondPasses, isADependencyOf,
startTable, dependentTable, visited );
}
orderedFkSecondPasses.add( fkSecondPass ); // O(1) dedup via LinkedHashSet
}
}
}
```
Note: `LinkedHashSet` preserves insertion order (same semantics as `add(0, ...)` reversed)
and provides O(1) `add`/`contains`. The `add(0, ...)` pattern builds the list in reverse
topological order; `LinkedHashSet` with final reversal achieves the same.
## Speedup
| Diamond depth (D), N=100 passes | Before (visits) | After (visits) | Speedup |
|---------------------------------|----------------|----------------|---------|
| 5 | 3,100 | 100 | 31× |
| 10 | 102,300 | 100 | 1,023× |
| 15 | 3,276,700 | 100 | 32,767× |
Growth before: O(2^D × N). Growth after: O(N).