gnss-js 2.10.1 → 2.12.0

This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
Files changed (55) hide show
  1. package/README.md +16 -1
  2. package/dist/analysis.cjs +24 -25
  3. package/dist/analysis.js +2 -2
  4. package/dist/{clk-DGVBGRzA.d.cts → bias-sinex-OGMw9xEZ.d.cts} +66 -1
  5. package/dist/{clk-DGVBGRzA.d.ts → bias-sinex-OGMw9xEZ.d.ts} +66 -1
  6. package/dist/binex.d.cts +1 -1
  7. package/dist/binex.d.ts +1 -1
  8. package/dist/{chunk-56HM5B6T.js → chunk-2DJ4XENO.js} +177 -9
  9. package/dist/{chunk-GH7MYXON.js → chunk-2KQMCJ5Z.js} +7 -5
  10. package/dist/chunk-E3Y6YKQM.js +65 -0
  11. package/dist/{chunk-3U5AX7PY.js → chunk-FEABDV5P.js} +24 -25
  12. package/dist/{chunk-WQX354KD.js → chunk-H3AKFD25.js} +1 -1
  13. package/dist/{chunk-YUW33VXK.js → chunk-HUXQABJI.js} +2 -0
  14. package/dist/{chunk-74IVYOQV.js → chunk-HWHD5E6V.js} +128 -78
  15. package/dist/{chunk-KUSUN7DP.js → chunk-MFCPYUEI.js} +1 -1
  16. package/dist/{chunk-3KSDL3CO.js → chunk-NIJ6WFQJ.js} +6 -321
  17. package/dist/chunk-NL2ORX75.js +319 -0
  18. package/dist/{chunk-K3GLUWZI.js → chunk-RWFJEVLJ.js} +590 -296
  19. package/dist/{chunk-SEYH4BEN.js → chunk-SZP4TLYR.js} +2 -2
  20. package/dist/chunk-TWGZTRBL.js +323 -0
  21. package/dist/index.cjs +1315 -460
  22. package/dist/index.d.cts +5 -5
  23. package/dist/index.d.ts +5 -5
  24. package/dist/index.js +20 -12
  25. package/dist/{nav-DImXUdbp.d.cts → nav-COp0Vmlw.d.cts} +83 -2
  26. package/dist/{nav-DImXUdbp.d.ts → nav-COp0Vmlw.d.ts} +83 -2
  27. package/dist/{nav-BYmYoh9A.d.cts → nav-CvZXmumD.d.cts} +1 -1
  28. package/dist/{nav-CN8rxL4h.d.ts → nav-D2DFlVpa.d.ts} +1 -1
  29. package/dist/novatel.d.cts +1 -1
  30. package/dist/novatel.d.ts +1 -1
  31. package/dist/novatel.js +3 -3
  32. package/dist/orbit.d.cts +2 -2
  33. package/dist/orbit.d.ts +2 -2
  34. package/dist/osnma.cjs +1336 -0
  35. package/dist/osnma.d.cts +273 -0
  36. package/dist/osnma.d.ts +273 -0
  37. package/dist/osnma.js +1216 -0
  38. package/dist/positioning.cjs +585 -291
  39. package/dist/positioning.d.cts +116 -6
  40. package/dist/positioning.d.ts +116 -6
  41. package/dist/positioning.js +3 -3
  42. package/dist/rinex.cjs +210 -36
  43. package/dist/rinex.d.cts +10 -55
  44. package/dist/rinex.d.ts +10 -55
  45. package/dist/rinex.js +6 -3
  46. package/dist/sbf.cjs +420 -24
  47. package/dist/sbf.d.cts +46 -5
  48. package/dist/sbf.d.ts +46 -5
  49. package/dist/sbf.js +12 -6
  50. package/dist/trimble.d.cts +1 -1
  51. package/dist/trimble.d.ts +1 -1
  52. package/dist/ubx.d.cts +1 -1
  53. package/dist/ubx.d.ts +1 -1
  54. package/dist/ubx.js +5 -4
  55. package/package.json +6 -1
