vp9_encodeintra.c 7.74 KB
Newer Older
John Koleszar's avatar
John Koleszar committed
1
/*
2
 *  Copyright (c) 2010 The WebM project authors. All Rights Reserved.
John Koleszar's avatar
John Koleszar committed
3
 *
4
 *  Use of this source code is governed by a BSD-style license
5
6
 *  that can be found in the LICENSE file in the root of the source
 *  tree. An additional intellectual property rights grant can be found
7
 *  in the file PATENTS.  All contributing project authors may
8
 *  be found in the AUTHORS file in the root of the source tree.
John Koleszar's avatar
John Koleszar committed
9
10
11
 */

#include "vpx_ports/config.h"
12
#include "vp9_rtcd.h"
13
14
15
16
17
18
#include "vp9_quantize.h"
#include "vp9/common/vp9_reconintra.h"
#include "vp9/common/vp9_reconintra4x4.h"
#include "vp9_encodemb.h"
#include "vp9/common/vp9_invtrans.h"
#include "vp9_encodeintra.h"
John Koleszar's avatar
John Koleszar committed
19
20
21
22
23
24

#if CONFIG_RUNTIME_CPU_DETECT
#define IF_RTCD(x) (x)
#else
#define IF_RTCD(x) NULL
#endif
25

26
int vp9_encode_intra(VP9_COMP *cpi, MACROBLOCK *x, int use_16x16_pred) {
John Koleszar's avatar
John Koleszar committed
27
28
  int i;
  int intra_pred_var = 0;
Paul Wilkins's avatar
Paul Wilkins committed
29
  MB_MODE_INFO * mbmi = &x->e_mbd.mode_info_context->mbmi;
John Koleszar's avatar
John Koleszar committed
30
  (void) cpi;
Tero Rintaluoma's avatar
Tero Rintaluoma committed
31

John Koleszar's avatar
John Koleszar committed
32
  if (use_16x16_pred) {
Paul Wilkins's avatar
Paul Wilkins committed
33
    mbmi->mode = DC_PRED;
34
#if CONFIG_COMP_INTRA_PRED
Paul Wilkins's avatar
Paul Wilkins committed
35
    mbmi->second_mode = (MB_PREDICTION_MODE)(DC_PRED - 1);
36
#endif
Paul Wilkins's avatar
Paul Wilkins committed
37
38
    mbmi->uv_mode = DC_PRED;
    mbmi->ref_frame = INTRA_FRAME;
John Koleszar's avatar
John Koleszar committed
39

40
    vp9_encode_intra16x16mby(x);
John Koleszar's avatar
John Koleszar committed
41
42
43
  } else {
    for (i = 0; i < 16; i++) {
      x->e_mbd.block[i].bmi.as_mode.first = B_DC_PRED;
44
      vp9_encode_intra4x4block(x, i);
Tero Rintaluoma's avatar
Tero Rintaluoma committed
45
    }
John Koleszar's avatar
John Koleszar committed
46
  }
Tero Rintaluoma's avatar
Tero Rintaluoma committed
47

48
  intra_pred_var = vp9_get_mb_ss(x->src_diff);
Tero Rintaluoma's avatar
Tero Rintaluoma committed
49

John Koleszar's avatar
John Koleszar committed
50
  return intra_pred_var;
Tero Rintaluoma's avatar
Tero Rintaluoma committed
51
}
52

