Skip to content

IEEE 802.11: prepare HT aggregate members within receiver limits - #1424

Draft
mgonzalezlopezudc wants to merge 15 commits into
inet-framework:masterfrom
mgonzalezlopezudc:work/ieee80211-ht-ampdu-preparation
Draft

mgonzalezlopezudc wants to merge 15 commits into
inet-framework:masterfrom
mgonzalezlopezudc:work/ieee80211-ht-ampdu-preparation

Conversation

@mgonzalezlopezudc

@mgonzalezlopezudc mgonzalezlopezudc commented Nov 5, 2026 •

Copy link
Copy Markdown
Contributor

HT aggregate construction lacks receiver spacing limits and reversible preparation for independent members. This PR adds both capabilities. Local aggregate transmission remains unavailable at this boundary.

Hypothetical example: a proposed aggregate exceeds the peer's byte limit. The builder reports that limit before the QoS service extracts queued sources. The service can refuse the batch without a DATA attempt. Each retained member keeps its sequence number and deadline.

The changes cover HT capability exchange, the MIB spacing parameter, aggregate construction, the selection policy, QoS batch preparation, and safe Rx rejection. The default MPDU policy leaves aggregation disabled. An explicit HT policy requires fixed DATA rates without a rate-control submodule.

This PR depends on PR #1363. Recipient acceptance and aggregate transmission belong to the next two PRs.

The capability fixtures check encoded spacing and the peer's value in each direction. The construction fixture checks bytes, chunks, source preservation, length, and HT duration limits. The preparation fixture checks refusal, sequence wrap, deadlines, retained members, and initialization with unsupported rate control. The Rx fixture checks failed containers before standalone MAC access.

The tests do not establish a production aggregate exchange at this boundary. No fingerprint, statistical, or chart baseline changes form part of this PR. Some inherited behavior commits lack separate protocol reviewer documents. This split preserves that limit.

This cumulative draft targets upstream master. Its own stage contains 6 commits. The stage comparison excludes prerequisite commits. Earlier commits remain visible until their prerequisite PRs merge.

If those merges change commit IDs, the dependent branches need a rebase.

Review the PRs in this order: #1363, preparation, reception, #1364.

Merge PR #1363 first. The later stages add recipient operation and complete transmission.

The capability fixture originally called the builder API one commit too early. This split moves only its construction block and includes to the builder commit. The capability assertions stay with capability exchange. Both corrected commits pass their assigned fixtures. The preparation boundary retains the original production code and complete fixtures.

Commits in this stage

Commit Contribution and test role
35e43f487b Permits sequence arithmetic across zero. Ieee80211SequenceNumberCyclic_1.test checks that operation.
d8c9914942 Retains peer receiver spacing in each direction. Encoding, capability, association, and initialization fixtures check those limits.
739127da1e Builds aggregates within spacing, length, and duration limits. Construction and capability fixtures check bytes and exchanged limits.
a08d7df969 Rejects failed containers before standalone MAC access. Ieee80211AmpduRxBoundary_1.test supplies malformed containers.
2ab47c31fa Prepares reversible previews and commits validated batches. Ieee80211AmpduPreparation_1.test checks ownership, refusal, deadlines, and sequence wrap.
c94778c89c Documents preparation interfaces and receiver limits. It states that local aggregate transmission remains unavailable.
Prerequisite commits in review order
Commit Contribution and test role
37e9b9a798 Defines the PHY and MAC plan boundaries. It changes no runtime behavior.
b6e769ebfd Corrects the typed VHT header. The identity fixture checks the selected header.
320a64461f Finds bounded members after delimiter damage. The deaggregation fixture checks recovered members.
a64a3b75af Retains HT-SIG fields in bytes. The wire fixture checks the representation.
4d9ddb1fe6 Samples DATA errors without loss of typed chunk boundaries. Direct unit fixtures check corruption.
eb7e4157e3 Preserves cached partial reception outcomes. Physical reception fixtures check the PHY path.
4eeab252e8 Adds seeded PHY error checks through module fixtures.
614f94a640 Checks ordinary PHY behavior against the parent.
c136f222f3 Records PHY scope and limitations. It changes no runtime behavior.

