Migration
Diese Seite wurde aus der AirSimTech MediaWiki migriert.
ARINC 429 Screen Buffer Pipeline
Overview
The ARINC 429 screen buffer pipeline carries MCDU page content from the McduCommandParser character writer all the way through to a UDP datagram sent to port 65520 as register 7100 payload. The key design feature is a differential XOR optimization: instead of transmitting all 312 character positions on every page render, the pipeline tracks which cells have changed since the last transmission and sends only the dirty range. A typical page refresh sends 50–100 bytes instead of the full 624-byte buffer, significantly reducing UDP bandwidth to the MCDU display hardware.
Pipeline Stages
Buffer Dimensions
The screen buffer models 13 lines of 24 columns each, giving 312 total character positions:
LINES As Integer = 13COLUMNS As Integer = 24BUFFER_SIZE As Integer = 312(= LINES × COLUMNS)
Two parallel byte arrays hold the screen state:
_charBuffer(311) As Byte— 312-element array (0-based). Each element is one ARINC 429 character byte._ctrlBuffer(311) As Byte— 312-element array (0-based). Each element is a control byte encoding font and color:CByte(CType(font, Byte) Or CType(color, Byte)).
Buffer index for a given position: pos = (line * 24) + column where both line and column are zero-based.
Dirty Range Tracking
Two integer fields track the range of modified positions:
_firstChange As Integer = Integer.MaxValue— lowest position index modified since last reset_lastChange As Integer = -1— highest position index modified since last reset
On each WriteChar or SetControl call:
HasChanges() returns True when _firstChange <= _lastChange.
Character Encoding
Color Codes
Defined in the McduColor enum (A320_FMGC/Inet/Arinc429Constants.vb), matching VB6 Variables_ARINC429.bas:
| Color | Byte Value | McduCommandParser Token |
|---|---|---|
| Black | 0 | (default background, not selectable by token) |
| Cyan | 16 | ~b |
| Red | 32 | ~r |
| Yellow | 48 | ~y |
| Green | 64 | ~g |
| Magenta | 80 | ~m |
| Amber | 96 | ~a |
| White | 112 | ~w |
Font Codes
| Font | Byte Value | McduCommandParser Token |
|---|---|---|
| Small | 0 | @s |
| Large | 128 | @l |
Control Byte Composition
The control byte combines font and color with bitwise OR:
Example: Large (128) + White (112) = 240 (0xF0). Small (0) + Cyan (16) = 16 (0x10).
Special Character Mapping
Arinc429SpecialChars.MapSpecialChar(c As Char) As Byte maps shorthand characters used in MCDU page source strings to their ARINC 429 display byte values:
| Input Char | Output Byte | Symbol |
|---|---|---|
a |
29 | Square symbol |
b |
28 | Degrees symbol |
i |
110 | Flyover waypoint symbol |
c |
95 | Left arrow |
d |
31 | Right arrow |
e |
94 | Up arrow |
f |
30 | Down arrow |
| all others | ASCII byte | Pass-through (ASCII value AND 0xFF) |
Differential XOR Transmission
BuildDifferentialMessage
BuildDifferentialMessage(isCaptain As Boolean) As Byte() produces the binary payload ready for Arinc429UdpSender.SendMessage:
- Returns an empty array (
Array.Empty(Of Byte)()) if there are no pending changes (HasChanges() = False). - Computes
changeCount = _lastChange - _firstChange + 1— the span of the dirty range. - Allocates a
totalLength = 18 + 2 * changeCountbyte array. - Writes an 18-byte fixed header (matching VB6
PageHandle.clslines 245–256):- Bytes 0–1:
0x45, 0x46("EF") - Byte 2:
0x76(118) for Captain,0x7A(122) for FO - Bytes 3–13: fixed magic bytes
- Bytes 14–15: start position as big-endian UInt16 (
_firstChange) - Bytes 16–17: change count as big-endian UInt16
- Bytes 0–1:
- Copies
_ctrlBuffer[_firstChange .. _lastChange]into bytes 18 onward. - Copies
_charBuffer[_firstChange .. _lastChange]immediately after the control bytes.
After calling BuildDifferentialMessage, the caller invokes ResetDirtyRange() to reset _firstChange and _lastChange for the next cycle.
Bandwidth Savings
A full buffer transmission would be 18 + 2 × 312 = 642 bytes. A typical page refresh touches 25–50 contiguous positions, producing 18 + 2 × 50 = 118 bytes or fewer. Single-field updates (e.g., distance readout changing one value) send as few as 20–30 bytes.
UDP Output
Arinc429UdpSender wraps a single System.Net.Sockets.UdpClient instance targeting 255.255.255.255:65520 (UDP broadcast).
XOR Scrambling
Before transmission, SendMessage applies the VB6 mod_ARINC429.bas scrambling algorithm:
- Pad the raw message to a minimum of 24 bytes with 0x00.
- Generate 3 random key bytes:
k0,k1,k2(0–255 each). - Compute
k3 = k0 XOR k1 XOR k2. - Build the scrambled output:
- Index 0: copy as-is
- Index 1:
0x4D('M') - Index 6:
0x45('E') - Index 7:
k0 - Index 8:
0x45('E') - Index 9:
k1 - Index 10:
0x4D('M') - Index 11:
k2 - Index 12:
0x01 - Index 13:
0x01 - All other indices:
rawMessage(i) XOR k3
IDisposable and PostStop
Arinc429UdpSender implements IDisposable. The Close() method shuts down the UdpClient and sets a _disposed flag to prevent double-close. INetActor.PostStop calls _arinc429Sender.Close() to release the socket when the actor system shuts down:
Protected Overrides Sub PostStop()
If _arinc429Sender IsNot Nothing Then _arinc429Sender.Close()
_Logger.Info("INetActor stopped")
End Sub
Calls to SendMessage after disposal are silently discarded with a warning log.
McduActor Integration
McduActor owns one Arinc429ScreenBuffer instance per side (Captain or FO). The buffer is NOT shared between actors. The render cycle operates as follows:
- An input event (LSK press, scratchpad entry, periodic refresh) triggers page rendering.
- The active
IPageimplementation'sHandleLskmethod returns aMcduCommand; separately, theRendermethod builds aList(Of String)of VB6 command strings into the screen buffer. McduCommandParser.ParseAndRender(commands, _screenBuffer)processes the command list:"LISTCLEAR"— calls_screenBuffer.Clear()and resets parser color/font state to White/Large."LISTCOMPLETE"— no-op end marker.- Line content entries (
"01..."through"13...") — parsed for column positions (|CC), font tokens (@s/@l), color tokens (~w/~b/~g/~y/~r/~a/~m), and character bytes.
_screenBuffer.BuildDifferentialMessage(isCaptain)produces the ARINC 429 binary payload._screenBuffer.LastCommandsprovides the raw VB6 command list cached duringParseAndRender— these are the original IPage commands (no binary-to-text reconstruction).ParseAndRenderauto-appendsLISTCOMPLETEif the page omitted it.- Both outputs are passed to INetActor:
_inetActor.Tell(New SendScreenBuffer(isCaptain, bytes, lstLines)). _screenBuffer.ResetDirtyRange()is called after the build.INetActor.HandleSendScreenBuffersends via two paths:- Path 1 — ARINC 429 binary: delegates to
_arinc429Sender.SendMessage(msg.ScreenData)for hardware MCDU displays. - Path 2 — INET register 5339 text: joins lstMcduLines with
Chr(26), sends viaINetClient1.DataTX 5339, 0, subPrefix & payloadfor software MCDU display. Also sends heartbeat on separate sub-address.
- Path 1 — ARINC 429 binary: delegates to
Source Files
A320_FMGC/Inet/Arinc429ScreenBuffer.vb— 13×24 buffer,_charBuffer/_ctrlBuffer, dirty range tracking,BuildDifferentialMessage, 18-byte header formatA320_FMGC/Inet/Arinc429Constants.vb—McduColorenum (Black=0, Cyan=16, Red=32, Yellow=48, Green=64, Magenta=80, Amber=96, White=112),McduFontenum (Small=0, Large=128),Arinc429SpecialChars.MapSpecialCharA320_FMGC/Inet/Arinc429UdpSender.vb—UdpClientwrapper, XOR scrambling algorithm,IDisposable,Close()A320_FMGC/Inet/INetActor.vb—HandleSendScreenBuffer,PostStopcleanupA320_FMGC/Mcdu/McduCommandParser.vb—ParseAndRender, VB6 command string format, color/font token parsingA320_FMGC/Mcdu/McduActor.vb— buffer ownership, render cycle,BuildDifferentialMessagecall site