53
void vp9_encode_intra4x4block(MACROBLOCK *x, int ib) {
John Koleszar's avatar
John Koleszar committed
54
55
  BLOCKD *b = &x->e_mbd.block[ib];
  BLOCK *be = &x->block[ib];
Deb Mukherjee's avatar
Deb Mukherjee committed
56
  TX_TYPE tx_type;
57

58
59
60
61
#if CONFIG_NEWBINTRAMODES
  b->bmi.as_mode.context = vp9_find_bpred_context(b);
#endif

62
#if CONFIG_COMP_INTRA_PRED
John Koleszar's avatar
John Koleszar committed
63
  if (b->bmi.as_mode.second == (B_PREDICTION_MODE)(B_DC_PRED - 1)) {
64
#endif
65
    vp9_intra4x4_predict(b, b->bmi.as_mode.first, b->predictor);
66
#if CONFIG_COMP_INTRA_PRED
John Koleszar's avatar
John Koleszar committed
67
  } else {
68
    vp9_comp_intra4x4_predict(b, b->bmi.as_mode.first, b->bmi.as_mode.second,
69
                              b->predictor);
John Koleszar's avatar
John Koleszar committed
70
  }
71
#endif
John Koleszar's avatar
John Koleszar committed
72

73
  vp9_subtract_b(be, b, 16);
John Koleszar's avatar
John Koleszar committed
74

Deb Mukherjee's avatar
Deb Mukherjee committed
75
76
  tx_type = get_tx_type(&x->e_mbd, b);
  if (tx_type != DCT_DCT) {
77
    vp9_fht(be->src_diff, 32, be->coeff, tx_type, 4);
78
    vp9_ht_quantize_b_4x4(be, b, tx_type);
79
    vp9_ihtllm_c(b->dqcoeff, b->diff, 32, tx_type, 4);
80
  } else {
81
    x->vp9_short_fdct4x4(be->src_diff, be->coeff, 32);
82
    x->quantize_b_4x4(be, b) ;
83
    vp9_inverse_transform_b_4x4(&x->e_mbd, ib, 32);
84
  }
John Koleszar's avatar
John Koleszar committed
85

86
  vp9_recon_b(b->predictor, b->diff, *(b->base_dst) + b->dst, b->dst_stride);
John Koleszar's avatar
John Koleszar committed
87
88
}

89
void vp9_encode_intra4x4mby(MACROBLOCK *mb) {
John Koleszar's avatar
John Koleszar committed
90
  int i;
John Koleszar's avatar
John Koleszar committed
91

John Koleszar's avatar
John Koleszar committed
92
  for (i = 0; i < 16; i++)
93
    vp9_encode_intra4x4block(mb, i);
John Koleszar's avatar
John Koleszar committed
94
  return;
John Koleszar's avatar
John Koleszar committed
95
96
}

97
void vp9_encode_intra16x16mby(MACROBLOCK *x) {
98
  MACROBLOCKD *xd = &x->e_mbd;
John Koleszar's avatar
John Koleszar committed
99
  BLOCK *b = &x->block[0];
100
  TX_SIZE tx_size = xd->mode_info_context->mbmi.txfm_size;
Deb Mukherjee's avatar
Deb Mukherjee committed
101
  TX_TYPE tx_type;
Paul Wilkins's avatar
Paul Wilkins committed
102

103
#if CONFIG_COMP_INTRA_PRED
104
  if (xd->mode_info_context->mbmi.second_mode == (MB_PREDICTION_MODE)(DC_PRED - 1))
105
#endif
106
    vp9_build_intra_predictors_mby(xd);
107
#if CONFIG_COMP_INTRA_PRED
John Koleszar's avatar
John Koleszar committed
108
  else
109
    vp9_build_comp_intra_predictors_mby(xd);
110
#endif
John Koleszar's avatar
John Koleszar committed
111

112
  vp9_subtract_mby(x->src_diff, *(b->base_src), xd->predictor, b->src_stride);
Paul Wilkins's avatar
Paul Wilkins committed
113

114
  if (tx_size == TX_16X16) {
Deb Mukherjee's avatar
Deb Mukherjee committed
115
116
117
    BLOCKD  *bd = &xd->block[0];
    tx_type = get_tx_type(xd, bd);
    if (tx_type != DCT_DCT) {
118
      vp9_fht(b->src_diff, 32, b->coeff, tx_type, 16);
119
      vp9_quantize_mby_16x16(x);
120
      if (x->optimize)
121
        vp9_optimize_mby_16x16(x);
122
      vp9_ihtllm_c(bd->dqcoeff, bd->diff, 32, tx_type, 16);
123
    } else {
124
125
      vp9_transform_mby_16x16(x);
      vp9_quantize_mby_16x16(x);
126
      if (x->optimize)
127
128
        vp9_optimize_mby_16x16(x);
      vp9_inverse_transform_mby_16x16(xd);
129
130
    }
  } else if (tx_size == TX_8X8) {
131
132
    vp9_transform_mby_8x8(x);
    vp9_quantize_mby_8x8(x);
133
    if (x->optimize)
134
135
      vp9_optimize_mby_8x8(x);
    vp9_inverse_transform_mby_8x8(xd);
136
  } else {
137
138
    vp9_transform_mby_4x4(x);
    vp9_quantize_mby_4x4(x);
139
    if (x->optimize)
140
141
      vp9_optimize_mby_4x4(x);
    vp9_inverse_transform_mby_4x4(xd);
John Koleszar's avatar
John Koleszar committed
142
143
  }

144
  vp9_recon_mby(xd);
John Koleszar's avatar
John Koleszar committed
145
146
}