@@ -0,0 +1,273 @@
1
+ /**
2
+ * OSNMA Merkle tree (SIS ICD v1.1 §6.2): the trust anchor that public
3
+ * keys — broadcast in DSM-PKR or loaded from the GSC — are checked
4
+ * against. N = 16 leaves, SHA-256, root x(4,0).
5
+ */
6
+ /**
7
+ * Root of the OSNMA Merkle tree in force since 2025-12-10 (GSC file
8
+ * OSNMA_MerkleTree_20251209100000_newPKID_2.xml, UID MT-D7A51E17…).
9
+ * Per the ICD a tree is renewed "very rarely, typically after more
10
+ * than 10 years", announced 2 years ahead; pass `merkleRoot` to
11
+ * {@link OsnmaReceiver} to use another one.
12
+ */
13
+ declare const OSNMA_MERKLE_ROOT: Uint8Array<ArrayBuffer>;
14
+ /** A public key with the Merkle path that proves it against a root. */
15
+ interface OsnmaPublicKeyRecord {
16
+ /** Public key ID (PKID). */
17
+ pkid: number;
18
+ /** Key type (NPKT): 1 = ECDSA P-256, 3 = ECDSA P-521. */
19
+ npkt: number;
20
+ /** SEC1-compressed public key. */
21
+ key: Uint8Array;
22
+ /** Leaf index i of m_i in the tree (MID). */
23
+ mid: number;
24
+ /** Intermediate nodes x(0,·), x(1,·), x(2,·), x(3,·) along the path. */
25
+ path: Uint8Array[];
26
+ }
27
+ /**
28
+ * The public key in force at the time of writing, PKID 2, as published
29
+ * by the GSC with its Merkle path (leaf m1). It is checked against the
30
+ * root before use, like a broadcast DSM-PKR, so a wrong constant here
31
+ * fails closed.
32
+ */
33
+ declare const OSNMA_KNOWN_PUBLIC_KEYS: readonly OsnmaPublicKeyRecord[];
34
+ /**
35
+ * Check a Merkle leaf m_i = (NPKT ‖ NPKID ‖ NPK) against `root` through
36
+ * the four intermediate nodes of its path (ICD Eq. 12-13, Table 4).
37
+ */
38
+ declare function merkleLeafOk(leaf: Uint8Array, mid: number, path: readonly Uint8Array[], root: Uint8Array): boolean;
39
+
40
+ /**
41
+ * Galileo OSNMA (Open Service Navigation Message Authentication)
42
+ * receiver, after the OSNMA SIS ICD v1.1 (October 2023) and the
43
+ * Receiver Guidelines v1.3.
44
+ *
45
+ * Feed it Galileo E1-B I/NAV nominal page pairs; it reassembles the
46
+ * 40-bit OSNMA field of each page into the per-subframe HKROOT (DSM
47
+ * blocks) and MACK (tags + TESLA key) messages and runs the whole
48
+ * chain of trust:
49
+ *
50
+ * Merkle root ─▶ public key (DSM-PKR, or a known key + its path)
51
+ * ─▶ ECDSA-signed TESLA root key (DSM-KROOT)
52
+ * ─▶ TESLA chain keys (one per subframe, delayed disclosure)
53
+ * ─▶ MAC tags over the satellites' navigation data
54
+ *
55
+ * A tag that verifies proves the satellite's ephemeris/clock (ADKD 0,
56
+ * 12) or GST-UTC/GPS timing parameters (ADKD 4) are the ones Galileo
57
+ * signed. A tag that does not verify against an authenticated key means
58
+ * the navigation data differ from what was signed — a spoofing or
59
+ * replay symptom. Supported: SHA-256 chains, HMAC-SHA-256 tags and
60
+ * ECDSA P-256 keys — the configuration Galileo has used since the
61
+ * service started; other choices are reported as unsupported.
62
+ */
63
+
64
+ type OsnmaNmaStatus = 'reserved' | 'test' | 'operational' | 'dont-use';
65
+ type OsnmaCpks = 'reserved' | 'nominal' | 'end-of-chain' | 'chain-revoked' | 'new-public-key' | 'public-key-revoked' | 'new-merkle-tree' | 'alert-message';
66
+ /** GST as Galileo week + time of week (s). */
67
+ interface Gst {
68
+ wn: number;
69
+ tow: number;
70
+ }
71
+ /** A TESLA chain whose root key verified against a public key. */
72
+ interface OsnmaChain {
73
+ /** Chain ID (CIDKR). */
74
+ cid: number;
75
+ /** PKID of the public key that verified the DSM-KROOT. */
76
+ pkid: number;
77
+ /** Hash function: 'SHA-256' | 'SHA3-256'. */
78
+ hashFunction: string;
79
+ /** MAC function: 'HMAC-SHA-256' | 'CMAC-AES'. */
80
+ macFunction: string;
81
+ keyBits: number;
82
+ tagBits: number;
83
+ /** MAC look-up table entry (ANNEX C). */
84
+ maclt: number;
85
+ /** Time of applicability GST0 of the KROOT. */
86
+ gst0: Gst;
87
+ /** Whether this library can verify tags of this chain. */
88
+ supported: boolean;
89
+ }
90
+ interface OsnmaTagStats {
91
+ /** Tags whose MAC verified. */
92
+ ok: number;
93
+ /** Tags whose MAC did not verify against an authenticated key. */
94
+ failed: number;
95
+ }
96
+ /** Per-satellite authentication state. */
97
+ interface OsnmaSatellite {
98
+ /** 'E05'… */
99
+ prn: string;
100
+ /** This satellite transmits OSNMA data (non-zero OSNMA field). */
101
+ transmitsOsnma: boolean;
102
+ /** Ephemeris, clock and status (ADKD 0 + slow-MAC ADKD 12). */
103
+ ced: OsnmaTagStats & {
104
+ /** IODnav of the latest authenticated data set (≥ 80 tag bits). */
105
+ authenticatedIodNav: number | null;
106
+ /** GST subframe of the latest tag that completed authentication. */
107
+ lastAuthenticated: Gst | null;
108
+ };
109
+ /** GST-UTC / GST-GPS conversion parameters (ADKD 4). */
110
+ timing: OsnmaTagStats & {
111
+ lastAuthenticated: Gst | null;
112
+ };
113
+ }
114
+ interface OsnmaEvent {
115
+ gst: Gst;
116
+ kind: 'public-key-verified' | 'public-key-rejected' | 'kroot-verified' | 'kroot-rejected' | 'key-rejected' | 'tag-failed' | 'macseq-failed' | 'alert-message' | 'unsupported';
117
+ message: string;
118
+ prn?: string;
119
+ }
120
+ interface OsnmaStatus {
121
+ /** Latest NMA header seen (null before any OSNMA page). */
122
+ nmaStatus: OsnmaNmaStatus | null;
123
+ cid: number | null;
124
+ cpks: OsnmaCpks | null;
125
+ /** Public keys proven against the Merkle root. */
126
+ publicKeys: {
127
+ pkid: number;
128
+ source: 'known' | 'broadcast';
129
+ }[];
130
+ /** TESLA chains with a verified root key. */
131
+ chains: OsnmaChain[];
132
+ /** Chain keys (one per subframe) verified back to a KROOT. */
133
+ keysVerified: number;
134
+ /** Keys that did not hash back to the root (a forged or broken chain). */
135
+ keysRejected: number;
136
+ /** GST of the latest verified TESLA key. */
137
+ lastKey: Gst | null;
138
+ tags: OsnmaTagStats & {
139
+ /** Tags whose key, data or chain is not available yet / any more. */
140
+ unverifiable: number;
141
+ /** Dummy tags (COP = 0) verified. */
142
+ dummy: number;
143
+ };
144
+ satellites: OsnmaSatellite[];
145
+ /** Notable events, oldest first (capped). */
146
+ events: OsnmaEvent[];
147
+ /** OSNMA pages fed (E1-B pages with a non-zero OSNMA field). */
148
+ osnmaPages: number;
149
+ /** MACK messages left unused because the NMA status was "don't use". */
150
+ dontUseMacks: number;
151
+ /** An authenticated OSNMA Alert Message was received: OSNMA stopped. */
152
+ alert: boolean;
153
+ }
154
+ interface OsnmaReceiverOptions {
155
+ /**
156
+ * Merkle tree root(s) (32 bytes each); default {@link OSNMA_MERKLE_ROOT}.
157
+ * During a Merkle tree renewal pass both the old and the new root.
158
+ */
159
+ merkleRoot?: Uint8Array | readonly Uint8Array[];
160
+ /**
161
+ * Public keys known in advance (each checked against the root);
162
+ * default {@link OSNMA_KNOWN_PUBLIC_KEYS}. Pass [] to rely only on
163
+ * keys broadcast in DSM-PKR.
164
+ */
165
+ publicKeys?: readonly OsnmaPublicKeyRecord[];
166
+ }
167
+ declare class OsnmaReceiver {
168
+ private readonly roots;
169
+ /** An authenticated OSNMA Alert Message stopped all processing. */
170
+ private alerted;
171
+ /** Revoked public keys and chains (hex), never to be used again. */
172
+ private readonly revoked;
173
+ private readonly pubKeys;
174
+ private readonly collect;
175
+ private readonly dsms;
176
+ private readonly chains;
177
+ private readonly macks;
178
+ private readonly words;
179
+ private readonly sats;
180
+ private readonly events;
181
+ private nmaHeader;
182
+ private keysVerified;
183
+ private keysRejected;
184
+ private lastKey;
185
+ private tags;
186
+ private osnmaPages;
187
+ private dontUseMacks;
188
+ private latestSf;
189
+ /** Keys already rejected, as `sf:hex` (one event each). */
190
+ private readonly rejectedKeys;
191
+ constructor(opts?: OsnmaReceiverOptions);
192
+ /**
193
+ * Feed one E1-B I/NAV nominal page pair: `page` holds the 114-bit even
194
+ * part (tail removed) followed by the 120-bit odd part, MSB first, as
195
+ * Septentrio's GALRawINAV carries it (CRC already checked by the
196
+ * caller). `wn`/`tow` give the GST of the page's first symbol.
197
+ */
198
+ pushPage(svid: number, wn: number, tow: number, page: Uint8Array): void;
199
+ /** Process anything still buffered (end of a file). */
200
+ flush(): void;
201
+ status(): OsnmaStatus;
202
+ private sat;
203
+ private event;
204
+ private storeWord;
205
+ private prune;
206
+ private closeSubframe;
207
+ private leafOk;
208
+ /**
209
+ * "Don't use" headers announcing a revocation (ICD §5.4.1, §5.5.3):
210
+ * drop the revoked chain or public key and never accept it again.
211
+ */
212
+ private applyRevocations;
213
+ private onDsmBlock;
214
+ private onPkr;
215
+ private onKroot;
216
+ /** F(K) for the key of subframe `sf`: the key of subframe sf − 30. */
217
+ private oneWay;
218
+ private chainFor;
219
+ /** Verify the TESLA key carried in a MACK against the chain. */
220
+ private onKeyFrom;
221
+ private rejectKey;
222
+ private processMacks;
223
+ private verifyTags;
224
+ private onTag;
225
+ /** Latest word of `wt` from `svid` in subframes [sf − 30·cop, sf − 30]. */
226
+ private wordIn;
227
+ /** ADKD 0/12 data: WT1-5 of one IODnav (Annex B.1). */
228
+ private cedData;
229
+ /** ADKD 4 data: WT6 ‖ WT10 timing parameters (Annex B.2). */
230
+ private timingData;
231
+ }
232
+
233
+ /**
234
+ * OSNMA from Septentrio SBF: GALRawINAV (4023) blocks on E1-B carry the
235
+ * nominal I/NAV page pair with its 40-bit OSNMA field.
236
+ */
237
+
238
+ /**
239
+ * Feed one SBF block at offset `b` to `rx` when it is an E1-B
240
+ * GALRawINAV page with a valid CRC. Returns true if a page was fed.
241
+ */
242
+ declare function feedSbfOsnmaBlock(data: Uint8Array, view: DataView, b: number, id: number, len: number, rx: OsnmaReceiver): boolean;
243
+ /** Run OSNMA verification over every GALRawINAV E1-B page of an SBF stream. */
244
+ declare function verifySbfOsnma(data: Uint8Array, opts?: OsnmaReceiverOptions): OsnmaStatus;
245
+
246
+ /**
247
+ * Synchronous SHA-256 (FIPS 180-4) and HMAC-SHA-256 (FIPS 198-1).
248
+ *
249
+ * OSNMA verification runs a TESLA chain of up to a few thousand hashes
250
+ * per key and an HMAC per tag, page by page on a live stream; WebCrypto
251
+ * is asynchronous only, so the library carries its own small, sync
252
+ * implementation (checked against the NIST vectors in the tests).
253
+ */
254
+ /** SHA-256 of the concatenation of `parts`. */
255
+ declare function sha256(...parts: Uint8Array[]): Uint8Array;
256
+ /** HMAC-SHA-256 of `msg` under `key`. */
257
+ declare function hmacSha256(key: Uint8Array, msg: Uint8Array): Uint8Array;
258
+ /** SHA-512 of the concatenation of `parts`. */
259
+ declare function sha512(...parts: Uint8Array[]): Uint8Array;
260
+
261
+ /**
262
+ * Verify an ECDSA P-256/SHA-256 signature `sig` (r ‖ s, 64 bytes) of
263
+ * `msg` under the SEC1-encoded public key `pubKey`.
264
+ */
265
+ declare const p256Verify: (pubKey: Uint8Array, msg: Uint8Array, sig: Uint8Array) => boolean;
266
+ /**
267
+ * Verify an ECDSA P-521/SHA-512 signature `sig` (r ‖ s, 66 bytes each)
268
+ * of `msg` under the SEC1-encoded public key `pubKey` (67 bytes
269
+ * compressed).
270
+ */
271
+ declare const p521Verify: (pubKey: Uint8Array, msg: Uint8Array, sig: Uint8Array) => boolean;
272
+
273
+ export { type Gst, OSNMA_KNOWN_PUBLIC_KEYS, OSNMA_MERKLE_ROOT, type OsnmaChain, type OsnmaCpks, type OsnmaEvent, type OsnmaNmaStatus, type OsnmaPublicKeyRecord, OsnmaReceiver, type OsnmaReceiverOptions, type OsnmaSatellite, type OsnmaStatus, type OsnmaTagStats, feedSbfOsnmaBlock, hmacSha256, merkleLeafOk, p256Verify, p521Verify, sha256, sha512, verifySbfOsnma };
@@ -0,0 +1,273 @@
1
+ /**
2
+ * OSNMA Merkle tree (SIS ICD v1.1 §6.2): the trust anchor that public
3
+ * keys — broadcast in DSM-PKR or loaded from the GSC — are checked
4
+ * against. N = 16 leaves, SHA-256, root x(4,0).
5
+ */
6
+ /**
7
+ * Root of the OSNMA Merkle tree in force since 2025-12-10 (GSC file
8
+ * OSNMA_MerkleTree_20251209100000_newPKID_2.xml, UID MT-D7A51E17…).
9
+ * Per the ICD a tree is renewed "very rarely, typically after more
10
+ * than 10 years", announced 2 years ahead; pass `merkleRoot` to
11
+ * {@link OsnmaReceiver} to use another one.
12
+ */
13
+ declare const OSNMA_MERKLE_ROOT: Uint8Array<ArrayBuffer>;
14
+ /** A public key with the Merkle path that proves it against a root. */
15
+ interface OsnmaPublicKeyRecord {
16
+ /** Public key ID (PKID). */
17
+ pkid: number;
18
+ /** Key type (NPKT): 1 = ECDSA P-256, 3 = ECDSA P-521. */
19
+ npkt: number;
20
+ /** SEC1-compressed public key. */
21
+ key: Uint8Array;
22
+ /** Leaf index i of m_i in the tree (MID). */
23
+ mid: number;
24
+ /** Intermediate nodes x(0,·), x(1,·), x(2,·), x(3,·) along the path. */
25
+ path: Uint8Array[];
26
+ }
27
+ /**
28
+ * The public key in force at the time of writing, PKID 2, as published
29
+ * by the GSC with its Merkle path (leaf m1). It is checked against the
30
+ * root before use, like a broadcast DSM-PKR, so a wrong constant here
31
+ * fails closed.
32
+ */
33
+ declare const OSNMA_KNOWN_PUBLIC_KEYS: readonly OsnmaPublicKeyRecord[];
34
+ /**
35
+ * Check a Merkle leaf m_i = (NPKT ‖ NPKID ‖ NPK) against `root` through
36
+ * the four intermediate nodes of its path (ICD Eq. 12-13, Table 4).
37
+ */
38
+ declare function merkleLeafOk(leaf: Uint8Array, mid: number, path: readonly Uint8Array[], root: Uint8Array): boolean;
39
+
40
+ /**
41
+ * Galileo OSNMA (Open Service Navigation Message Authentication)
42
+ * receiver, after the OSNMA SIS ICD v1.1 (October 2023) and the
43
+ * Receiver Guidelines v1.3.
44
+ *
45
+ * Feed it Galileo E1-B I/NAV nominal page pairs; it reassembles the
46
+ * 40-bit OSNMA field of each page into the per-subframe HKROOT (DSM
47
+ * blocks) and MACK (tags + TESLA key) messages and runs the whole
48
+ * chain of trust:
49
+ *
50
+ * Merkle root ─▶ public key (DSM-PKR, or a known key + its path)
51
+ * ─▶ ECDSA-signed TESLA root key (DSM-KROOT)
52
+ * ─▶ TESLA chain keys (one per subframe, delayed disclosure)
53
+ * ─▶ MAC tags over the satellites' navigation data
54
+ *
55
+ * A tag that verifies proves the satellite's ephemeris/clock (ADKD 0,
56
+ * 12) or GST-UTC/GPS timing parameters (ADKD 4) are the ones Galileo
57
+ * signed. A tag that does not verify against an authenticated key means
58
+ * the navigation data differ from what was signed — a spoofing or
59
+ * replay symptom. Supported: SHA-256 chains, HMAC-SHA-256 tags and
60
+ * ECDSA P-256 keys — the configuration Galileo has used since the
61
+ * service started; other choices are reported as unsupported.
62
+ */
63
+
64
+ type OsnmaNmaStatus = 'reserved' | 'test' | 'operational' | 'dont-use';
65
+ type OsnmaCpks = 'reserved' | 'nominal' | 'end-of-chain' | 'chain-revoked' | 'new-public-key' | 'public-key-revoked' | 'new-merkle-tree' | 'alert-message';
66
+ /** GST as Galileo week + time of week (s). */
67
+ interface Gst {
68
+ wn: number;
69
+ tow: number;
70
+ }
71
+ /** A TESLA chain whose root key verified against a public key. */
72
+ interface OsnmaChain {
73
+ /** Chain ID (CIDKR). */
74
+ cid: number;
75
+ /** PKID of the public key that verified the DSM-KROOT. */
76
+ pkid: number;
77
+ /** Hash function: 'SHA-256' | 'SHA3-256'. */
78
+ hashFunction: string;
79
+ /** MAC function: 'HMAC-SHA-256' | 'CMAC-AES'. */
80
+ macFunction: string;
81
+ keyBits: number;
82
+ tagBits: number;
83
+ /** MAC look-up table entry (ANNEX C). */
84
+ maclt: number;
85
+ /** Time of applicability GST0 of the KROOT. */
86
+ gst0: Gst;
87
+ /** Whether this library can verify tags of this chain. */
88
+ supported: boolean;
89
+ }
90
+ interface OsnmaTagStats {
91
+ /** Tags whose MAC verified. */
92
+ ok: number;
93
+ /** Tags whose MAC did not verify against an authenticated key. */
94
+ failed: number;
95
+ }
96
+ /** Per-satellite authentication state. */
97
+ interface OsnmaSatellite {
98
+ /** 'E05'… */
99
+ prn: string;
100
+ /** This satellite transmits OSNMA data (non-zero OSNMA field). */
101
+ transmitsOsnma: boolean;
102
+ /** Ephemeris, clock and status (ADKD 0 + slow-MAC ADKD 12). */
103
+ ced: OsnmaTagStats & {
104
+ /** IODnav of the latest authenticated data set (≥ 80 tag bits). */
105
+ authenticatedIodNav: number | null;
106
+ /** GST subframe of the latest tag that completed authentication. */
107
+ lastAuthenticated: Gst | null;
108
+ };
109
+ /** GST-UTC / GST-GPS conversion parameters (ADKD 4). */
110
+ timing: OsnmaTagStats & {
111
+ lastAuthenticated: Gst | null;
112
+ };
113
+ }
114
+ interface OsnmaEvent {
115
+ gst: Gst;
116
+ kind: 'public-key-verified' | 'public-key-rejected' | 'kroot-verified' | 'kroot-rejected' | 'key-rejected' | 'tag-failed' | 'macseq-failed' | 'alert-message' | 'unsupported';
117
+ message: string;
118
+ prn?: string;
119
+ }
120
+ interface OsnmaStatus {
121
+ /** Latest NMA header seen (null before any OSNMA page). */
122
+ nmaStatus: OsnmaNmaStatus | null;
123
+ cid: number | null;
124
+ cpks: OsnmaCpks | null;
125
+ /** Public keys proven against the Merkle root. */
126
+ publicKeys: {
127
+ pkid: number;
128
+ source: 'known' | 'broadcast';
129
+ }[];
130
+ /** TESLA chains with a verified root key. */
131
+ chains: OsnmaChain[];
132
+ /** Chain keys (one per subframe) verified back to a KROOT. */
133
+ keysVerified: number;
134
+ /** Keys that did not hash back to the root (a forged or broken chain). */
135
+ keysRejected: number;
136
+ /** GST of the latest verified TESLA key. */
137
+ lastKey: Gst | null;
138
+ tags: OsnmaTagStats & {
139
+ /** Tags whose key, data or chain is not available yet / any more. */
140
+ unverifiable: number;
141
+ /** Dummy tags (COP = 0) verified. */
142
+ dummy: number;
143
+ };
144
+ satellites: OsnmaSatellite[];
145
+ /** Notable events, oldest first (capped). */
146
+ events: OsnmaEvent[];
147
+ /** OSNMA pages fed (E1-B pages with a non-zero OSNMA field). */
148
+ osnmaPages: number;
149
+ /** MACK messages left unused because the NMA status was "don't use". */
150
+ dontUseMacks: number;
151
+ /** An authenticated OSNMA Alert Message was received: OSNMA stopped. */
152
+ alert: boolean;
153
+ }
154
+ interface OsnmaReceiverOptions {
155
+ /**
156
+ * Merkle tree root(s) (32 bytes each); default {@link OSNMA_MERKLE_ROOT}.
157
+ * During a Merkle tree renewal pass both the old and the new root.
158
+ */
159
+ merkleRoot?: Uint8Array | readonly Uint8Array[];
160
+ /**
161
+ * Public keys known in advance (each checked against the root);
162
+ * default {@link OSNMA_KNOWN_PUBLIC_KEYS}. Pass [] to rely only on
163
+ * keys broadcast in DSM-PKR.
164
+ */
165
+ publicKeys?: readonly OsnmaPublicKeyRecord[];
166
+ }
167
+ declare class OsnmaReceiver {
168
+ private readonly roots;
169
+ /** An authenticated OSNMA Alert Message stopped all processing. */
170
+ private alerted;
171
+ /** Revoked public keys and chains (hex), never to be used again. */
172
+ private readonly revoked;
173
+ private readonly pubKeys;
174
+ private readonly collect;
175
+ private readonly dsms;
176
+ private readonly chains;
177
+ private readonly macks;
178
+ private readonly words;
179
+ private readonly sats;
180
+ private readonly events;
181
+ private nmaHeader;
182
+ private keysVerified;
183
+ private keysRejected;
184
+ private lastKey;
185
+ private tags;
186
+ private osnmaPages;
187
+ private dontUseMacks;
188
+ private latestSf;
189
+ /** Keys already rejected, as `sf:hex` (one event each). */
190
+ private readonly rejectedKeys;
191
+ constructor(opts?: OsnmaReceiverOptions);
192
+ /**
193
+ * Feed one E1-B I/NAV nominal page pair: `page` holds the 114-bit even
194
+ * part (tail removed) followed by the 120-bit odd part, MSB first, as
195
+ * Septentrio's GALRawINAV carries it (CRC already checked by the
196
+ * caller). `wn`/`tow` give the GST of the page's first symbol.
197
+ */
198
+ pushPage(svid: number, wn: number, tow: number, page: Uint8Array): void;
199
+ /** Process anything still buffered (end of a file). */
200
+ flush(): void;
201
+ status(): OsnmaStatus;
202
+ private sat;
203
+ private event;
204
+ private storeWord;
205
+ private prune;
206
+ private closeSubframe;
207
+ private leafOk;
208
+ /**
209
+ * "Don't use" headers announcing a revocation (ICD §5.4.1, §5.5.3):
210
+ * drop the revoked chain or public key and never accept it again.
211
+ */
212
+ private applyRevocations;
213
+ private onDsmBlock;
214
+ private onPkr;
215
+ private onKroot;
216
+ /** F(K) for the key of subframe `sf`: the key of subframe sf − 30. */
217
+ private oneWay;
218
+ private chainFor;
219
+ /** Verify the TESLA key carried in a MACK against the chain. */
220
+ private onKeyFrom;
221
+ private rejectKey;
222
+ private processMacks;
223
+ private verifyTags;
224
+ private onTag;
225
+ /** Latest word of `wt` from `svid` in subframes [sf − 30·cop, sf − 30]. */
226
+ private wordIn;
227
+ /** ADKD 0/12 data: WT1-5 of one IODnav (Annex B.1). */
228
+ private cedData;
229
+ /** ADKD 4 data: WT6 ‖ WT10 timing parameters (Annex B.2). */
230
+ private timingData;
231
+ }
232
+
233
+ /**
234
+ * OSNMA from Septentrio SBF: GALRawINAV (4023) blocks on E1-B carry the
235
+ * nominal I/NAV page pair with its 40-bit OSNMA field.
236
+ */
237
+
238
+ /**
239
+ * Feed one SBF block at offset `b` to `rx` when it is an E1-B
240
+ * GALRawINAV page with a valid CRC. Returns true if a page was fed.
241
+ */
242
+ declare function feedSbfOsnmaBlock(data: Uint8Array, view: DataView, b: number, id: number, len: number, rx: OsnmaReceiver): boolean;
243
+ /** Run OSNMA verification over every GALRawINAV E1-B page of an SBF stream. */
244
+ declare function verifySbfOsnma(data: Uint8Array, opts?: OsnmaReceiverOptions): OsnmaStatus;
245
+
246
+ /**
247
+ * Synchronous SHA-256 (FIPS 180-4) and HMAC-SHA-256 (FIPS 198-1).
248
+ *
249
+ * OSNMA verification runs a TESLA chain of up to a few thousand hashes
250
+ * per key and an HMAC per tag, page by page on a live stream; WebCrypto
251
+ * is asynchronous only, so the library carries its own small, sync
252
+ * implementation (checked against the NIST vectors in the tests).
253
+ */
254
+ /** SHA-256 of the concatenation of `parts`. */
255
+ declare function sha256(...parts: Uint8Array[]): Uint8Array;
256
+ /** HMAC-SHA-256 of `msg` under `key`. */
257
+ declare function hmacSha256(key: Uint8Array, msg: Uint8Array): Uint8Array;
258
+ /** SHA-512 of the concatenation of `parts`. */
259
+ declare function sha512(...parts: Uint8Array[]): Uint8Array;
260
+
261
+ /**
262
+ * Verify an ECDSA P-256/SHA-256 signature `sig` (r ‖ s, 64 bytes) of
263
+ * `msg` under the SEC1-encoded public key `pubKey`.
264
+ */
265
+ declare const p256Verify: (pubKey: Uint8Array, msg: Uint8Array, sig: Uint8Array) => boolean;
266
+ /**
267
+ * Verify an ECDSA P-521/SHA-512 signature `sig` (r ‖ s, 66 bytes each)
268
+ * of `msg` under the SEC1-encoded public key `pubKey` (67 bytes
269
+ * compressed).
270
+ */
271
+ declare const p521Verify: (pubKey: Uint8Array, msg: Uint8Array, sig: Uint8Array) => boolean;
272
+
273
+ export { type Gst, OSNMA_KNOWN_PUBLIC_KEYS, OSNMA_MERKLE_ROOT, type OsnmaChain, type OsnmaCpks, type OsnmaEvent, type OsnmaNmaStatus, type OsnmaPublicKeyRecord, OsnmaReceiver, type OsnmaReceiverOptions, type OsnmaSatellite, type OsnmaStatus, type OsnmaTagStats, feedSbfOsnmaBlock, hmacSha256, merkleLeafOk, p256Verify, p521Verify, sha256, sha512, verifySbfOsnma };