nx_jpeg_dequant_test.nx source
↩ module page · 122 lines · 4375 B
1// nx_jpeg_dequant_test.nx -- KAT for dequant + un-zigzag composer.
2//
3// Construction:
4// zz_coeffs[k] = k (0, 1, 2, ..., 63)
5// quant_zz[k] = k + 1 (1, 2, 3, ..., 64)
6// natural[un_zigzag[k]] = zz_coeffs[k] * quant_zz[k] = k * (k + 1)
7//
8// Cross-check against the published un_zigzag table for the first
9// few positions:
10// k=0 -> nat[0] = 0 * 1 = 0
11// k=1 -> nat[1] = 1 * 2 = 2
12// k=2 -> nat[8] = 2 * 3 = 6
13// k=3 -> nat[16] = 3 * 4 = 12
14// k=4 -> nat[9] = 4 * 5 = 20
15// k=5 -> nat[2] = 5 * 6 = 30
16// ...
17//
18// Also: end-to-end composition with the entropy decoder's output
19// shape (zero-padded zig-zag block) yields a sparse natural block
20// at the expected natural positions.
21//
22// expect_exit: 0
23// license_tier: ORIGINAL
24
25import "nx_syscalls.nx"
26import "nx_jpeg_zigzag.nx"
27import "nx_jpeg_dequant.nx"
28
29func _fail(n: i64) -> i64 {
30 let b: *u8 = sys_mmap(16)
31 b[0]=0x46; b[1]=0x41; b[2]=0x49; b[3]=0x4C; b[4]=0x3D
32 sys_write(2, b, 5)
33 var x: i64 = n
34 if x < 0 { let m: *u8 = sys_mmap(4); m[0]=0x2D; sys_write(2, m, 1); x = 0 - x }
35 if x == 0 { let z: *u8 = sys_mmap(4); z[0]=0x30; sys_write(2, z, 1) }
36 else {
37 let buf: *u8 = sys_mmap(16)
38 var pos: i64 = 0
39 while x > 0 { buf[pos] = (0x30 + (x % 10)) as u8; x = x / 10; pos = pos + 1 }
40 let out: *u8 = sys_mmap(16)
41 var i: i64 = 0
42 while i < pos { out[i] = buf[pos - 1 - i]; i = i + 1 }
43 sys_write(2, out, pos)
44 }
45 let nl: *u8 = sys_mmap(4); nl[0]=0x0A; sys_write(2, nl, 1)
46 return 0
47}
48
49func main() -> i64 {
50 let table: *i64 = sys_mmap(64 * 8) as *i64
51 nx_jpeg_zigzag_inverse_table(table)
52
53 // ============================================================
54 // Section A: full sweep. Each zig-zag position k holds k, each
55 // quantization value holds (k+1); product = k * (k+1) at natural
56 // position un_zigzag[k].
57 // ============================================================
58 let zz: *i64 = sys_mmap(64 * 8) as *i64
59 let quant: *i64 = sys_mmap(64 * 8) as *i64
60 let nat: *i64 = sys_mmap(64 * 8) as *i64
61 var k: i64 = 0
62 while k < 64 {
63 zz[k] = k
64 quant[k] = k + 1
65 nat[k] = 0 // zero-init so we can confirm WRITES happened
66 k = k + 1
67 }
68 nx_jpeg_dequant_un_zigzag(zz, quant, nat)
69
70 k = 0
71 while k < 64 {
72 let expected: i64 = k * (k + 1)
73 let got: i64 = nat[table[k]]
74 if got != expected { _fail(1 + k); return 1 }
75 k = k + 1
76 }
77
78 // ============================================================
79 // Section B: DC-only block (typical from EOB-right-after-DC
80 // entropy output). zz[0] != 0, rest zero. natural should
81 // have natural[0] = zz[0] * quant[0], rest zero.
82 // ============================================================
83 k = 0
84 while k < 64 { zz[k] = 0; quant[k] = 5; nat[k] = 0; k = k + 1 }
85 zz[0] = 7
86 nx_jpeg_dequant_un_zigzag(zz, quant, nat)
87 if nat[0] != 35 { _fail(70); return 70 }
88 k = 1
89 while k < 64 {
90 if nat[k] != 0 { _fail(71); return 71 }
91 k = k + 1
92 }
93
94 // ============================================================
95 // Section C: AC-at-zz[1] block. zz[1] is the second zig-zag
96 // coefficient; un_zigzag[1] = 1 (i.e., natural-position 1, the
97 // "AC top-right of DC" in row-major). Quant[1] = 2.
98 // zz[1] = 9; natural[1] should be 18, all others 0.
99 // ============================================================
100 k = 0
101 while k < 64 { zz[k] = 0; quant[k] = 2; nat[k] = 0; k = k + 1 }
102 zz[1] = 9
103 nx_jpeg_dequant_un_zigzag(zz, quant, nat)
104 if nat[1] != 18 { _fail(80); return 80 }
105 if nat[0] != 0 { _fail(81); return 81 }
106
107 // ============================================================
108 // Section D: AC-at-zz[2] -> natural-position 8 (start of row 1).
109 // ============================================================
110 k = 0
111 while k < 64 { zz[k] = 0; quant[k] = 3; nat[k] = 0; k = k + 1 }
112 zz[2] = 4
113 nx_jpeg_dequant_un_zigzag(zz, quant, nat)
114 if nat[8] != 12 { _fail(90); return 90 }
115 if nat[0] != 0 { _fail(91); return 91 }
116 if nat[1] != 0 { _fail(92); return 92 }
117
118 let pass: *u8 = sys_mmap(16)
119 pass[0]=0x50; pass[1]=0x41; pass[2]=0x53; pass[3]=0x53; pass[4]=0x0A
120 sys_write(1, pass, 5)
121 return 0
122}