147
void vp9_encode_intra16x16mbuv(MACROBLOCK *x) {
148
149
150
  MACROBLOCKD *xd = &x->e_mbd;
  TX_SIZE tx_size = xd->mode_info_context->mbmi.txfm_size;

151
#if CONFIG_COMP_INTRA_PRED
152
  if (xd->mode_info_context->mbmi.second_uv_mode == (MB_PREDICTION_MODE)(DC_PRED - 1)) {
Paul Wilkins's avatar
Paul Wilkins committed
153
#endif
154
    vp9_build_intra_predictors_mbuv(xd);
155
#if CONFIG_COMP_INTRA_PRED
John Koleszar's avatar
John Koleszar committed
156
  } else {
157
    vp9_build_comp_intra_predictors_mbuv(xd);
John Koleszar's avatar
John Koleszar committed
158
  }
159
#endif
John Koleszar's avatar
John Koleszar committed
160

161
  vp9_subtract_mbuv(x->src_diff, x->src.u_buffer, x->src.v_buffer,
Jim Bankoski's avatar
Jim Bankoski committed
162
163
                    xd->predictor, x->src.uv_stride);

164
  if (tx_size == TX_4X4) {
165
166
    vp9_transform_mbuv_4x4(x);
    vp9_quantize_mbuv_4x4(x);
167
    if (x->optimize)
168
169
      vp9_optimize_mbuv_4x4(x);
    vp9_inverse_transform_mbuv_4x4(xd);
170
  } else /* 16x16 or 8x8 */ {
171
172
    vp9_transform_mbuv_8x8(x);
    vp9_quantize_mbuv_8x8(x);
173
    if (x->optimize)
174
175
      vp9_optimize_mbuv_8x8(x);
    vp9_inverse_transform_mbuv_8x8(xd);
John Koleszar's avatar
John Koleszar committed
176
177
  }

178
  vp9_recon_intra_mbuv(xd);
John Koleszar's avatar
John Koleszar committed
179
}
Yaowu Xu's avatar
Yaowu Xu committed
180

181
void vp9_encode_intra8x8(MACROBLOCK *x, int ib) {
182
183
  MACROBLOCKD *xd = &x->e_mbd;
  BLOCKD *b = &xd->block[ib];
John Koleszar's avatar
John Koleszar committed
184
185
186
  BLOCK *be = &x->block[ib];
  const int iblock[4] = {0, 1, 4, 5};
  int i;
Deb Mukherjee's avatar
Deb Mukherjee committed
187
  TX_TYPE tx_type;
Yaowu Xu's avatar
Yaowu Xu committed
188

189
#if CONFIG_COMP_INTRA_PRED
John Koleszar's avatar
John Koleszar committed
190
  if (b->bmi.as_mode.second == (MB_PREDICTION_MODE)(DC_PRED - 1)) {
191
#endif
192
    vp9_intra8x8_predict(b, b->bmi.as_mode.first, b->predictor);
193
#if CONFIG_COMP_INTRA_PRED
John Koleszar's avatar
John Koleszar committed
194
  } else {
195
    vp9_comp_intra8x8_predict(b, b->bmi.as_mode.first, b->bmi.as_mode.second,
196
                              b->predictor);
John Koleszar's avatar
John Koleszar committed
197
  }
198
#endif
Yaowu Xu's avatar
Yaowu Xu committed
199

200
  if (xd->mode_info_context->mbmi.txfm_size == TX_8X8) {
201
202
203
    int idx = (ib & 0x02) ? (ib + 2) : ib;

    // generate residual blocks
204
    vp9_subtract_4b_c(be, b, 16);
205

206
    tx_type = get_tx_type(xd, xd->block + idx);
Deb Mukherjee's avatar
Deb Mukherjee committed
207
    if (tx_type != DCT_DCT) {
208
      vp9_fht(be->src_diff, 32, (x->block + idx)->coeff,
Deb Mukherjee's avatar
Deb Mukherjee committed
209
210
                tx_type, 8);
      x->quantize_b_8x8(x->block + idx, xd->block + idx);
211
      vp9_ihtllm_c(xd->block[idx].dqcoeff, xd->block[ib].diff, 32,
Deb Mukherjee's avatar
Deb Mukherjee committed
212
213
                   tx_type, 8);
    } else {
214
      x->vp9_short_fdct8x8(be->src_diff, (x->block + idx)->coeff, 32);
Deb Mukherjee's avatar
Deb Mukherjee committed
215
      x->quantize_b_8x8(x->block + idx, xd->block + idx);
216
      vp9_short_idct8x8(xd->block[idx].dqcoeff, xd->block[ib].diff, 32);
Deb Mukherjee's avatar
Deb Mukherjee committed
217
    }
218
  } else {
219
220
    for (i = 0; i < 4; i++) {
      b = &xd->block[ib + iblock[i]];
221
      be = &x->block[ib + iblock[i]];
222
223
      vp9_subtract_b(be, b, 16);
      x->vp9_short_fdct4x4(be->src_diff, be->coeff, 32);
224
      x->quantize_b_4x4(be, b);
225
      vp9_inverse_transform_b_4x4(xd, ib + iblock[i], 32);
226
227
    }
  }
228
229
230
231

  // reconstruct submacroblock
  for (i = 0; i < 4; i++) {
    b = &xd->block[ib + iblock[i]];
232
    vp9_recon_b_c(b->predictor, b->diff, *(b->base_dst) + b->dst,
233
234
                  b->dst_stride);
  }
Yaowu Xu's avatar
Yaowu Xu committed
235
236
}