Fresh verification

The PR head is c94778c89c. Verification uses OMNeT++ 6.4.0aipre2, Clang, and the retained workspace. Fixture definitions supply configurations and seeds. Counts below identify fixtures, not simulation repetitions.

Check Observed result
Focused unit selection 3 PASS.
Focused module selection 5 PASS.
Debug compilation PASS.
Release compilation PASS.

Whole-tree architecture and interface checks retain existing findings. Their reports match the previous published feature reports. Naming checks retain the same violation lines. These checks remain FAIL. Mechanical series and source protection checks pass. C++ lint remains unverified without a compilation database.

Commands and local evidence

Evidence is under audit/ampdu-pr-split-20261105/. The execution record is ai-logs/executions/2026-11-05_ampdu-pr-split.md. Each source commit in the MAC split has a fresh debug build and focused test record. The prerequisite PHY commits retain their historical evidence. The temporary compatible descriptor omits only the unsupported coverage.report metadata. The checked-in descriptor remains unchanged.

make MODE=debug -j6
opp_run_unit_tests --load /home/user/omnetpp_ws/inet-ieee80211-ampdu-implicit-blockack-a1-a7/audit/ampdu-exchange-split-20261105/compatible.opp -p inet -m debug --no-build --no-concurrent -f 'Ieee80211(SequenceNumberCyclic|AmpduCapabilityEncoding|AmpduConstruction)_1\.test$' --result-file /home/user/omnetpp_ws/inet-ieee80211-ampdu-implicit-blockack-a1-a7/audit/ampdu-pr-split-20261105/pr1-unit-results.json
opp_run_module_tests --load /home/user/omnetpp_ws/inet-ieee80211-ampdu-implicit-blockack-a1-a7/audit/ampdu-exchange-split-20261105/compatible.opp -p inet -m debug --no-build --no-concurrent -f 'Ieee80211(AmpduCapabilities|HtAssociation|MgmtStaSimplifiedInitialization|AmpduRxBoundary|AmpduPreparation)_1\.test$' --result-file /home/user/omnetpp_ws/inet-ieee80211-ampdu-implicit-blockack-a1-a7/audit/ampdu-pr-split-20261105/pr1-module-results.json
make MODE=release -j6

Raw logs, JSON results, output archives, source comparisons, and file hashes retain the evidence and preservation checks.

Before this commit, the branch has no plan for HT aggregate reception or implicit Block Ack integration.

After this commit, the plans define separate PHY and MAC duties, staged changes, required evidence, and acceptance limits. Both plans use the integrated master base. Their first stages define wire representation, bounded member ranges, and cached PHY outcomes. MAC acceptance remains separate. This commit changes no runtime behavior.

Plan: plan/pending/ieee80211-ampdu-phy-reception.md
Change: plan | behavior.add | - | ieee80211-ampdu-phy-reception
Before this commit, a VHT signal mode creates an HT header. The transmission has the wrong typed header and can enter later HT validation without an HT MCS.

After this commit, the VHT signal mode creates the existing VHT header. Its selected length remains unchanged. This prerequisite adds no VHT serializer or aggregate profile.

WifiVhtHeaderIdentity.test sends an ordinary PSDU through the production radio and checks the header at transmission start. On the parent, the factory supplies an HT object, so the assertion that requires Ieee80211VhtPhyHeader fails. With this commit, the factory supplies a VHT object. The VHT assertion succeeds, the HT exclusion succeeds, and the header length matches the selected mode. The driver then emits its required completion event. Both guard intervals use these assertions.

Protocol verification: tests/protocol/wifi/vht-header-identity.md

Protocol comparison: tests/protocol/wifi/vht-header-identity-comparison.md

