Phase 1 (rfsim): per-UE deterministic channel injection.
Each UE container sets OAI_UE_CHANNEL_CLASS=k (k in {0..3}). The rfsim
no-chanmod sample-mixing path applies a 4x4 channel:
H^(k)[r,a] = H_orig[r,a] * w_k[a]
where w_k is the k-th codeword of the Type I 4-port rank-1 codebook
(N1=2, N2=1). Multiplying by w_k rotates the channel's optimal PMI
direction to k while preserving the original symmetric kernel's
full-rank reception (so SSB sync still works on all UE classes).
10 UEs cycle through 4 classes (UE_index mod 4), giving 4 mutually
orthogonal PMI populations.
Phase 3 (scheduler): pf_dl partner search now scans connected_ue_list
(not just UE_sched). After leader UE A is allocated, iterate over all
connected UEs, run update_dlsch_buffer/dlsch_to_schedule per candidate,
and pair the first orthogonal-PMI partner that has data + free CCE/PUCCH.
This bypasses PF time-multiplexing — multiple UEs needn't be in
UE_sched simultaneously for MU-MIMO to fire.
Per-slot pairing tag (mumimo_paired_slot in NR_UE_sched_ctrl_t) prevents
double-allocation: incremented per pf_dl call, leader and partner both
tagged on success; subsequent leader iterations skip already-tagged UEs.
Results on rfsim with 10 UEs cycling 4 classes (10-min run):
17000+ pairings observed
Distribution by (leader_class, partner_class):
0->2: 6261 (XOR=2)
3->1: 4382 (XOR=2)
2->0: 2765 (XOR=2)
1->3: 1920 (XOR=2)
All pairs strictly orthogonal per Type I codebook rank-1 rule
(same x1, x2 differ by 2). 2-way MU-MIMO working end-to-end.
Also includes:
- ri_bitlen=0 fix in evaluate_cqi_report (uninitialized r_index)
- OAI_MU_MIMO=1 env to enable, OAI_MU_MIMO_RELAXED=1 for relaxed test
- Diagnostic logs every 200th call: ENTER + per-skip-reason