237
void vp9_encode_intra8x8mby(MACROBLOCK *x) {
John Koleszar's avatar
John Koleszar committed
238
239
240
  int i, ib;

  for (i = 0; i < 4; i++) {
241
    ib = vp9_i8x8_block[i];
242
    vp9_encode_intra8x8(x, ib);
John Koleszar's avatar
John Koleszar committed
243
  }
Yaowu Xu's avatar
Yaowu Xu committed
244
245
}

246
void vp9_encode_intra_uv4x4(MACROBLOCK *x, int ib,
John Koleszar's avatar
John Koleszar committed
247
248
249
                            int mode, int second) {
  BLOCKD *b = &x->e_mbd.block[ib];
  BLOCK *be = &x->block[ib];
Yaowu Xu's avatar
Yaowu Xu committed
250

251
#if CONFIG_COMP_INTRA_PRED
John Koleszar's avatar
John Koleszar committed
252
  if (second == -1) {
253
#endif
254
    vp9_intra_uv4x4_predict(b, mode, b->predictor);
255
#if CONFIG_COMP_INTRA_PRED
John Koleszar's avatar
John Koleszar committed
256
  } else {
257
    vp9_comp_intra_uv4x4_predict(b, mode, second, b->predictor);
John Koleszar's avatar
John Koleszar committed
258
  }
259
#endif
Yaowu Xu's avatar
Yaowu Xu committed
260

261
  vp9_subtract_b(be, b, 8);
Yaowu Xu's avatar
Yaowu Xu committed
262

263
  x->vp9_short_fdct4x4(be->src_diff, be->coeff, 16);
264
  x->quantize_b_4x4(be, b);
265
  vp9_inverse_transform_b_4x4(&x->e_mbd, ib, 16);
Yaowu Xu's avatar
Yaowu Xu committed
266

267
268
  vp9_recon_uv_b_c(b->predictor, b->diff, *(b->base_dst) + b->dst,
                   b->dst_stride);
Yaowu Xu's avatar
Yaowu Xu committed
269
270
}

271
void vp9_encode_intra8x8mbuv(MACROBLOCK *x) {
John Koleszar's avatar
John Koleszar committed
272
273
  int i, ib, mode, second;
  BLOCKD *b;
274

John Koleszar's avatar
John Koleszar committed
275
  for (i = 0; i < 4; i++) {
276
    ib = vp9_i8x8_block[i];
John Koleszar's avatar
John Koleszar committed
277
278
    b = &x->e_mbd.block[ib];
    mode = b->bmi.as_mode.first;
279
#if CONFIG_COMP_INTRA_PRED
John Koleszar's avatar
John Koleszar committed
280
    second = b->bmi.as_mode.second;
281
#else
John Koleszar's avatar
John Koleszar committed
282
    second = -1;
283
#endif
John Koleszar's avatar
John Koleszar committed
284
    /*u */
285
    vp9_encode_intra_uv4x4(x, i + 16, mode, second);
John Koleszar's avatar
John Koleszar committed
286
    /*v */
287
    vp9_encode_intra_uv4x4(x, i + 20, mode, second);
John Koleszar's avatar
John Koleszar committed
288
  }
Yaowu Xu's avatar
Yaowu Xu committed
289
}