Plan: plan/pending/ieee80211-ampdu-phy-reception.md
Change: src.ieee80211 | behavior.change.fix | test whatsnew | ieee80211-ampdu-phy-reception
Before this commit, the shared loop stops at an invalid delimiter. In a three-member aggregate, the middle delimiter declares 2000 octets where only 124 remain. The deaggregator returns the first member but loses the later complete member.

After this commit, the same loop examines delimiter candidates at four-octet intervals. Explicit byte reinterpretation permits the search to cross typed MAC headers. A later valid delimiter supplies the final complete MPDU without an intermediate layout.

WifiMpduDeaggregation.test from this commit requires two outputs for the malformed input: the first and final complete members. On the immediate parent, the bounds check stops extraction after the first member. The two-member count assertion therefore fails. With this commit, the search finds the final delimiter and extracts its twenty-octet member. The count, length, and byte-content assertions succeed, so the driver emits its required completion event. Complete input still returns all three members. The fixture applies these assertions to typed chunks and reconstructed bytes.

The unit fixture also compares callback order and offsets across both representations. Extraction alone grants no MAC acceptance.

Protocol verification: tests/protocol/wifi/mpdu-deaggregation.md

Protocol comparison: tests/protocol/wifi/mpdu-deaggregation-comparison.md

Plan: plan/pending/ieee80211-ampdu-phy-reception.md
Change: src.ieee80211 | behavior.change.fix | test whatsnew | ieee80211-ampdu-phy-reception
Before this commit, HT header conversion supplies no HT-SIG bytes. A singleton aggregate cannot retain its aggregate identity through byte conversion. The preceding VHT prerequisite already supplies the correct VHT header type.

After this commit, the radio assigns HT-SIG fields and CRC from the selected mode and aggregate identity. The serializer preserves all 48 bits. Validation rejects invalid CRC, unsupported fields, and insufficient content before length-based trailer removal. Ordinary valid HT duration inputs remain unchanged.

WifiHtAmpduWire.test sends a 104-octet singleton through the production radio. It requires the independent HT-SIG vector 00 68 00 0F B4 01. On the parent, the HT serializer writes zero bits for a 48-bit header. The serialization-length check fails before the expected-byte assertion can succeed. With this commit, serialization produces those six octets. Independent decode also satisfies the Length, Aggregation, MCS, guard-interval, and CRC assertions. Typed and raw-byte transmission use the same checks.

The fixture reads new fields through descriptors, so it can compile with the parent's header API. MAC aggregate acceptance remains outside this commit.

Protocol verification: tests/protocol/wifi/ampdu-ht-sig-wire.md

Protocol comparison: tests/protocol/wifi/ampdu-ht-sig-wire-comparison.md

Plan: plan/pending/ieee80211-ampdu-phy-reception.md
Change: src.ieee80211 | behavior.add | test whatsnew migration | ieee80211-ampdu-phy-reception
Before this commit, the public error-model interface offers whole-packet corruption only after a failed reception decision. The common corruption function repeats its samples until some error occurs. That contract cannot represent one unconditional DATA result with correct and incorrect chunks.

After this commit, computeReceivedData() samples each existing DATA chunk once. It returns content of the same length and bytes. Failed chunks receive local incorrect flags; transmitted chunks remain unchanged. An entirely correct result needs no retry. The common probability calculation uses DATA BER. Models can override that calculation with their existing PHY functions. Zero and unit probabilities consume no random number. Invalid probabilities cause a runtime error.

DataChunkCorruption_1.test checks correct content, local errors, unchanged bytes, duplication, extraction, and invalid probabilities without a MAC format. The receiver integration follows in the next commit. Existing whole-packet callers retain their current path.

Plan: plan/pending/ieee80211-ampdu-phy-reception.md
Change: src.physicallayer | behavior.add | test whatsnew | ieee80211-ampdu-phy-reception
Before this commit, the receiver samples an HT aggregate as one packet. It cannot preserve an incorrect payload chunk beside correct content. Rx can inspect that container as a standalone MAC frame and request an invalid header.

