@@ -198,8 +198,8 @@ static void intra_filter_reference(
198
198
refs -> filtered_initialized = true;
199
199
}
200
200
201
- const int_fast8_t ref_width = 2 * (1 << log2_width ) + 1 ;
202
- const int_fast8_t ref_height = 2 * (1 << log2_height ) + 1 ;
201
+ const int_fast16_t ref_width = 2 * (1 << ( log2_width ) ) + 1 ;
202
+ const int_fast16_t ref_height = 2 * (1 << ( log2_height ) ) + 1 ;
203
203
uvg_intra_ref * ref = & refs -> ref ;
204
204
uvg_intra_ref * filtered_ref = & refs -> filtered_ref ;
205
205
@@ -208,15 +208,15 @@ static void intra_filter_reference(
208
208
filtered_ref -> top [0 ] = filtered_ref -> left [0 ];
209
209
210
210
// Top to bottom
211
- for (int_fast8_t y = 1 ; y < ref_height - 1 ; ++ y ) {
211
+ for (int_fast16_t y = 1 ; y < ref_height - 1 ; ++ y ) {
212
212
uvg_pixel * p = & ref -> left [y ];
213
213
filtered_ref -> left [y ] = (p [-1 ] + 2 * p [0 ] + p [1 ] + 2 ) >> 2 ;
214
214
}
215
215
// Bottom left (not filtered)
216
216
filtered_ref -> left [ref_height - 1 ] = ref -> left [ref_height - 1 ];
217
217
218
218
// Left to right
219
- for (int_fast8_t x = 1 ; x < ref_width - 1 ; ++ x ) {
219
+ for (int_fast16_t x = 1 ; x < ref_width - 1 ; ++ x ) {
220
220
uvg_pixel * p = & ref -> top [x ];
221
221
filtered_ref -> top [x ] = (p [-1 ] + 2 * p [0 ] + p [1 ] + 2 ) >> 2 ;
222
222
}
@@ -713,7 +713,16 @@ static void intra_predict_regular(
713
713
}
714
714
715
715
if (used_ref == & refs -> filtered_ref && !refs -> filtered_initialized ) {
716
- intra_filter_reference (log2_width , log2_height , refs );
716
+ int temp_log2_width = log2_width ;
717
+ int temp_log2_height = log2_height ;
718
+ if (color == COLOR_Y && isp_mode == ISP_MODE_NO_ISP ) {
719
+ temp_log2_width = cur_cu -> log2_width ;
720
+ temp_log2_height = cur_cu -> log2_height ;
721
+ } else if (color != COLOR_Y ) {
722
+ temp_log2_width = cur_cu -> log2_chroma_width ;
723
+ temp_log2_height = cur_cu -> log2_chroma_height ;
724
+ }
725
+ intra_filter_reference (temp_log2_width , temp_log2_height , refs );
717
726
}
718
727
719
728
if (mode == 0 ) {
@@ -780,7 +789,6 @@ void uvg_intra_build_reference_any(
780
789
781
790
const uvg_pixel dc_val = 1 << (UVG_BIT_DEPTH - 1 ); //TODO: add used bitdepth as a variable
782
791
const int is_chroma = color != COLOR_Y ? 1 : 0 ;
783
- const int is_dual_tree = is_chroma && state -> encoder_control -> cfg .dual_tree && state -> frame -> is_irap ;
784
792
785
793
// Get multi ref index from CU under prediction or reconstrcution. Do not use MRL if not luma
786
794
const uint8_t multi_ref_index = !is_chroma ? multi_ref_idx : 0 ;
@@ -799,7 +807,7 @@ void uvg_intra_build_reference_any(
799
807
// Init pointers to LCUs reconstruction buffers, such that index 0 refers to block coordinate 0.
800
808
const uvg_pixel * left_ref ;
801
809
bool extra_ref = false;
802
- // On the left LCU edge, if left neighboring LCU is available,
810
+ // On the left LCU edge, if left neighboring LCU is available,
803
811
// left_ref needs to point to correct extra reference line if MRL is used.
804
812
if (luma_px -> x > 0 && lcu_px .x == 0 && multi_ref_index != 0 ) {
805
813
left_ref = & extra_ref_lines [multi_ref_index * 128 ];
@@ -836,6 +844,9 @@ void uvg_intra_build_reference_any(
836
844
left_stride = 1 ;
837
845
}
838
846
847
+ const int log2_ratio = log2_width - log2_height ;
848
+ int s = MAX (0 , - log2_ratio );
849
+ int mrl_extension = (multi_ref_index << s ) + (height << s ) + 2 ;
839
850
// Generate left reference.
840
851
if (luma_px -> x > 0 ) {
841
852
// Get the number of reference pixels based on the PU coordinate within the LCU.
@@ -856,7 +867,7 @@ void uvg_intra_build_reference_any(
856
867
857
868
// Limit the number of available pixels based on block size and dimensions
858
869
// of the picture.
859
- px_available_left = MIN (px_available_left , cu_height * 2 + multi_ref_index );
870
+ px_available_left = MIN (px_available_left , cu_height + pu_loc -> height );
860
871
px_available_left = MIN (px_available_left , (pic_px -> y - luma_px -> y ) >> is_chroma );
861
872
862
873
// Copy pixels from coded CUs.
@@ -869,15 +880,17 @@ void uvg_intra_build_reference_any(
869
880
870
881
// If first isp split, take samples as if it were normal square block
871
882
int tmp_h = is_first_isp_block ? cu_height * 2 : (isp_mode ? cu_height + height : height * 2 );
872
- for (int i = px_available_left ; i < tmp_h + multi_ref_index * 2 ; ++ i ) {
883
+ int total_height = MIN (tmp_h + mrl_extension , INTRA_REF_LENGTH );
884
+ for (int i = px_available_left ; i < total_height ; ++ i ) {
873
885
out_left_ref [i + 1 + multi_ref_index ] = nearest_pixel ;
874
886
}
875
887
} else {
876
888
// If we are on the left edge, extend the first pixel of the top row.
877
889
uvg_pixel nearest_pixel = luma_px -> y > 0 ? top_border [0 ] : dc_val ;
878
890
// If first isp split, take samples as if it were normal square block
879
891
int tmp_h = is_first_isp_block ? cu_height * 2 : (isp_mode ? cu_height + height : height * 2 );
880
- for (int i = 0 ; i < tmp_h + multi_ref_index ; i ++ ) {
892
+ int total_height = MIN (tmp_h + mrl_extension , INTRA_REF_LENGTH );
893
+ for (int i = 0 ; i < total_height ; i ++ ) {
881
894
// Reserve space for top left reference
882
895
out_left_ref [i + 1 + multi_ref_index ] = nearest_pixel ;
883
896
}
@@ -899,9 +912,22 @@ void uvg_intra_build_reference_any(
899
912
else if (px .x == 0 ) {
900
913
// LCU left border case
901
914
uvg_pixel * top_left_corner = & extra_ref_lines [multi_ref_index * 128 ];
902
- for (int i = 0 ; i <= multi_ref_index ; ++ i ) {
903
- out_left_ref [i ] = left_border [(i - 1 - multi_ref_index ) * left_stride ];
904
- out_top_ref [i ] = top_left_corner [(128 * - i ) + MAX_REF_LINE_IDX - 1 - multi_ref_index ];
915
+ switch (multi_ref_index ) {
916
+ case 0 :
917
+ out_left_ref [0 ] = left_border [(-1 ) * left_stride ];
918
+ out_top_ref [0 ] = top_left_corner [MAX_REF_LINE_IDX - 1 ];
919
+ break ;
920
+ case 1 :
921
+ for (int i = 0 ; i <= 1 ; ++ i ) {
922
+ out_left_ref [i ] = left_border [(i - 1 - 1 ) * left_stride ];
923
+ out_top_ref [i ] = top_left_corner [(128 * - i ) + MAX_REF_LINE_IDX - 1 - 1 ];
924
+ } break ;
925
+ case 2 :
926
+ for (int i = 0 ; i <= 2 ; ++ i ) {
927
+ out_left_ref [i ] = left_border [(i - 1 - 2 ) * left_stride ];
928
+ out_top_ref [i ] = top_left_corner [(128 * - i ) + MAX_REF_LINE_IDX - 1 - 2 ];
929
+ } break ;
930
+ default : break ;
905
931
}
906
932
}
907
933
else if (px .y == 0 ) {
@@ -911,9 +937,23 @@ void uvg_intra_build_reference_any(
911
937
}
912
938
else {
913
939
// Inner case
914
- for (int i = 0 ; i <= multi_ref_index ; ++ i ) {
915
- out_left_ref [i ] = left_border [(i - 1 - multi_ref_index ) * left_stride ];
916
- out_top_ref [i ] = top_border [i - 1 - multi_ref_index ];
940
+ switch (multi_ref_index ) {
941
+ case 0 :
942
+ for (int i = 0 ; i <= 0 ; ++ i ) {
943
+ out_left_ref [i ] = left_border [(i - 1 - 0 ) * left_stride ];
944
+ out_top_ref [i ] = top_border [i - 1 - 0 ];
945
+ } break ;
946
+ case 1 :
947
+ for (int i = 0 ; i <= 1 ; ++ i ) {
948
+ out_left_ref [i ] = left_border [(i - 1 - 1 ) * left_stride ];
949
+ out_top_ref [i ] = top_border [i - 1 - 1 ];
950
+ } break ;
951
+ case 2 :
952
+ for (int i = 0 ; i <= 2 ; ++ i ) {
953
+ out_left_ref [i ] = left_border [(i - 1 - 2 ) * left_stride ];
954
+ out_top_ref [i ] = top_border [i - 1 - 2 ];
955
+ } break ;
956
+ default : break ;
917
957
}
918
958
}
919
959
}
@@ -927,10 +967,22 @@ void uvg_intra_build_reference_any(
927
967
else if (px .x == 0 ) {
928
968
// Picture left border case. Reference pixel cannot be taken from outside LCU border
929
969
uvg_pixel nearest = out_left_ref [1 + multi_ref_index ];
930
- for (int i = 0 ; i <= multi_ref_index ; ++ i ) {
931
- out_left_ref [i ] = nearest ;
932
- out_top_ref [i ] = nearest ;
970
+ switch (multi_ref_index ) {
971
+ case 2 :
972
+ out_left_ref [2 ] = nearest ;
973
+ out_top_ref [2 ] = nearest ;
974
+ // Fall through
975
+ case 1 :
976
+ out_left_ref [1 ] = nearest ;
977
+ out_top_ref [1 ] = nearest ;
978
+ // Fall through
979
+ case 0 :
980
+ out_left_ref [0 ] = nearest ;
981
+ out_top_ref [0 ] = nearest ;
982
+ break ;
983
+ default : break ;
933
984
}
985
+
934
986
}
935
987
else {
936
988
// Picture top border case. Multi ref will be 0.
@@ -961,6 +1013,8 @@ void uvg_intra_build_reference_any(
961
1013
962
1014
// Generate top reference.
963
1015
int px_available_top ;
1016
+ s = MAX (0 , log2_ratio );
1017
+ mrl_extension = (multi_ref_index << s ) + (width << s ) + 2 ;
964
1018
if (luma_px -> y > 0 ) {
965
1019
// Get the number of reference pixels based on the PU coordinate within the LCU.
966
1020
if (isp_mode && !is_first_isp_block && !is_chroma ) {
@@ -976,10 +1030,10 @@ void uvg_intra_build_reference_any(
976
1030
const int num_cus = uvg_count_available_edge_cus (cu_loc , lcu , false);
977
1031
px_available_top = !is_chroma ? num_cus * 4 : num_cus * 2 ;
978
1032
}
979
-
1033
+
980
1034
// Limit the number of available pixels based on block size and dimensions
981
1035
// of the picture.
982
- px_available_top = MIN (px_available_top , cu_width * 2 + multi_ref_index );
1036
+ px_available_top = MIN (px_available_top , cu_width + pu_loc -> width );
983
1037
px_available_top = MIN (px_available_top , (pic_px -> x - luma_px -> x ) >> is_chroma );
984
1038
985
1039
// Copy all the pixels we can.
@@ -991,7 +1045,8 @@ void uvg_intra_build_reference_any(
991
1045
992
1046
// If first isp split, take samples as if it were normal square block
993
1047
int tmp_w = is_first_isp_block ? cu_width * 2 : (isp_mode ? cu_width + width : width * 2 );
994
- for (int i = px_available_top ; i < tmp_w + multi_ref_index * 2 ; ++ i ) {
1048
+ int total_width = MIN (tmp_w + mrl_extension , INTRA_REF_LENGTH );
1049
+ for (int i = px_available_top ; i < total_width ; ++ i ) {
995
1050
out_top_ref [i + 1 + multi_ref_index ] = nearest_pixel ;
996
1051
}
997
1052
} else {
@@ -1000,7 +1055,8 @@ void uvg_intra_build_reference_any(
1000
1055
1001
1056
// If first isp split, take samples as if it were normal square block
1002
1057
int tmp_w = is_first_isp_block ? cu_width * 2 : (isp_mode ? cu_width + width : width * 2 );
1003
- for (int i = 0 ; i < tmp_w + multi_ref_index * 2 ; i ++ ) {
1058
+ int total_width = MIN (tmp_w + mrl_extension , INTRA_REF_LENGTH );
1059
+ for (int i = 0 ; i < total_width ; i ++ ) {
1004
1060
out_top_ref [i + 1 ] = nearest_pixel ;
1005
1061
}
1006
1062
}
@@ -1111,9 +1167,22 @@ void uvg_intra_build_reference_inner(
1111
1167
else if (px .x == 0 ) {
1112
1168
// LCU left border case
1113
1169
uvg_pixel * top_left_corner = & extra_ref_lines [multi_ref_index * 128 ];
1114
- for (int i = 0 ; i <= multi_ref_index ; ++ i ) {
1115
- out_left_ref [i ] = left_border [(i - 1 - multi_ref_index ) * left_stride ];
1116
- out_top_ref [i ] = top_left_corner [(128 * - i ) + MAX_REF_LINE_IDX - 1 - multi_ref_index ];
1170
+ switch (multi_ref_index ) {
1171
+ case 0 :
1172
+ out_left_ref [0 ] = left_border [(-1 ) * left_stride ];
1173
+ out_top_ref [0 ] = top_left_corner [MAX_REF_LINE_IDX - 1 ];
1174
+ break ;
1175
+ case 1 :
1176
+ for (int i = 0 ; i <= 1 ; ++ i ) {
1177
+ out_left_ref [i ] = left_border [(i - 1 - 1 ) * left_stride ];
1178
+ out_top_ref [i ] = top_left_corner [(128 * - i ) + MAX_REF_LINE_IDX - 1 - 1 ];
1179
+ } break ;
1180
+ case 2 :
1181
+ for (int i = 0 ; i <= 2 ; ++ i ) {
1182
+ out_left_ref [i ] = left_border [(i - 1 - 2 ) * left_stride ];
1183
+ out_top_ref [i ] = top_left_corner [(128 * - i ) + MAX_REF_LINE_IDX - 1 - 2 ];
1184
+ } break ;
1185
+ default : break ;
1117
1186
}
1118
1187
}
1119
1188
else if (px .y == 0 ) {
@@ -1123,9 +1192,23 @@ void uvg_intra_build_reference_inner(
1123
1192
}
1124
1193
else {
1125
1194
// Inner case
1126
- for (int i = 0 ; i <= multi_ref_index ; ++ i ) {
1127
- out_left_ref [i ] = left_border [(i - 1 - multi_ref_index ) * left_stride ];
1128
- out_top_ref [i ] = top_border [i - 1 - multi_ref_index ];
1195
+ switch (multi_ref_index ) {
1196
+ case 0 :
1197
+ for (int i = 0 ; i <= 0 ; ++ i ) {
1198
+ out_left_ref [i ] = left_border [(i - 1 - 0 ) * left_stride ];
1199
+ out_top_ref [i ] = top_border [i - 1 - 0 ];
1200
+ } break ;
1201
+ case 1 :
1202
+ for (int i = 0 ; i <= 1 ; ++ i ) {
1203
+ out_left_ref [i ] = left_border [(i - 1 - 1 ) * left_stride ];
1204
+ out_top_ref [i ] = top_border [i - 1 - 1 ];
1205
+ } break ;
1206
+ case 2 :
1207
+ for (int i = 0 ; i <= 2 ; ++ i ) {
1208
+ out_left_ref [i ] = left_border [(i - 1 - 2 ) * left_stride ];
1209
+ out_top_ref [i ] = top_border [i - 1 - 2 ];
1210
+ } break ;
1211
+ default : break ;
1129
1212
}
1130
1213
}
1131
1214
}
@@ -1167,14 +1250,15 @@ void uvg_intra_build_reference_inner(
1167
1250
1168
1251
// Limit the number of available pixels based on block size and dimensions
1169
1252
// of the picture.
1170
- px_available_left = MIN (px_available_left , cu_height * 2 );
1253
+ px_available_left = MIN (px_available_left , cu_height + pu_loc -> height );
1254
+ // if (is_first_isp_block && isp_mode == ISP_MODE_HOR && px_available_left == cu_height * 2) px_available_left -= (pu_loc->height);
1171
1255
px_available_left = MIN (px_available_left , (pic_px -> y - luma_px -> y ) >> is_chroma );
1172
1256
1173
1257
// Copy pixels from coded CUs.
1174
1258
int i = multi_ref_index ; // Offset by multi_ref_index
1175
1259
1176
1260
// Do different loop for heights smaller than 4 (possible for some ISP splits)
1177
- if (px .y % 4 != 0 || px_available_left < 4 ) {
1261
+ if (px .y % 4 != 0 || px_available_left % 4 != 0 ) {
1178
1262
do {
1179
1263
out_left_ref [i + 1 ] = left_border [(i + 0 - multi_ref_index ) * left_stride ];
1180
1264
i += 1 ;
@@ -1194,20 +1278,18 @@ void uvg_intra_build_reference_inner(
1194
1278
uvg_pixel nearest_pixel = out_left_ref [i ];
1195
1279
1196
1280
// If first isp split, take samples as if it were normal square block
1281
+ const int log2_ratio = log2_width - log2_height ;
1282
+ int s = MAX (0 , - log2_ratio );
1283
+ int mrl_extension = ((multi_ref_index + 0 ) << s ) + (height << s ) + 2 ;
1197
1284
int tmp_h = is_first_isp_block ? cu_height * 2 : (isp_mode ? cu_height + height : height * 2 );
1198
- for (; i < tmp_h ; i += 4 ) {
1285
+ int total_height = MIN (tmp_h + mrl_extension , INTRA_REF_LENGTH - 2 );
1286
+ for (; i < total_height ; i += 4 ) {
1199
1287
out_left_ref [i + 1 ] = nearest_pixel ;
1200
1288
out_left_ref [i + 2 ] = nearest_pixel ;
1201
1289
out_left_ref [i + 3 ] = nearest_pixel ;
1202
1290
out_left_ref [i + 4 ] = nearest_pixel ;
1203
1291
}
1204
1292
1205
- // Extend for MRL
1206
- if (multi_ref_index ) {
1207
- for (; i < height * 2 + multi_ref_index ; ++ i ) {
1208
- out_left_ref [i + 1 ] = nearest_pixel ;
1209
- }
1210
- }
1211
1293
1212
1294
// Generate top reference.
1213
1295
@@ -1229,24 +1311,28 @@ void uvg_intra_build_reference_inner(
1229
1311
1230
1312
// Limit the number of available pixels based on block size and dimensions
1231
1313
// of the picture.
1232
- px_available_top = MIN (px_available_top , cu_width * 2 + multi_ref_index );
1314
+ px_available_top = MIN (px_available_top , cu_width + pu_loc -> width );
1315
+ //if (is_first_isp_block && isp_mode == ISP_MODE_VER && px_available_top == cu_width * 2) px_available_top -= MIN(pu_loc->width, 4);
1233
1316
px_available_top = MIN (px_available_top , (pic_px -> x - luma_px -> x ) >> is_chroma );
1234
1317
1235
- if (entropy_sync && px .y == 0 ) px_available_top = MIN (px_available_top , ((LCU_WIDTH >> is_chroma ) - px .x ) - 1 );
1318
+ if (entropy_sync && px .y == 0 ) px_available_top = MIN (px_available_top , ((LCU_WIDTH >> is_chroma ) - px .x ));
1236
1319
1237
1320
// Copy all the pixels we can.
1238
1321
i = 0 ;
1239
1322
do {
1240
- memcpy (out_top_ref + i + 1 + multi_ref_index , top_border + i , 4 * sizeof (uvg_pixel ));
1241
- i += 4 ;
1323
+ memcpy (out_top_ref + i + 1 + multi_ref_index , top_border + i , sizeof (uvg_pixel ));
1324
+ i += 1 ;
1242
1325
} while (i < px_available_top );
1243
1326
1244
1327
// Extend the last pixel for the rest of the reference values.
1245
1328
nearest_pixel = out_top_ref [i + multi_ref_index ];
1246
1329
1247
1330
// If first isp split, take samples as if it were normal square block
1331
+ s = MAX (0 , - log2_ratio );
1332
+ mrl_extension = ((multi_ref_index + 0 ) << s ) + (width << s ) + 2 ;
1248
1333
int tmp_w = is_first_isp_block ? cu_width * 2 : (isp_mode ? cu_width + width : width * 2 );
1249
- for (; i < tmp_w + (multi_ref_index * 2 ); i += 4 ) {
1334
+ int total_width = MIN (tmp_w + mrl_extension , INTRA_REF_LENGTH - 2 );
1335
+ for (; i < total_width ; i += 4 ) {
1250
1336
out_top_ref [i + 1 + multi_ref_index ] = nearest_pixel ;
1251
1337
out_top_ref [i + 2 + multi_ref_index ] = nearest_pixel ;
1252
1338
out_top_ref [i + 3 + multi_ref_index ] = nearest_pixel ;
0 commit comments