OLD | NEW |
(Empty) | |
| 1 // Copyright 2011 The Go Authors. All rights reserved. |
| 2 // Use of this source code is governed by a BSD-style |
| 3 // license that can be found in the LICENSE file. |
| 4 |
| 5 package vp8 |
| 6 |
| 7 // This file implements decoding DCT/WHT residual coefficients and |
| 8 // reconstructing YCbCr data equal to predicted values plus residuals. |
| 9 // |
| 10 // There are 1*16*16 + 2*8*8 + 1*4*4 coefficients per macroblock: |
| 11 // - 1*16*16 luma DCT coefficients, |
| 12 // - 2*8*8 chroma DCT coefficients, and |
| 13 // - 1*4*4 luma WHT coefficients. |
| 14 // Coefficients are read in lots of 16, and the later coefficients in each lot |
| 15 // are often zero. |
| 16 // |
| 17 // The YCbCr data consists of 1*16*16 luma values and 2*8*8 chroma values, |
| 18 // plus previously decoded values along the top and left borders. The combined |
| 19 // values are laid out as a [1+16+1+8][32]uint8 so that vertically adjacent |
| 20 // samples are 32 bytes apart. In detail, the layout is: |
| 21 // |
| 22 // 0 1 2 3 4 5 6 7 8 9 0 1 2 3 4 5 6 7 8 9 0 1 2 3 4 5 6 7 8 9 0 1 |
| 23 // . . . . . . . a b b b b b b b b b b b b b b b b c c c c . . . .
0 |
| 24 // . . . . . . . d Y Y Y Y Y Y Y Y Y Y Y Y Y Y Y Y . . . . . . . .
1 |
| 25 // . . . . . . . d Y Y Y Y Y Y Y Y Y Y Y Y Y Y Y Y . . . . . . . .
2 |
| 26 // . . . . . . . d Y Y Y Y Y Y Y Y Y Y Y Y Y Y Y Y . . . . . . . .
3 |
| 27 // . . . . . . . d Y Y Y Y Y Y Y Y Y Y Y Y Y Y Y Y c c c c . . . .
4 |
| 28 // . . . . . . . d Y Y Y Y Y Y Y Y Y Y Y Y Y Y Y Y . . . . . . . .
5 |
| 29 // . . . . . . . d Y Y Y Y Y Y Y Y Y Y Y Y Y Y Y Y . . . . . . . .
6 |
| 30 // . . . . . . . d Y Y Y Y Y Y Y Y Y Y Y Y Y Y Y Y . . . . . . . .
7 |
| 31 // . . . . . . . d Y Y Y Y Y Y Y Y Y Y Y Y Y Y Y Y c c c c . . . .
8 |
| 32 // . . . . . . . d Y Y Y Y Y Y Y Y Y Y Y Y Y Y Y Y . . . . . . . .
9 |
| 33 // . . . . . . . d Y Y Y Y Y Y Y Y Y Y Y Y Y Y Y Y . . . . . . . .
10 |
| 34 // . . . . . . . d Y Y Y Y Y Y Y Y Y Y Y Y Y Y Y Y . . . . . . . .
11 |
| 35 // . . . . . . . d Y Y Y Y Y Y Y Y Y Y Y Y Y Y Y Y c c c c . . . .
12 |
| 36 // . . . . . . . d Y Y Y Y Y Y Y Y Y Y Y Y Y Y Y Y . . . . . . . .
13 |
| 37 // . . . . . . . d Y Y Y Y Y Y Y Y Y Y Y Y Y Y Y Y . . . . . . . .
14 |
| 38 // . . . . . . . d Y Y Y Y Y Y Y Y Y Y Y Y Y Y Y Y . . . . . . . .
15 |
| 39 // . . . . . . . d Y Y Y Y Y Y Y Y Y Y Y Y Y Y Y Y . . . . . . . .
16 |
| 40 // . . . . . . . e f f f f f f f f . . . . . . . g h h h h h h h h
17 |
| 41 // . . . . . . . i B B B B B B B B . . . . . . . j R R R R R R R R
18 |
| 42 // . . . . . . . i B B B B B B B B . . . . . . . j R R R R R R R R
19 |
| 43 // . . . . . . . i B B B B B B B B . . . . . . . j R R R R R R R R
20 |
| 44 // . . . . . . . i B B B B B B B B . . . . . . . j R R R R R R R R
21 |
| 45 // . . . . . . . i B B B B B B B B . . . . . . . j R R R R R R R R
22 |
| 46 // . . . . . . . i B B B B B B B B . . . . . . . j R R R R R R R R
23 |
| 47 // . . . . . . . i B B B B B B B B . . . . . . . j R R R R R R R R
24 |
| 48 // . . . . . . . i B B B B B B B B . . . . . . . j R R R R R R R R
25 |
| 49 // |
| 50 // Y, B and R are the reconstructed luma (Y) and chroma (B, R) values. |
| 51 // The Y values are predicted (either as one 16x16 region or 16 4x4 regions) |
| 52 // based on the row above's Y values (some combination of {abc} or {dYC}) and |
| 53 // the column left's Y values (either {ad} or {bY}). Similarly, B and R values |
| 54 // are predicted on the row above and column left of their respective 8x8 |
| 55 // region: {efi} for B, {ghj} for R. |
| 56 // |
| 57 // For uppermost macroblocks (i.e. those with mby == 0), the {abcefgh} values |
| 58 // are initialized to 0x81. Otherwise, they are copied from the bottom row of |
| 59 // the macroblock above. The {c} values are then duplicated from row 0 to rows |
| 60 // 4, 8 and 12 of the ybr workspace. |
| 61 // Similarly, for leftmost macroblocks (i.e. those with mbx == 0), the {adeigj} |
| 62 // values are initialized to 0x7f. Otherwise, they are copied from the right |
| 63 // column of the macroblock to the left. |
| 64 // For the top-left macroblock (with mby == 0 && mbx == 0), {aeg} is 0x81. |
| 65 // |
| 66 // When moving from one macroblock to the next horizontally, the {adeigj} |
| 67 // values can simply be copied from the workspace to itself, shifted by 8 or |
| 68 // 16 columns. When moving from one macroblock to the next vertically, |
| 69 // filtering can occur and hence the row values have to be copied from the |
| 70 // post-filtered image instead of the pre-filtered workspace. |
| 71 |
| 72 const ( |
| 73 bCoeffBase = 1*16*16 + 0*8*8 |
| 74 rCoeffBase = 1*16*16 + 1*8*8 |
| 75 whtCoeffBase = 1*16*16 + 2*8*8 |
| 76 ) |
| 77 |
| 78 const ( |
| 79 ybrYX = 8 |
| 80 ybrYY = 1 |
| 81 ybrBX = 8 |
| 82 ybrBY = 18 |
| 83 ybrRX = 24 |
| 84 ybrRY = 18 |
| 85 ) |
| 86 |
| 87 // prepareYBR prepares the {abcdefghij} elements of ybr. |
| 88 func (d *Decoder) prepareYBR(mbx, mby int) { |
| 89 if mbx == 0 { |
| 90 for y := 0; y < 17; y++ { |
| 91 d.ybr[y][7] = 0x81 |
| 92 } |
| 93 for y := 17; y < 26; y++ { |
| 94 d.ybr[y][7] = 0x81 |
| 95 d.ybr[y][23] = 0x81 |
| 96 } |
| 97 } else { |
| 98 for y := 0; y < 17; y++ { |
| 99 d.ybr[y][7] = d.ybr[y][7+16] |
| 100 } |
| 101 for y := 17; y < 26; y++ { |
| 102 d.ybr[y][7] = d.ybr[y][15] |
| 103 d.ybr[y][23] = d.ybr[y][31] |
| 104 } |
| 105 } |
| 106 if mby == 0 { |
| 107 for x := 7; x < 28; x++ { |
| 108 d.ybr[0][x] = 0x7f |
| 109 } |
| 110 for x := 7; x < 16; x++ { |
| 111 d.ybr[17][x] = 0x7f |
| 112 } |
| 113 for x := 23; x < 32; x++ { |
| 114 d.ybr[17][x] = 0x7f |
| 115 } |
| 116 } else { |
| 117 for i := 0; i < 16; i++ { |
| 118 d.ybr[0][8+i] = d.img.Y[(16*mby-1)*d.img.YStride+16*mbx+
i] |
| 119 } |
| 120 for i := 0; i < 8; i++ { |
| 121 d.ybr[17][8+i] = d.img.Cb[(8*mby-1)*d.img.CStride+8*mbx+
i] |
| 122 } |
| 123 for i := 0; i < 8; i++ { |
| 124 d.ybr[17][24+i] = d.img.Cr[(8*mby-1)*d.img.CStride+8*mbx
+i] |
| 125 } |
| 126 if mbx == d.mbw-1 { |
| 127 for i := 16; i < 20; i++ { |
| 128 d.ybr[0][8+i] = d.img.Y[(16*mby-1)*d.img.YStride
+16*mbx+15] |
| 129 } |
| 130 } else { |
| 131 for i := 16; i < 20; i++ { |
| 132 d.ybr[0][8+i] = d.img.Y[(16*mby-1)*d.img.YStride
+16*mbx+i] |
| 133 } |
| 134 } |
| 135 } |
| 136 for y := 4; y < 16; y += 4 { |
| 137 d.ybr[y][24] = d.ybr[0][24] |
| 138 d.ybr[y][25] = d.ybr[0][25] |
| 139 d.ybr[y][26] = d.ybr[0][26] |
| 140 d.ybr[y][27] = d.ybr[0][27] |
| 141 } |
| 142 } |
| 143 |
| 144 // btou converts a bool to a 0/1 value. |
| 145 func btou(b bool) uint8 { |
| 146 if b { |
| 147 return 1 |
| 148 } |
| 149 return 0 |
| 150 } |
| 151 |
| 152 // pack packs four 0/1 values into four bits of a uint32. |
| 153 func pack(x [4]uint8, shift int) uint32 { |
| 154 u := uint32(x[0])<<0 | uint32(x[1])<<1 | uint32(x[2])<<2 | uint32(x[3])<
<3 |
| 155 return u << uint(shift) |
| 156 } |
| 157 |
| 158 // unpack unpacks four 0/1 values from a four-bit value. |
| 159 var unpack = [16][4]uint8{ |
| 160 {0, 0, 0, 0}, |
| 161 {1, 0, 0, 0}, |
| 162 {0, 1, 0, 0}, |
| 163 {1, 1, 0, 0}, |
| 164 {0, 0, 1, 0}, |
| 165 {1, 0, 1, 0}, |
| 166 {0, 1, 1, 0}, |
| 167 {1, 1, 1, 0}, |
| 168 {0, 0, 0, 1}, |
| 169 {1, 0, 0, 1}, |
| 170 {0, 1, 0, 1}, |
| 171 {1, 1, 0, 1}, |
| 172 {0, 0, 1, 1}, |
| 173 {1, 0, 1, 1}, |
| 174 {0, 1, 1, 1}, |
| 175 {1, 1, 1, 1}, |
| 176 } |
| 177 |
| 178 var ( |
| 179 // The mapping from 4x4 region position to band is specified in section
13.3. |
| 180 bands = [17]uint8{0, 1, 2, 3, 6, 4, 5, 6, 6, 6, 6, 6, 6, 6, 6, 7, 0} |
| 181 // Category probabilties are specified in section 13.2. |
| 182 // Decoding categories 1 and 2 are done inline. |
| 183 cat3456 = [4][12]uint8{ |
| 184 {173, 148, 140, 0, 0, 0, 0, 0, 0, 0, 0, 0}, |
| 185 {176, 155, 140, 135, 0, 0, 0, 0, 0, 0, 0, 0}, |
| 186 {180, 157, 141, 134, 130, 0, 0, 0, 0, 0, 0, 0}, |
| 187 {254, 254, 243, 230, 196, 177, 153, 140, 133, 130, 129, 0}, |
| 188 } |
| 189 // The zigzag order is: |
| 190 // 0 1 5 6 |
| 191 // 2 4 7 12 |
| 192 // 3 8 11 13 |
| 193 // 9 10 14 15 |
| 194 zigzag = [16]uint8{0, 1, 4, 8, 5, 2, 3, 6, 9, 12, 13, 10, 7, 11, 14, 15} |
| 195 ) |
| 196 |
| 197 // parseResiduals4 parses a 4x4 region of residual coefficients, as specified |
| 198 // in section 13.3, and returns a 0/1 value indicating whether there was at |
| 199 // least one non-zero coefficient. |
| 200 // r is the partition to read bits from. |
| 201 // plane and context describe which token probability table to use. context is |
| 202 // either 0, 1 or 2, and equals how many of the macroblock left and macroblock |
| 203 // above have non-zero coefficients. |
| 204 // quant are the DC/AC quantization factors. |
| 205 // skipFirstCoeff is whether the DC coefficient has already been parsed. |
| 206 // coeffBase is the base index of d.coeff to write to. |
| 207 func (d *Decoder) parseResiduals4(r *partition, plane int, context uint8, quant
[2]uint16, skipFirstCoeff bool, coeffBase int) uint8 { |
| 208 prob, n := &d.tokenProb[plane], 0 |
| 209 if skipFirstCoeff { |
| 210 n = 1 |
| 211 } |
| 212 p := prob[bands[n]][context] |
| 213 if !r.readBit(p[0]) { |
| 214 return 0 |
| 215 } |
| 216 for n != 16 { |
| 217 n++ |
| 218 if !r.readBit(p[1]) { |
| 219 p = prob[bands[n]][0] |
| 220 continue |
| 221 } |
| 222 var v uint32 |
| 223 if !r.readBit(p[2]) { |
| 224 v = 1 |
| 225 p = prob[bands[n]][1] |
| 226 } else { |
| 227 if !r.readBit(p[3]) { |
| 228 if !r.readBit(p[4]) { |
| 229 v = 2 |
| 230 } else { |
| 231 v = 3 + r.readUint(p[5], 1) |
| 232 } |
| 233 } else if !r.readBit(p[6]) { |
| 234 if !r.readBit(p[7]) { |
| 235 // Category 1. |
| 236 v = 5 + r.readUint(159, 1) |
| 237 } else { |
| 238 // Category 2. |
| 239 v = 7 + 2*r.readUint(165, 1) + r.readUin
t(145, 1) |
| 240 } |
| 241 } else { |
| 242 // Categories 3, 4, 5 or 6. |
| 243 b1 := r.readUint(p[8], 1) |
| 244 b0 := r.readUint(p[9+b1], 1) |
| 245 cat := 2*b1 + b0 |
| 246 tab := &cat3456[cat] |
| 247 v = 0 |
| 248 for i := 0; tab[i] != 0; i++ { |
| 249 v *= 2 |
| 250 v += r.readUint(tab[i], 1) |
| 251 } |
| 252 v += 3 + (8 << cat) |
| 253 } |
| 254 p = prob[bands[n]][2] |
| 255 } |
| 256 z := zigzag[n-1] |
| 257 c := int32(v) * int32(quant[btou(z > 0)]) |
| 258 if r.readBit(uniformProb) { |
| 259 c = -c |
| 260 } |
| 261 d.coeff[coeffBase+int(z)] = int16(c) |
| 262 if n == 16 || !r.readBit(p[0]) { |
| 263 return 1 |
| 264 } |
| 265 } |
| 266 return 1 |
| 267 } |
| 268 |
| 269 // parseResiduals parses the residuals. |
| 270 func (d *Decoder) parseResiduals(mbx, mby int) { |
| 271 partition := &d.op[mby&(d.nOP-1)] |
| 272 plane := planeY1SansY2 |
| 273 quant := &d.quant[d.segment] |
| 274 |
| 275 // Parse the DC coefficient of each 4x4 luma region. |
| 276 if d.usePredY16 { |
| 277 nz := d.parseResiduals4(partition, planeY2, d.leftMB.nzY16+d.upM
B[mbx].nzY16, quant.y2, false, whtCoeffBase) |
| 278 d.leftMB.nzY16 = nz |
| 279 d.upMB[mbx].nzY16 = nz |
| 280 d.inverseWHT16() |
| 281 plane = planeY1WithY2 |
| 282 } |
| 283 |
| 284 var ( |
| 285 nzDC, nzAC [4]uint8 |
| 286 nzDCMask, nzACMask uint32 |
| 287 coeffBase int |
| 288 ) |
| 289 |
| 290 // Parse the luma coefficients. |
| 291 lnz := unpack[d.leftMB.nzMask&0x0f] |
| 292 unz := unpack[d.upMB[mbx].nzMask&0x0f] |
| 293 for y := 0; y < 4; y++ { |
| 294 nz := lnz[y] |
| 295 for x := 0; x < 4; x++ { |
| 296 nz = d.parseResiduals4(partition, plane, nz+unz[x], quan
t.y1, d.usePredY16, coeffBase) |
| 297 unz[x] = nz |
| 298 nzAC[x] = nz |
| 299 nzDC[x] = btou(d.coeff[coeffBase] != 0) |
| 300 coeffBase += 16 |
| 301 } |
| 302 lnz[y] = nz |
| 303 nzDCMask |= pack(nzDC, y*4) |
| 304 nzACMask |= pack(nzAC, y*4) |
| 305 } |
| 306 lnzMask := pack(lnz, 0) |
| 307 unzMask := pack(unz, 0) |
| 308 |
| 309 // Parse the chroma coefficients. |
| 310 lnz = unpack[d.leftMB.nzMask>>4] |
| 311 unz = unpack[d.upMB[mbx].nzMask>>4] |
| 312 for c := 0; c < 4; c += 2 { |
| 313 for y := 0; y < 2; y++ { |
| 314 nz := lnz[y+c] |
| 315 for x := 0; x < 2; x++ { |
| 316 nz = d.parseResiduals4(partition, planeUV, nz+un
z[x+c], quant.uv, false, coeffBase) |
| 317 unz[x+c] = nz |
| 318 nzAC[y*2+x] = nz |
| 319 nzDC[y*2+x] = btou(d.coeff[coeffBase] != 0) |
| 320 coeffBase += 16 |
| 321 } |
| 322 lnz[y+c] = nz |
| 323 } |
| 324 nzDCMask |= pack(nzDC, 16+c*2) |
| 325 nzACMask |= pack(nzAC, 16+c*2) |
| 326 } |
| 327 lnzMask |= pack(lnz, 4) |
| 328 unzMask |= pack(unz, 4) |
| 329 |
| 330 // Save decoder state. |
| 331 d.leftMB.nzMask = uint8(lnzMask) |
| 332 d.upMB[mbx].nzMask = uint8(unzMask) |
| 333 d.nzDCMask = nzDCMask |
| 334 d.nzACMask = nzACMask |
| 335 } |
| 336 |
| 337 // reconstructMacroblock applies the predictor functions and adds the inverse- |
| 338 // DCT transformed residuals to recover the YCbCr data. |
| 339 func (d *Decoder) reconstructMacroblock(mbx, mby int) { |
| 340 if d.usePredY16 { |
| 341 p := checkTopLeftPred(mbx, mby, d.predY16) |
| 342 predFunc16[p](d, 1, 8) |
| 343 for j := 0; j < 4; j++ { |
| 344 for i := 0; i < 4; i++ { |
| 345 n := 4*j + i |
| 346 y := 4*j + 1 |
| 347 x := 4*i + 8 |
| 348 mask := uint32(1) << uint(n) |
| 349 if d.nzACMask&mask != 0 { |
| 350 d.inverseDCT4(y, x, 16*n) |
| 351 } else if d.nzDCMask&mask != 0 { |
| 352 d.inverseDCT4DCOnly(y, x, 16*n) |
| 353 } |
| 354 } |
| 355 } |
| 356 } else { |
| 357 for j := 0; j < 4; j++ { |
| 358 for i := 0; i < 4; i++ { |
| 359 n := 4*j + i |
| 360 y := 4*j + 1 |
| 361 x := 4*i + 8 |
| 362 predFunc4[d.predY4[j][i]](d, y, x) |
| 363 mask := uint32(1) << uint(n) |
| 364 if d.nzACMask&mask != 0 { |
| 365 d.inverseDCT4(y, x, 16*n) |
| 366 } else if d.nzDCMask&mask != 0 { |
| 367 d.inverseDCT4DCOnly(y, x, 16*n) |
| 368 } |
| 369 } |
| 370 } |
| 371 } |
| 372 p := checkTopLeftPred(mbx, mby, d.predC8) |
| 373 predFunc8[p](d, ybrBY, ybrBX) |
| 374 if d.nzACMask&0x0f0000 != 0 { |
| 375 d.inverseDCT8(ybrBY, ybrBX, bCoeffBase) |
| 376 } else if d.nzDCMask&0x0f0000 != 0 { |
| 377 d.inverseDCT8DCOnly(ybrBY, ybrBX, bCoeffBase) |
| 378 } |
| 379 predFunc8[p](d, ybrRY, ybrRX) |
| 380 if d.nzACMask&0xf00000 != 0 { |
| 381 d.inverseDCT8(ybrRY, ybrRX, rCoeffBase) |
| 382 } else if d.nzDCMask&0xf00000 != 0 { |
| 383 d.inverseDCT8DCOnly(ybrRY, ybrRX, rCoeffBase) |
| 384 } |
| 385 } |
| 386 |
| 387 // reconstruct reconstructs one macroblock. |
| 388 func (d *Decoder) reconstruct(mbx, mby int) { |
| 389 if d.segmentHeader.updateMap { |
| 390 if !d.fp.readBit(d.segmentHeader.prob[0]) { |
| 391 d.segment = int(d.fp.readUint(d.segmentHeader.prob[1], 1
)) |
| 392 } else { |
| 393 d.segment = int(d.fp.readUint(d.segmentHeader.prob[2], 1
)) + 2 |
| 394 } |
| 395 } |
| 396 skip := false |
| 397 if d.useSkipProb { |
| 398 skip = d.fp.readBit(d.skipProb) |
| 399 } |
| 400 // Prepare the workspace. |
| 401 for i := range d.coeff { |
| 402 d.coeff[i] = 0 |
| 403 } |
| 404 d.prepareYBR(mbx, mby) |
| 405 // Parse the predictor modes. |
| 406 d.usePredY16 = d.fp.readBit(145) |
| 407 if d.usePredY16 { |
| 408 d.parsePredModeY16(mbx) |
| 409 } else { |
| 410 d.parsePredModeY4(mbx) |
| 411 } |
| 412 d.parsePredModeC8() |
| 413 // Parse the residuals. |
| 414 if !skip { |
| 415 d.parseResiduals(mbx, mby) |
| 416 } else { |
| 417 if d.usePredY16 { |
| 418 d.leftMB.nzY16 = 0 |
| 419 d.upMB[mbx].nzY16 = 0 |
| 420 } |
| 421 d.leftMB.nzMask = 0 |
| 422 d.upMB[mbx].nzMask = 0 |
| 423 d.nzDCMask = 0 |
| 424 d.nzACMask = 0 |
| 425 } |
| 426 // Reconstruct the YCbCr data and copy it to the image. |
| 427 d.reconstructMacroblock(mbx, mby) |
| 428 for i, y := (mby*d.img.YStride+mbx)*16, 0; y < 16; i, y = i+d.img.YStrid
e, y+1 { |
| 429 copy(d.img.Y[i:i+16], d.ybr[ybrYY+y][ybrYX:ybrYX+16]) |
| 430 } |
| 431 for i, y := (mby*d.img.CStride+mbx)*8, 0; y < 8; i, y = i+d.img.CStride,
y+1 { |
| 432 copy(d.img.Cb[i:i+8], d.ybr[ybrBY+y][ybrBX:ybrBX+8]) |
| 433 copy(d.img.Cr[i:i+8], d.ybr[ybrRY+y][ybrRX:ybrRX+8]) |
| 434 } |
| 435 } |
OLD | NEW |