After this commit, the receiver validates HT-SIG and PSDU bounds before DATA corruption. The IEEE 802.11 error-model base supplies chunk probabilities through its existing DATA calculation. The common error-model operation samples each chunk once without delimiter or MPDU knowledge. The DATA decision retains the received chunks. WHOLE and result queries reuse them. Failed chunks retain local incorrect flags without a change to the transmitted content.

For three typed members with an incorrect middle payload, the received packet retains that error beside correct first and final members. Byte conversion removes those boundaries, so raw input has one DATA outcome. The protocol fixture checks both cases at the production Rx drop. A later CTS must still set its 50-microsecond NAV. On the parent, the required indication is absent and the fixture fails at the drop. Fresh parent execution remains separate from final-HEAD verification.

Rx rejects aggregate containers before standalone checks. The indication retains header and content facts; chunk flags retain errors. Aggregate error-rate estimates remain unknown with a present model. Ordinary reception keeps its current path. Member acceptance and implicit Block Ack remain separate work.

Protocol verification: tests/protocol/wifi/ampdu-partial-reception.md

Protocol comparison: tests/protocol/wifi/ampdu-partial-reception-comparison.md

Plan: plan/pending/ieee80211-ampdu-phy-reception.md
Change: src.ieee80211 | behavior.add+change | test whatsnew migration | ieee80211-ampdu-phy-reception
Before this commit, deterministic fixtures fix selected chunk failures but do not compare production model probabilities and random draws. A receiver could repeat DATA samples without those fixtures detecting every difference.

After this commit, the receiver fixture compares NIST and Yans chunk probabilities with their existing DATA calculations. Fixed seeds verify the sampled chunk flags, retained packet content, cache reuse, and the next random value. Scalar and dimensional radios cover both guard intervals and both reception-part modes. Each existing chunk receives one outcome, including padding.

For an intermediate probability, the reference generator consumes one draw per chunk. Repeated PREAMBLE, HEADER, DATA, WHOLE, and result queries must preserve the recorded flags and draw count. Header failure and insufficient content must prevent DATA draws. A generic BER model needs no aggregation role for initialization.

The fixture also checks pure PHY calculations across 64 HT20 modes, six lengths, and seven SNIR values. Production code and stored fingerprint expectations remain unchanged.

Plan: plan/pending/ieee80211-ampdu-phy-reception.md
Change: tests | behavior.add | - | ieee80211-ampdu-phy-reception
Before this commit, ordinary reception controls lack a fixture that compiles unchanged on the pinned parent and the feature branch. The earlier receiver fixture cannot provide that independent compatibility comparison.

After this commit, one fixture records ordinary reception with identical inputs on both revisions. NIST, Yans, absent-model, and non-HT custom controls cover three noise levels and seeds 0, 1, and 2. The campaign uses scalar and dimensional radios with whole and separate signal parts. Each record includes outcomes, duration, metadata, draw counts, and subsequent random values.

For example, a failed ordinary reception must retain the same metadata and next random value as its parent control. The migration guide states the independent-range abstraction and its limits. MAC aggregate receipt and implicit Block Ack remain pending. BerTable retains its documented parent crash, which supplies no successful reception evidence.

The additional fixture and records change no production contract or stored expectation. Execution results belong in the PR description and execution record.

Plan: plan/pending/ieee80211-ampdu-phy-reception.md
Change: tests | behavior.add | - | ieee80211-ampdu-phy-reception
Before this commit, the plans describe aggregate-specific probability roles and separate range outcomes. They also describe bounded deaggregation as a prerequisite in the same visible PR. These descriptions obscure the responsibilities of the PHY error model and the MAC parser.

After this commit, the plans assign chunk corruption to the common PHY interface. The receiver caches the received chunks. Error models use PHY conditions and bit lengths without MAC format knowledge. MAC extraction retains delimiter parsing and member validation. Raw byte input has one DATA outcome because byte conversion removes its original chunk boundaries.

The plans also separate the deaggregation prerequisite from recovery and partial PHY reception. Master supplies bounded extraction. The dependent work adds delimiter recovery and cached chunk errors. Member acceptance and implicit Block Ack remain separate future work. Expected results and retained historical evidence remain distinct.

Plan: plan/pending/ieee80211-ampdu-phy-reception.md
Change: plan | behavior.change | - | ieee80211-ampdu-phy-reception
Before this commit, valid sequence arithmetic can produce an intermediate value of minus one. The shared helper rejects that value, so 0 - 1 fails instead of returning sequence 4095.

After this commit, the helper reduces every valid intermediate modulo 4096. Constructors and arithmetic operators still reject an unspecified source. The unit fixture checks every sequence value with positive and negative offsets. Aggregate reorder advancement needs this correction at sequence wrap.

Plan: plan/pending/ieee80211-ampdu-implicit-blockack.md
Change: src.ieee80211 | behavior.change.fix | test | ieee80211-implicit-blockack
Before this commit, negotiated HT state lacks the receiver's minimum MPDU start spacing. An aggregate builder therefore cannot apply that receiver limit.

After this commit, full and simplified management preserve the encoded spacing in each negotiated direction. The MIB exposes the local receiver setting. The transmitter can obtain the peer receiver's limit before aggregate construction. Capability fixtures check asymmetric limits, encoding, initialization, and reset.

Plan: plan/pending/ieee80211-ampdu-implicit-blockack.md
Change: src.ieee80211 | behavior.add | test whatsnew migration | ieee80211-implicit-blockack
Before this commit, aggregate construction cannot preview spacing at the selected DATA mode while it preserves the source MPDUs. It also lacks the complete HT duration admission calculation.

After this commit, the builder borrows source references and copies their data and region tags. Alignment padding and zero-length delimiters satisfy negotiated spacing. Construction checks the receiver byte limit, PPDU duration, and L-SIG length. Singleton aggregates retain their delimiter. Construction tests use the existing chunk walker without an intermediate layout.

The wire, traversal, and construction fixtures check serialization, spacing boundaries, source ownership, and malformed input. These operations prepare the later exchange without enabling the default MPDU policy.

Plan: plan/pending/ieee80211-ampdu-implicit-blockack.md
Change: src.ieee80211 | behavior.add+change | test whatsnew migration | ieee80211-implicit-blockack
Before this commit, Rx excludes a decoded aggregate from standalone FCS checks. A failed common header can lack that decoded property, so its container can reach an unsafe MAC peek.

After this commit, Rx also checks common-header success and complete content before standalone parsing. The boundary fixture supplies malformed containers and proves refusal before the FCS predicate. Correct standalone reception retains its existing path.

Plan: plan/pending/ieee80211-ampdu-implicit-blockack.md
Change: src.ieee80211 | behavior.change.fix | test | ieee80211-implicit-blockack
Before this commit, the QoS service can prepare one DATA transmission but cannot retain independent previews beside canonical retry members. An aggregate selection must preserve sources until actual submission.

After this commit, the HT policy selects borrowed members under supplied peer, window, mode, spacing, and length limits. The service gives each queued member an independent preview. Batch commitment validates every source before extraction. Canonical members retain their sequence numbers and deadlines. Forwarded previews use the local transmitter address without changing queued headers or ordinary A-MSDU construction.

HCF rejects aggregate opt-in with a rate-control submodule at initialization. The default Basic policy remains disabled. Preparation fixtures check refusal, wrap, deadlines, limits, retained members, and both AARF rejection configurations.

Plan: plan/pending/ieee80211-ampdu-implicit-blockack.md
Change: src.ieee80211 | behavior.add | test whatsnew migration | ieee80211-implicit-blockack
Before this commit, extension authors lack documentation for HT construction and reversible batch preparation. The MAC still cannot transmit aggregates.

After this commit, the migration guide describes receiver spacing, builders that retain sources, policy selection, batch commitment, and safe Rx rejection. The release note states the available capabilities and limits. This commit changes no runtime behavior.

Change: doc | comment | - | ieee80211-implicit-blockack

This branch has not been deployed

No deployments
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment

Labels

None yet

Projects

None yet

Development

Successfully merging this pull request may close these issues.

1 participant