141294d96d7dbf9bc215b09832a8336c5fb158f0bjohannkoenig@chromium.org/* 241294d96d7dbf9bc215b09832a8336c5fb158f0bjohannkoenig@chromium.org * Copyright 2011 The LibYuv Project Authors. All rights reserved. 341294d96d7dbf9bc215b09832a8336c5fb158f0bjohannkoenig@chromium.org * 441294d96d7dbf9bc215b09832a8336c5fb158f0bjohannkoenig@chromium.org * Use of this source code is governed by a BSD-style license 541294d96d7dbf9bc215b09832a8336c5fb158f0bjohannkoenig@chromium.org * that can be found in the LICENSE file in the root of the source 641294d96d7dbf9bc215b09832a8336c5fb158f0bjohannkoenig@chromium.org * tree. An additional intellectual property rights grant can be found 741294d96d7dbf9bc215b09832a8336c5fb158f0bjohannkoenig@chromium.org * in the file PATENTS. All contributing project authors may 841294d96d7dbf9bc215b09832a8336c5fb158f0bjohannkoenig@chromium.org * be found in the AUTHORS file in the root of the source tree. 941294d96d7dbf9bc215b09832a8336c5fb158f0bjohannkoenig@chromium.org */ 1041294d96d7dbf9bc215b09832a8336c5fb158f0bjohannkoenig@chromium.org 1141294d96d7dbf9bc215b09832a8336c5fb158f0bjohannkoenig@chromium.org#include "libyuv/convert.h" 1241294d96d7dbf9bc215b09832a8336c5fb158f0bjohannkoenig@chromium.org 1341294d96d7dbf9bc215b09832a8336c5fb158f0bjohannkoenig@chromium.org#include "libyuv/basic_types.h" 1441294d96d7dbf9bc215b09832a8336c5fb158f0bjohannkoenig@chromium.org#include "libyuv/cpu_id.h" 1541294d96d7dbf9bc215b09832a8336c5fb158f0bjohannkoenig@chromium.org#include "libyuv/planar_functions.h" 1641294d96d7dbf9bc215b09832a8336c5fb158f0bjohannkoenig@chromium.org#include "libyuv/rotate.h" 1741294d96d7dbf9bc215b09832a8336c5fb158f0bjohannkoenig@chromium.org#include "libyuv/scale.h" // For ScalePlane() 1841294d96d7dbf9bc215b09832a8336c5fb158f0bjohannkoenig@chromium.org#include "libyuv/row.h" 1941294d96d7dbf9bc215b09832a8336c5fb158f0bjohannkoenig@chromium.org 2041294d96d7dbf9bc215b09832a8336c5fb158f0bjohannkoenig@chromium.org#ifdef __cplusplus 2141294d96d7dbf9bc215b09832a8336c5fb158f0bjohannkoenig@chromium.orgnamespace libyuv { 2241294d96d7dbf9bc215b09832a8336c5fb158f0bjohannkoenig@chromium.orgextern "C" { 2341294d96d7dbf9bc215b09832a8336c5fb158f0bjohannkoenig@chromium.org#endif 2441294d96d7dbf9bc215b09832a8336c5fb158f0bjohannkoenig@chromium.org 2541294d96d7dbf9bc215b09832a8336c5fb158f0bjohannkoenig@chromium.org#define SUBSAMPLE(v, a, s) (v < 0) ? (-((-v + a) >> s)) : ((v + a) >> s) 2641294d96d7dbf9bc215b09832a8336c5fb158f0bjohannkoenig@chromium.orgstatic __inline int Abs(int v) { 2741294d96d7dbf9bc215b09832a8336c5fb158f0bjohannkoenig@chromium.org return v >= 0 ? v : -v; 2841294d96d7dbf9bc215b09832a8336c5fb158f0bjohannkoenig@chromium.org} 2941294d96d7dbf9bc215b09832a8336c5fb158f0bjohannkoenig@chromium.org 3041294d96d7dbf9bc215b09832a8336c5fb158f0bjohannkoenig@chromium.org// Any I4xx To I420 format with mirroring. 3141294d96d7dbf9bc215b09832a8336c5fb158f0bjohannkoenig@chromium.orgstatic int I4xxToI420(const uint8* src_y, int src_stride_y, 3241294d96d7dbf9bc215b09832a8336c5fb158f0bjohannkoenig@chromium.org const uint8* src_u, int src_stride_u, 3341294d96d7dbf9bc215b09832a8336c5fb158f0bjohannkoenig@chromium.org const uint8* src_v, int src_stride_v, 3441294d96d7dbf9bc215b09832a8336c5fb158f0bjohannkoenig@chromium.org uint8* dst_y, int dst_stride_y, 3541294d96d7dbf9bc215b09832a8336c5fb158f0bjohannkoenig@chromium.org uint8* dst_u, int dst_stride_u, 3641294d96d7dbf9bc215b09832a8336c5fb158f0bjohannkoenig@chromium.org uint8* dst_v, int dst_stride_v, 3741294d96d7dbf9bc215b09832a8336c5fb158f0bjohannkoenig@chromium.org int src_y_width, int src_y_height, 3841294d96d7dbf9bc215b09832a8336c5fb158f0bjohannkoenig@chromium.org int src_uv_width, int src_uv_height) { 3941294d96d7dbf9bc215b09832a8336c5fb158f0bjohannkoenig@chromium.org const int dst_y_width = Abs(src_y_width); 4041294d96d7dbf9bc215b09832a8336c5fb158f0bjohannkoenig@chromium.org const int dst_y_height = Abs(src_y_height); 4141294d96d7dbf9bc215b09832a8336c5fb158f0bjohannkoenig@chromium.org const int dst_uv_width = SUBSAMPLE(dst_y_width, 1, 1); 4241294d96d7dbf9bc215b09832a8336c5fb158f0bjohannkoenig@chromium.org const int dst_uv_height = SUBSAMPLE(dst_y_height, 1, 1); 4341294d96d7dbf9bc215b09832a8336c5fb158f0bjohannkoenig@chromium.org if (src_y_width == 0 || src_y_height == 0 || 4441294d96d7dbf9bc215b09832a8336c5fb158f0bjohannkoenig@chromium.org src_uv_width == 0 || src_uv_height == 0) { 4541294d96d7dbf9bc215b09832a8336c5fb158f0bjohannkoenig@chromium.org return -1; 4641294d96d7dbf9bc215b09832a8336c5fb158f0bjohannkoenig@chromium.org } 4741294d96d7dbf9bc215b09832a8336c5fb158f0bjohannkoenig@chromium.org ScalePlane(src_y, src_stride_y, src_y_width, src_y_height, 4841294d96d7dbf9bc215b09832a8336c5fb158f0bjohannkoenig@chromium.org dst_y, dst_stride_y, dst_y_width, dst_y_height, 4941294d96d7dbf9bc215b09832a8336c5fb158f0bjohannkoenig@chromium.org kFilterBilinear); 5041294d96d7dbf9bc215b09832a8336c5fb158f0bjohannkoenig@chromium.org ScalePlane(src_u, src_stride_u, src_uv_width, src_uv_height, 5141294d96d7dbf9bc215b09832a8336c5fb158f0bjohannkoenig@chromium.org dst_u, dst_stride_u, dst_uv_width, dst_uv_height, 5241294d96d7dbf9bc215b09832a8336c5fb158f0bjohannkoenig@chromium.org kFilterBilinear); 5341294d96d7dbf9bc215b09832a8336c5fb158f0bjohannkoenig@chromium.org ScalePlane(src_v, src_stride_v, src_uv_width, src_uv_height, 5441294d96d7dbf9bc215b09832a8336c5fb158f0bjohannkoenig@chromium.org dst_v, dst_stride_v, dst_uv_width, dst_uv_height, 5541294d96d7dbf9bc215b09832a8336c5fb158f0bjohannkoenig@chromium.org kFilterBilinear); 5641294d96d7dbf9bc215b09832a8336c5fb158f0bjohannkoenig@chromium.org return 0; 5741294d96d7dbf9bc215b09832a8336c5fb158f0bjohannkoenig@chromium.org} 5841294d96d7dbf9bc215b09832a8336c5fb158f0bjohannkoenig@chromium.org 5941294d96d7dbf9bc215b09832a8336c5fb158f0bjohannkoenig@chromium.org// Copy I420 with optional flipping 6041294d96d7dbf9bc215b09832a8336c5fb158f0bjohannkoenig@chromium.org// TODO(fbarchard): Use Scale plane which supports mirroring, but ensure 6141294d96d7dbf9bc215b09832a8336c5fb158f0bjohannkoenig@chromium.org// is does row coalescing. 6241294d96d7dbf9bc215b09832a8336c5fb158f0bjohannkoenig@chromium.orgLIBYUV_API 6341294d96d7dbf9bc215b09832a8336c5fb158f0bjohannkoenig@chromium.orgint I420Copy(const uint8* src_y, int src_stride_y, 6441294d96d7dbf9bc215b09832a8336c5fb158f0bjohannkoenig@chromium.org const uint8* src_u, int src_stride_u, 6541294d96d7dbf9bc215b09832a8336c5fb158f0bjohannkoenig@chromium.org const uint8* src_v, int src_stride_v, 6641294d96d7dbf9bc215b09832a8336c5fb158f0bjohannkoenig@chromium.org uint8* dst_y, int dst_stride_y, 6741294d96d7dbf9bc215b09832a8336c5fb158f0bjohannkoenig@chromium.org uint8* dst_u, int dst_stride_u, 6841294d96d7dbf9bc215b09832a8336c5fb158f0bjohannkoenig@chromium.org uint8* dst_v, int dst_stride_v, 6941294d96d7dbf9bc215b09832a8336c5fb158f0bjohannkoenig@chromium.org int width, int height) { 7041294d96d7dbf9bc215b09832a8336c5fb158f0bjohannkoenig@chromium.org int halfwidth = (width + 1) >> 1; 7141294d96d7dbf9bc215b09832a8336c5fb158f0bjohannkoenig@chromium.org int halfheight = (height + 1) >> 1; 7241294d96d7dbf9bc215b09832a8336c5fb158f0bjohannkoenig@chromium.org if (!src_y || !src_u || !src_v || 7341294d96d7dbf9bc215b09832a8336c5fb158f0bjohannkoenig@chromium.org !dst_y || !dst_u || !dst_v || 7441294d96d7dbf9bc215b09832a8336c5fb158f0bjohannkoenig@chromium.org width <= 0 || height == 0) { 7541294d96d7dbf9bc215b09832a8336c5fb158f0bjohannkoenig@chromium.org return -1; 7641294d96d7dbf9bc215b09832a8336c5fb158f0bjohannkoenig@chromium.org } 7741294d96d7dbf9bc215b09832a8336c5fb158f0bjohannkoenig@chromium.org // Negative height means invert the image. 7841294d96d7dbf9bc215b09832a8336c5fb158f0bjohannkoenig@chromium.org if (height < 0) { 7941294d96d7dbf9bc215b09832a8336c5fb158f0bjohannkoenig@chromium.org height = -height; 8041294d96d7dbf9bc215b09832a8336c5fb158f0bjohannkoenig@chromium.org halfheight = (height + 1) >> 1; 8141294d96d7dbf9bc215b09832a8336c5fb158f0bjohannkoenig@chromium.org src_y = src_y + (height - 1) * src_stride_y; 8241294d96d7dbf9bc215b09832a8336c5fb158f0bjohannkoenig@chromium.org src_u = src_u + (halfheight - 1) * src_stride_u; 8341294d96d7dbf9bc215b09832a8336c5fb158f0bjohannkoenig@chromium.org src_v = src_v + (halfheight - 1) * src_stride_v; 8441294d96d7dbf9bc215b09832a8336c5fb158f0bjohannkoenig@chromium.org src_stride_y = -src_stride_y; 8541294d96d7dbf9bc215b09832a8336c5fb158f0bjohannkoenig@chromium.org src_stride_u = -src_stride_u; 8641294d96d7dbf9bc215b09832a8336c5fb158f0bjohannkoenig@chromium.org src_stride_v = -src_stride_v; 8741294d96d7dbf9bc215b09832a8336c5fb158f0bjohannkoenig@chromium.org } 8841294d96d7dbf9bc215b09832a8336c5fb158f0bjohannkoenig@chromium.org 8941294d96d7dbf9bc215b09832a8336c5fb158f0bjohannkoenig@chromium.org if (dst_y) { 9041294d96d7dbf9bc215b09832a8336c5fb158f0bjohannkoenig@chromium.org CopyPlane(src_y, src_stride_y, dst_y, dst_stride_y, width, height); 9141294d96d7dbf9bc215b09832a8336c5fb158f0bjohannkoenig@chromium.org } 9241294d96d7dbf9bc215b09832a8336c5fb158f0bjohannkoenig@chromium.org // Copy UV planes. 9341294d96d7dbf9bc215b09832a8336c5fb158f0bjohannkoenig@chromium.org CopyPlane(src_u, src_stride_u, dst_u, dst_stride_u, halfwidth, halfheight); 9441294d96d7dbf9bc215b09832a8336c5fb158f0bjohannkoenig@chromium.org CopyPlane(src_v, src_stride_v, dst_v, dst_stride_v, halfwidth, halfheight); 9541294d96d7dbf9bc215b09832a8336c5fb158f0bjohannkoenig@chromium.org return 0; 9641294d96d7dbf9bc215b09832a8336c5fb158f0bjohannkoenig@chromium.org} 9741294d96d7dbf9bc215b09832a8336c5fb158f0bjohannkoenig@chromium.org 9841294d96d7dbf9bc215b09832a8336c5fb158f0bjohannkoenig@chromium.org// 422 chroma is 1/2 width, 1x height 9941294d96d7dbf9bc215b09832a8336c5fb158f0bjohannkoenig@chromium.org// 420 chroma is 1/2 width, 1/2 height 10041294d96d7dbf9bc215b09832a8336c5fb158f0bjohannkoenig@chromium.orgLIBYUV_API 10141294d96d7dbf9bc215b09832a8336c5fb158f0bjohannkoenig@chromium.orgint I422ToI420(const uint8* src_y, int src_stride_y, 10241294d96d7dbf9bc215b09832a8336c5fb158f0bjohannkoenig@chromium.org const uint8* src_u, int src_stride_u, 10341294d96d7dbf9bc215b09832a8336c5fb158f0bjohannkoenig@chromium.org const uint8* src_v, int src_stride_v, 10441294d96d7dbf9bc215b09832a8336c5fb158f0bjohannkoenig@chromium.org uint8* dst_y, int dst_stride_y, 10541294d96d7dbf9bc215b09832a8336c5fb158f0bjohannkoenig@chromium.org uint8* dst_u, int dst_stride_u, 10641294d96d7dbf9bc215b09832a8336c5fb158f0bjohannkoenig@chromium.org uint8* dst_v, int dst_stride_v, 10741294d96d7dbf9bc215b09832a8336c5fb158f0bjohannkoenig@chromium.org int width, int height) { 10841294d96d7dbf9bc215b09832a8336c5fb158f0bjohannkoenig@chromium.org const int src_uv_width = SUBSAMPLE(width, 1, 1); 10941294d96d7dbf9bc215b09832a8336c5fb158f0bjohannkoenig@chromium.org return I4xxToI420(src_y, src_stride_y, 11041294d96d7dbf9bc215b09832a8336c5fb158f0bjohannkoenig@chromium.org src_u, src_stride_u, 11141294d96d7dbf9bc215b09832a8336c5fb158f0bjohannkoenig@chromium.org src_v, src_stride_v, 11241294d96d7dbf9bc215b09832a8336c5fb158f0bjohannkoenig@chromium.org dst_y, dst_stride_y, 11341294d96d7dbf9bc215b09832a8336c5fb158f0bjohannkoenig@chromium.org dst_u, dst_stride_u, 11441294d96d7dbf9bc215b09832a8336c5fb158f0bjohannkoenig@chromium.org dst_v, dst_stride_v, 11541294d96d7dbf9bc215b09832a8336c5fb158f0bjohannkoenig@chromium.org width, height, 11641294d96d7dbf9bc215b09832a8336c5fb158f0bjohannkoenig@chromium.org src_uv_width, height); 11741294d96d7dbf9bc215b09832a8336c5fb158f0bjohannkoenig@chromium.org} 11841294d96d7dbf9bc215b09832a8336c5fb158f0bjohannkoenig@chromium.org 11941294d96d7dbf9bc215b09832a8336c5fb158f0bjohannkoenig@chromium.org// 444 chroma is 1x width, 1x height 12041294d96d7dbf9bc215b09832a8336c5fb158f0bjohannkoenig@chromium.org// 420 chroma is 1/2 width, 1/2 height 12141294d96d7dbf9bc215b09832a8336c5fb158f0bjohannkoenig@chromium.orgLIBYUV_API 12241294d96d7dbf9bc215b09832a8336c5fb158f0bjohannkoenig@chromium.orgint I444ToI420(const uint8* src_y, int src_stride_y, 12341294d96d7dbf9bc215b09832a8336c5fb158f0bjohannkoenig@chromium.org const uint8* src_u, int src_stride_u, 12441294d96d7dbf9bc215b09832a8336c5fb158f0bjohannkoenig@chromium.org const uint8* src_v, int src_stride_v, 12541294d96d7dbf9bc215b09832a8336c5fb158f0bjohannkoenig@chromium.org uint8* dst_y, int dst_stride_y, 12641294d96d7dbf9bc215b09832a8336c5fb158f0bjohannkoenig@chromium.org uint8* dst_u, int dst_stride_u, 12741294d96d7dbf9bc215b09832a8336c5fb158f0bjohannkoenig@chromium.org uint8* dst_v, int dst_stride_v, 12841294d96d7dbf9bc215b09832a8336c5fb158f0bjohannkoenig@chromium.org int width, int height) { 12941294d96d7dbf9bc215b09832a8336c5fb158f0bjohannkoenig@chromium.org return I4xxToI420(src_y, src_stride_y, 13041294d96d7dbf9bc215b09832a8336c5fb158f0bjohannkoenig@chromium.org src_u, src_stride_u, 13141294d96d7dbf9bc215b09832a8336c5fb158f0bjohannkoenig@chromium.org src_v, src_stride_v, 13241294d96d7dbf9bc215b09832a8336c5fb158f0bjohannkoenig@chromium.org dst_y, dst_stride_y, 13341294d96d7dbf9bc215b09832a8336c5fb158f0bjohannkoenig@chromium.org dst_u, dst_stride_u, 13441294d96d7dbf9bc215b09832a8336c5fb158f0bjohannkoenig@chromium.org dst_v, dst_stride_v, 13541294d96d7dbf9bc215b09832a8336c5fb158f0bjohannkoenig@chromium.org width, height, 13641294d96d7dbf9bc215b09832a8336c5fb158f0bjohannkoenig@chromium.org width, height); 13741294d96d7dbf9bc215b09832a8336c5fb158f0bjohannkoenig@chromium.org} 13841294d96d7dbf9bc215b09832a8336c5fb158f0bjohannkoenig@chromium.org 13941294d96d7dbf9bc215b09832a8336c5fb158f0bjohannkoenig@chromium.org// 411 chroma is 1/4 width, 1x height 14041294d96d7dbf9bc215b09832a8336c5fb158f0bjohannkoenig@chromium.org// 420 chroma is 1/2 width, 1/2 height 14141294d96d7dbf9bc215b09832a8336c5fb158f0bjohannkoenig@chromium.orgLIBYUV_API 14241294d96d7dbf9bc215b09832a8336c5fb158f0bjohannkoenig@chromium.orgint I411ToI420(const uint8* src_y, int src_stride_y, 14341294d96d7dbf9bc215b09832a8336c5fb158f0bjohannkoenig@chromium.org const uint8* src_u, int src_stride_u, 14441294d96d7dbf9bc215b09832a8336c5fb158f0bjohannkoenig@chromium.org const uint8* src_v, int src_stride_v, 14541294d96d7dbf9bc215b09832a8336c5fb158f0bjohannkoenig@chromium.org uint8* dst_y, int dst_stride_y, 14641294d96d7dbf9bc215b09832a8336c5fb158f0bjohannkoenig@chromium.org uint8* dst_u, int dst_stride_u, 14741294d96d7dbf9bc215b09832a8336c5fb158f0bjohannkoenig@chromium.org uint8* dst_v, int dst_stride_v, 14841294d96d7dbf9bc215b09832a8336c5fb158f0bjohannkoenig@chromium.org int width, int height) { 14941294d96d7dbf9bc215b09832a8336c5fb158f0bjohannkoenig@chromium.org const int src_uv_width = SUBSAMPLE(width, 3, 2); 15041294d96d7dbf9bc215b09832a8336c5fb158f0bjohannkoenig@chromium.org return I4xxToI420(src_y, src_stride_y, 15141294d96d7dbf9bc215b09832a8336c5fb158f0bjohannkoenig@chromium.org src_u, src_stride_u, 15241294d96d7dbf9bc215b09832a8336c5fb158f0bjohannkoenig@chromium.org src_v, src_stride_v, 15341294d96d7dbf9bc215b09832a8336c5fb158f0bjohannkoenig@chromium.org dst_y, dst_stride_y, 15441294d96d7dbf9bc215b09832a8336c5fb158f0bjohannkoenig@chromium.org dst_u, dst_stride_u, 15541294d96d7dbf9bc215b09832a8336c5fb158f0bjohannkoenig@chromium.org dst_v, dst_stride_v, 15641294d96d7dbf9bc215b09832a8336c5fb158f0bjohannkoenig@chromium.org width, height, 15741294d96d7dbf9bc215b09832a8336c5fb158f0bjohannkoenig@chromium.org src_uv_width, height); 15841294d96d7dbf9bc215b09832a8336c5fb158f0bjohannkoenig@chromium.org} 15941294d96d7dbf9bc215b09832a8336c5fb158f0bjohannkoenig@chromium.org 16041294d96d7dbf9bc215b09832a8336c5fb158f0bjohannkoenig@chromium.org// I400 is greyscale typically used in MJPG 16141294d96d7dbf9bc215b09832a8336c5fb158f0bjohannkoenig@chromium.orgLIBYUV_API 16241294d96d7dbf9bc215b09832a8336c5fb158f0bjohannkoenig@chromium.orgint I400ToI420(const uint8* src_y, int src_stride_y, 16341294d96d7dbf9bc215b09832a8336c5fb158f0bjohannkoenig@chromium.org uint8* dst_y, int dst_stride_y, 16441294d96d7dbf9bc215b09832a8336c5fb158f0bjohannkoenig@chromium.org uint8* dst_u, int dst_stride_u, 16541294d96d7dbf9bc215b09832a8336c5fb158f0bjohannkoenig@chromium.org uint8* dst_v, int dst_stride_v, 16641294d96d7dbf9bc215b09832a8336c5fb158f0bjohannkoenig@chromium.org int width, int height) { 16741294d96d7dbf9bc215b09832a8336c5fb158f0bjohannkoenig@chromium.org int halfwidth = (width + 1) >> 1; 16841294d96d7dbf9bc215b09832a8336c5fb158f0bjohannkoenig@chromium.org int halfheight = (height + 1) >> 1; 16941294d96d7dbf9bc215b09832a8336c5fb158f0bjohannkoenig@chromium.org if (!src_y || !dst_y || !dst_u || !dst_v || 17041294d96d7dbf9bc215b09832a8336c5fb158f0bjohannkoenig@chromium.org width <= 0 || height == 0) { 17141294d96d7dbf9bc215b09832a8336c5fb158f0bjohannkoenig@chromium.org return -1; 17241294d96d7dbf9bc215b09832a8336c5fb158f0bjohannkoenig@chromium.org } 17341294d96d7dbf9bc215b09832a8336c5fb158f0bjohannkoenig@chromium.org // Negative height means invert the image. 17441294d96d7dbf9bc215b09832a8336c5fb158f0bjohannkoenig@chromium.org if (height < 0) { 17541294d96d7dbf9bc215b09832a8336c5fb158f0bjohannkoenig@chromium.org height = -height; 17641294d96d7dbf9bc215b09832a8336c5fb158f0bjohannkoenig@chromium.org halfheight = (height + 1) >> 1; 17741294d96d7dbf9bc215b09832a8336c5fb158f0bjohannkoenig@chromium.org src_y = src_y + (height - 1) * src_stride_y; 17841294d96d7dbf9bc215b09832a8336c5fb158f0bjohannkoenig@chromium.org src_stride_y = -src_stride_y; 17941294d96d7dbf9bc215b09832a8336c5fb158f0bjohannkoenig@chromium.org } 18041294d96d7dbf9bc215b09832a8336c5fb158f0bjohannkoenig@chromium.org CopyPlane(src_y, src_stride_y, dst_y, dst_stride_y, width, height); 18141294d96d7dbf9bc215b09832a8336c5fb158f0bjohannkoenig@chromium.org SetPlane(dst_u, dst_stride_u, halfwidth, halfheight, 128); 18241294d96d7dbf9bc215b09832a8336c5fb158f0bjohannkoenig@chromium.org SetPlane(dst_v, dst_stride_v, halfwidth, halfheight, 128); 18341294d96d7dbf9bc215b09832a8336c5fb158f0bjohannkoenig@chromium.org return 0; 18441294d96d7dbf9bc215b09832a8336c5fb158f0bjohannkoenig@chromium.org} 18541294d96d7dbf9bc215b09832a8336c5fb158f0bjohannkoenig@chromium.org 18641294d96d7dbf9bc215b09832a8336c5fb158f0bjohannkoenig@chromium.orgstatic void CopyPlane2(const uint8* src, int src_stride_0, int src_stride_1, 18741294d96d7dbf9bc215b09832a8336c5fb158f0bjohannkoenig@chromium.org uint8* dst, int dst_stride, 18841294d96d7dbf9bc215b09832a8336c5fb158f0bjohannkoenig@chromium.org int width, int height) { 18941294d96d7dbf9bc215b09832a8336c5fb158f0bjohannkoenig@chromium.org int y; 19041294d96d7dbf9bc215b09832a8336c5fb158f0bjohannkoenig@chromium.org void (*CopyRow)(const uint8* src, uint8* dst, int width) = CopyRow_C; 19141294d96d7dbf9bc215b09832a8336c5fb158f0bjohannkoenig@chromium.org#if defined(HAS_COPYROW_X86) 19241294d96d7dbf9bc215b09832a8336c5fb158f0bjohannkoenig@chromium.org if (TestCpuFlag(kCpuHasX86) && IS_ALIGNED(width, 4)) { 19341294d96d7dbf9bc215b09832a8336c5fb158f0bjohannkoenig@chromium.org CopyRow = CopyRow_X86; 19441294d96d7dbf9bc215b09832a8336c5fb158f0bjohannkoenig@chromium.org } 19541294d96d7dbf9bc215b09832a8336c5fb158f0bjohannkoenig@chromium.org#endif 19641294d96d7dbf9bc215b09832a8336c5fb158f0bjohannkoenig@chromium.org#if defined(HAS_COPYROW_SSE2) 19741294d96d7dbf9bc215b09832a8336c5fb158f0bjohannkoenig@chromium.org if (TestCpuFlag(kCpuHasSSE2) && IS_ALIGNED(width, 32) && 19841294d96d7dbf9bc215b09832a8336c5fb158f0bjohannkoenig@chromium.org IS_ALIGNED(src, 16) && 19941294d96d7dbf9bc215b09832a8336c5fb158f0bjohannkoenig@chromium.org IS_ALIGNED(src_stride_0, 16) && IS_ALIGNED(src_stride_1, 16) && 20041294d96d7dbf9bc215b09832a8336c5fb158f0bjohannkoenig@chromium.org IS_ALIGNED(dst, 16) && IS_ALIGNED(dst_stride, 16)) { 20141294d96d7dbf9bc215b09832a8336c5fb158f0bjohannkoenig@chromium.org CopyRow = CopyRow_SSE2; 20241294d96d7dbf9bc215b09832a8336c5fb158f0bjohannkoenig@chromium.org } 20341294d96d7dbf9bc215b09832a8336c5fb158f0bjohannkoenig@chromium.org#endif 20441294d96d7dbf9bc215b09832a8336c5fb158f0bjohannkoenig@chromium.org#if defined(HAS_COPYROW_ERMS) 20541294d96d7dbf9bc215b09832a8336c5fb158f0bjohannkoenig@chromium.org if (TestCpuFlag(kCpuHasERMS)) { 20641294d96d7dbf9bc215b09832a8336c5fb158f0bjohannkoenig@chromium.org CopyRow = CopyRow_ERMS; 20741294d96d7dbf9bc215b09832a8336c5fb158f0bjohannkoenig@chromium.org } 20841294d96d7dbf9bc215b09832a8336c5fb158f0bjohannkoenig@chromium.org#endif 20941294d96d7dbf9bc215b09832a8336c5fb158f0bjohannkoenig@chromium.org#if defined(HAS_COPYROW_NEON) 21041294d96d7dbf9bc215b09832a8336c5fb158f0bjohannkoenig@chromium.org if (TestCpuFlag(kCpuHasNEON) && IS_ALIGNED(width, 32)) { 21141294d96d7dbf9bc215b09832a8336c5fb158f0bjohannkoenig@chromium.org CopyRow = CopyRow_NEON; 21241294d96d7dbf9bc215b09832a8336c5fb158f0bjohannkoenig@chromium.org } 21341294d96d7dbf9bc215b09832a8336c5fb158f0bjohannkoenig@chromium.org#endif 21441294d96d7dbf9bc215b09832a8336c5fb158f0bjohannkoenig@chromium.org#if defined(HAS_COPYROW_MIPS) 21541294d96d7dbf9bc215b09832a8336c5fb158f0bjohannkoenig@chromium.org if (TestCpuFlag(kCpuHasMIPS)) { 21641294d96d7dbf9bc215b09832a8336c5fb158f0bjohannkoenig@chromium.org CopyRow = CopyRow_MIPS; 21741294d96d7dbf9bc215b09832a8336c5fb158f0bjohannkoenig@chromium.org } 21841294d96d7dbf9bc215b09832a8336c5fb158f0bjohannkoenig@chromium.org#endif 21941294d96d7dbf9bc215b09832a8336c5fb158f0bjohannkoenig@chromium.org 22041294d96d7dbf9bc215b09832a8336c5fb158f0bjohannkoenig@chromium.org // Copy plane 22141294d96d7dbf9bc215b09832a8336c5fb158f0bjohannkoenig@chromium.org for (y = 0; y < height - 1; y += 2) { 22241294d96d7dbf9bc215b09832a8336c5fb158f0bjohannkoenig@chromium.org CopyRow(src, dst, width); 22341294d96d7dbf9bc215b09832a8336c5fb158f0bjohannkoenig@chromium.org CopyRow(src + src_stride_0, dst + dst_stride, width); 22441294d96d7dbf9bc215b09832a8336c5fb158f0bjohannkoenig@chromium.org src += src_stride_0 + src_stride_1; 22541294d96d7dbf9bc215b09832a8336c5fb158f0bjohannkoenig@chromium.org dst += dst_stride * 2; 22641294d96d7dbf9bc215b09832a8336c5fb158f0bjohannkoenig@chromium.org } 22741294d96d7dbf9bc215b09832a8336c5fb158f0bjohannkoenig@chromium.org if (height & 1) { 22841294d96d7dbf9bc215b09832a8336c5fb158f0bjohannkoenig@chromium.org CopyRow(src, dst, width); 22941294d96d7dbf9bc215b09832a8336c5fb158f0bjohannkoenig@chromium.org } 23041294d96d7dbf9bc215b09832a8336c5fb158f0bjohannkoenig@chromium.org} 23141294d96d7dbf9bc215b09832a8336c5fb158f0bjohannkoenig@chromium.org 23241294d96d7dbf9bc215b09832a8336c5fb158f0bjohannkoenig@chromium.org// Support converting from FOURCC_M420 23341294d96d7dbf9bc215b09832a8336c5fb158f0bjohannkoenig@chromium.org// Useful for bandwidth constrained transports like USB 1.0 and 2.0 and for 23441294d96d7dbf9bc215b09832a8336c5fb158f0bjohannkoenig@chromium.org// easy conversion to I420. 23541294d96d7dbf9bc215b09832a8336c5fb158f0bjohannkoenig@chromium.org// M420 format description: 23641294d96d7dbf9bc215b09832a8336c5fb158f0bjohannkoenig@chromium.org// M420 is row biplanar 420: 2 rows of Y and 1 row of UV. 23741294d96d7dbf9bc215b09832a8336c5fb158f0bjohannkoenig@chromium.org// Chroma is half width / half height. (420) 23841294d96d7dbf9bc215b09832a8336c5fb158f0bjohannkoenig@chromium.org// src_stride_m420 is row planar. Normally this will be the width in pixels. 23941294d96d7dbf9bc215b09832a8336c5fb158f0bjohannkoenig@chromium.org// The UV plane is half width, but 2 values, so src_stride_m420 applies to 24041294d96d7dbf9bc215b09832a8336c5fb158f0bjohannkoenig@chromium.org// this as well as the two Y planes. 24141294d96d7dbf9bc215b09832a8336c5fb158f0bjohannkoenig@chromium.orgstatic int X420ToI420(const uint8* src_y, 24241294d96d7dbf9bc215b09832a8336c5fb158f0bjohannkoenig@chromium.org int src_stride_y0, int src_stride_y1, 24341294d96d7dbf9bc215b09832a8336c5fb158f0bjohannkoenig@chromium.org const uint8* src_uv, int src_stride_uv, 24441294d96d7dbf9bc215b09832a8336c5fb158f0bjohannkoenig@chromium.org uint8* dst_y, int dst_stride_y, 24541294d96d7dbf9bc215b09832a8336c5fb158f0bjohannkoenig@chromium.org uint8* dst_u, int dst_stride_u, 24641294d96d7dbf9bc215b09832a8336c5fb158f0bjohannkoenig@chromium.org uint8* dst_v, int dst_stride_v, 24741294d96d7dbf9bc215b09832a8336c5fb158f0bjohannkoenig@chromium.org int width, int height) { 24841294d96d7dbf9bc215b09832a8336c5fb158f0bjohannkoenig@chromium.org int y; 24941294d96d7dbf9bc215b09832a8336c5fb158f0bjohannkoenig@chromium.org int halfwidth = (width + 1) >> 1; 25041294d96d7dbf9bc215b09832a8336c5fb158f0bjohannkoenig@chromium.org int halfheight = (height + 1) >> 1; 25141294d96d7dbf9bc215b09832a8336c5fb158f0bjohannkoenig@chromium.org void (*SplitUVRow)(const uint8* src_uv, uint8* dst_u, uint8* dst_v, int pix) = 25241294d96d7dbf9bc215b09832a8336c5fb158f0bjohannkoenig@chromium.org SplitUVRow_C; 25341294d96d7dbf9bc215b09832a8336c5fb158f0bjohannkoenig@chromium.org if (!src_y || !src_uv || 25441294d96d7dbf9bc215b09832a8336c5fb158f0bjohannkoenig@chromium.org !dst_y || !dst_u || !dst_v || 25541294d96d7dbf9bc215b09832a8336c5fb158f0bjohannkoenig@chromium.org width <= 0 || height == 0) { 25641294d96d7dbf9bc215b09832a8336c5fb158f0bjohannkoenig@chromium.org return -1; 25741294d96d7dbf9bc215b09832a8336c5fb158f0bjohannkoenig@chromium.org } 25841294d96d7dbf9bc215b09832a8336c5fb158f0bjohannkoenig@chromium.org // Negative height means invert the image. 25941294d96d7dbf9bc215b09832a8336c5fb158f0bjohannkoenig@chromium.org if (height < 0) { 26041294d96d7dbf9bc215b09832a8336c5fb158f0bjohannkoenig@chromium.org height = -height; 26141294d96d7dbf9bc215b09832a8336c5fb158f0bjohannkoenig@chromium.org halfheight = (height + 1) >> 1; 26241294d96d7dbf9bc215b09832a8336c5fb158f0bjohannkoenig@chromium.org dst_y = dst_y + (height - 1) * dst_stride_y; 26341294d96d7dbf9bc215b09832a8336c5fb158f0bjohannkoenig@chromium.org dst_u = dst_u + (halfheight - 1) * dst_stride_u; 26441294d96d7dbf9bc215b09832a8336c5fb158f0bjohannkoenig@chromium.org dst_v = dst_v + (halfheight - 1) * dst_stride_v; 26541294d96d7dbf9bc215b09832a8336c5fb158f0bjohannkoenig@chromium.org dst_stride_y = -dst_stride_y; 26641294d96d7dbf9bc215b09832a8336c5fb158f0bjohannkoenig@chromium.org dst_stride_u = -dst_stride_u; 26741294d96d7dbf9bc215b09832a8336c5fb158f0bjohannkoenig@chromium.org dst_stride_v = -dst_stride_v; 26841294d96d7dbf9bc215b09832a8336c5fb158f0bjohannkoenig@chromium.org } 26941294d96d7dbf9bc215b09832a8336c5fb158f0bjohannkoenig@chromium.org // Coalesce rows. 27041294d96d7dbf9bc215b09832a8336c5fb158f0bjohannkoenig@chromium.org if (src_stride_y0 == width && 27141294d96d7dbf9bc215b09832a8336c5fb158f0bjohannkoenig@chromium.org src_stride_y1 == width && 27241294d96d7dbf9bc215b09832a8336c5fb158f0bjohannkoenig@chromium.org dst_stride_y == width) { 27341294d96d7dbf9bc215b09832a8336c5fb158f0bjohannkoenig@chromium.org width *= height; 27441294d96d7dbf9bc215b09832a8336c5fb158f0bjohannkoenig@chromium.org height = 1; 27541294d96d7dbf9bc215b09832a8336c5fb158f0bjohannkoenig@chromium.org src_stride_y0 = src_stride_y1 = dst_stride_y = 0; 27641294d96d7dbf9bc215b09832a8336c5fb158f0bjohannkoenig@chromium.org } 27741294d96d7dbf9bc215b09832a8336c5fb158f0bjohannkoenig@chromium.org // Coalesce rows. 27841294d96d7dbf9bc215b09832a8336c5fb158f0bjohannkoenig@chromium.org if (src_stride_uv == halfwidth * 2 && 27941294d96d7dbf9bc215b09832a8336c5fb158f0bjohannkoenig@chromium.org dst_stride_u == halfwidth && 28041294d96d7dbf9bc215b09832a8336c5fb158f0bjohannkoenig@chromium.org dst_stride_v == halfwidth) { 28141294d96d7dbf9bc215b09832a8336c5fb158f0bjohannkoenig@chromium.org halfwidth *= halfheight; 28241294d96d7dbf9bc215b09832a8336c5fb158f0bjohannkoenig@chromium.org halfheight = 1; 28341294d96d7dbf9bc215b09832a8336c5fb158f0bjohannkoenig@chromium.org src_stride_uv = dst_stride_u = dst_stride_v = 0; 28441294d96d7dbf9bc215b09832a8336c5fb158f0bjohannkoenig@chromium.org } 28541294d96d7dbf9bc215b09832a8336c5fb158f0bjohannkoenig@chromium.org#if defined(HAS_SPLITUVROW_SSE2) 28641294d96d7dbf9bc215b09832a8336c5fb158f0bjohannkoenig@chromium.org if (TestCpuFlag(kCpuHasSSE2) && halfwidth >= 16) { 28741294d96d7dbf9bc215b09832a8336c5fb158f0bjohannkoenig@chromium.org SplitUVRow = SplitUVRow_Any_SSE2; 28841294d96d7dbf9bc215b09832a8336c5fb158f0bjohannkoenig@chromium.org if (IS_ALIGNED(halfwidth, 16)) { 28941294d96d7dbf9bc215b09832a8336c5fb158f0bjohannkoenig@chromium.org SplitUVRow = SplitUVRow_Unaligned_SSE2; 29041294d96d7dbf9bc215b09832a8336c5fb158f0bjohannkoenig@chromium.org if (IS_ALIGNED(src_uv, 16) && IS_ALIGNED(src_stride_uv, 16) && 29141294d96d7dbf9bc215b09832a8336c5fb158f0bjohannkoenig@chromium.org IS_ALIGNED(dst_u, 16) && IS_ALIGNED(dst_stride_u, 16) && 29241294d96d7dbf9bc215b09832a8336c5fb158f0bjohannkoenig@chromium.org IS_ALIGNED(dst_v, 16) && IS_ALIGNED(dst_stride_v, 16)) { 29341294d96d7dbf9bc215b09832a8336c5fb158f0bjohannkoenig@chromium.org SplitUVRow = SplitUVRow_SSE2; 29441294d96d7dbf9bc215b09832a8336c5fb158f0bjohannkoenig@chromium.org } 29541294d96d7dbf9bc215b09832a8336c5fb158f0bjohannkoenig@chromium.org } 29641294d96d7dbf9bc215b09832a8336c5fb158f0bjohannkoenig@chromium.org } 29741294d96d7dbf9bc215b09832a8336c5fb158f0bjohannkoenig@chromium.org#endif 29841294d96d7dbf9bc215b09832a8336c5fb158f0bjohannkoenig@chromium.org#if defined(HAS_SPLITUVROW_AVX2) 29941294d96d7dbf9bc215b09832a8336c5fb158f0bjohannkoenig@chromium.org if (TestCpuFlag(kCpuHasAVX2) && halfwidth >= 32) { 30041294d96d7dbf9bc215b09832a8336c5fb158f0bjohannkoenig@chromium.org SplitUVRow = SplitUVRow_Any_AVX2; 30141294d96d7dbf9bc215b09832a8336c5fb158f0bjohannkoenig@chromium.org if (IS_ALIGNED(halfwidth, 32)) { 30241294d96d7dbf9bc215b09832a8336c5fb158f0bjohannkoenig@chromium.org SplitUVRow = SplitUVRow_AVX2; 30341294d96d7dbf9bc215b09832a8336c5fb158f0bjohannkoenig@chromium.org } 30441294d96d7dbf9bc215b09832a8336c5fb158f0bjohannkoenig@chromium.org } 30541294d96d7dbf9bc215b09832a8336c5fb158f0bjohannkoenig@chromium.org#endif 30641294d96d7dbf9bc215b09832a8336c5fb158f0bjohannkoenig@chromium.org#if defined(HAS_SPLITUVROW_NEON) 30741294d96d7dbf9bc215b09832a8336c5fb158f0bjohannkoenig@chromium.org if (TestCpuFlag(kCpuHasNEON) && halfwidth >= 16) { 30841294d96d7dbf9bc215b09832a8336c5fb158f0bjohannkoenig@chromium.org SplitUVRow = SplitUVRow_Any_NEON; 30941294d96d7dbf9bc215b09832a8336c5fb158f0bjohannkoenig@chromium.org if (IS_ALIGNED(halfwidth, 16)) { 31041294d96d7dbf9bc215b09832a8336c5fb158f0bjohannkoenig@chromium.org SplitUVRow = SplitUVRow_NEON; 31141294d96d7dbf9bc215b09832a8336c5fb158f0bjohannkoenig@chromium.org } 31241294d96d7dbf9bc215b09832a8336c5fb158f0bjohannkoenig@chromium.org } 31341294d96d7dbf9bc215b09832a8336c5fb158f0bjohannkoenig@chromium.org#endif 31441294d96d7dbf9bc215b09832a8336c5fb158f0bjohannkoenig@chromium.org#if defined(HAS_SPLITUVROW_MIPS_DSPR2) 31541294d96d7dbf9bc215b09832a8336c5fb158f0bjohannkoenig@chromium.org if (TestCpuFlag(kCpuHasMIPS_DSPR2) && halfwidth >= 16) { 31641294d96d7dbf9bc215b09832a8336c5fb158f0bjohannkoenig@chromium.org SplitUVRow = SplitUVRow_Any_MIPS_DSPR2; 31741294d96d7dbf9bc215b09832a8336c5fb158f0bjohannkoenig@chromium.org if (IS_ALIGNED(halfwidth, 16)) { 31841294d96d7dbf9bc215b09832a8336c5fb158f0bjohannkoenig@chromium.org SplitUVRow = SplitUVRow_Unaligned_MIPS_DSPR2; 31941294d96d7dbf9bc215b09832a8336c5fb158f0bjohannkoenig@chromium.org if (IS_ALIGNED(src_uv, 4) && IS_ALIGNED(src_stride_uv, 4) && 32041294d96d7dbf9bc215b09832a8336c5fb158f0bjohannkoenig@chromium.org IS_ALIGNED(dst_u, 4) && IS_ALIGNED(dst_stride_u, 4) && 32141294d96d7dbf9bc215b09832a8336c5fb158f0bjohannkoenig@chromium.org IS_ALIGNED(dst_v, 4) && IS_ALIGNED(dst_stride_v, 4)) { 32241294d96d7dbf9bc215b09832a8336c5fb158f0bjohannkoenig@chromium.org SplitUVRow = SplitUVRow_MIPS_DSPR2; 32341294d96d7dbf9bc215b09832a8336c5fb158f0bjohannkoenig@chromium.org } 32441294d96d7dbf9bc215b09832a8336c5fb158f0bjohannkoenig@chromium.org } 32541294d96d7dbf9bc215b09832a8336c5fb158f0bjohannkoenig@chromium.org } 32641294d96d7dbf9bc215b09832a8336c5fb158f0bjohannkoenig@chromium.org#endif 32741294d96d7dbf9bc215b09832a8336c5fb158f0bjohannkoenig@chromium.org 32841294d96d7dbf9bc215b09832a8336c5fb158f0bjohannkoenig@chromium.org if (dst_y) { 32941294d96d7dbf9bc215b09832a8336c5fb158f0bjohannkoenig@chromium.org if (src_stride_y0 == src_stride_y1) { 33041294d96d7dbf9bc215b09832a8336c5fb158f0bjohannkoenig@chromium.org CopyPlane(src_y, src_stride_y0, dst_y, dst_stride_y, width, height); 33141294d96d7dbf9bc215b09832a8336c5fb158f0bjohannkoenig@chromium.org } else { 33241294d96d7dbf9bc215b09832a8336c5fb158f0bjohannkoenig@chromium.org CopyPlane2(src_y, src_stride_y0, src_stride_y1, dst_y, dst_stride_y, 33341294d96d7dbf9bc215b09832a8336c5fb158f0bjohannkoenig@chromium.org width, height); 33441294d96d7dbf9bc215b09832a8336c5fb158f0bjohannkoenig@chromium.org } 33541294d96d7dbf9bc215b09832a8336c5fb158f0bjohannkoenig@chromium.org } 33641294d96d7dbf9bc215b09832a8336c5fb158f0bjohannkoenig@chromium.org 33741294d96d7dbf9bc215b09832a8336c5fb158f0bjohannkoenig@chromium.org for (y = 0; y < halfheight; ++y) { 33841294d96d7dbf9bc215b09832a8336c5fb158f0bjohannkoenig@chromium.org // Copy a row of UV. 33941294d96d7dbf9bc215b09832a8336c5fb158f0bjohannkoenig@chromium.org SplitUVRow(src_uv, dst_u, dst_v, halfwidth); 34041294d96d7dbf9bc215b09832a8336c5fb158f0bjohannkoenig@chromium.org dst_u += dst_stride_u; 34141294d96d7dbf9bc215b09832a8336c5fb158f0bjohannkoenig@chromium.org dst_v += dst_stride_v; 34241294d96d7dbf9bc215b09832a8336c5fb158f0bjohannkoenig@chromium.org src_uv += src_stride_uv; 34341294d96d7dbf9bc215b09832a8336c5fb158f0bjohannkoenig@chromium.org } 34441294d96d7dbf9bc215b09832a8336c5fb158f0bjohannkoenig@chromium.org return 0; 34541294d96d7dbf9bc215b09832a8336c5fb158f0bjohannkoenig@chromium.org} 34641294d96d7dbf9bc215b09832a8336c5fb158f0bjohannkoenig@chromium.org 34741294d96d7dbf9bc215b09832a8336c5fb158f0bjohannkoenig@chromium.org// Convert NV12 to I420. 34841294d96d7dbf9bc215b09832a8336c5fb158f0bjohannkoenig@chromium.orgLIBYUV_API 34941294d96d7dbf9bc215b09832a8336c5fb158f0bjohannkoenig@chromium.orgint NV12ToI420(const uint8* src_y, int src_stride_y, 35041294d96d7dbf9bc215b09832a8336c5fb158f0bjohannkoenig@chromium.org const uint8* src_uv, int src_stride_uv, 35141294d96d7dbf9bc215b09832a8336c5fb158f0bjohannkoenig@chromium.org uint8* dst_y, int dst_stride_y, 35241294d96d7dbf9bc215b09832a8336c5fb158f0bjohannkoenig@chromium.org uint8* dst_u, int dst_stride_u, 35341294d96d7dbf9bc215b09832a8336c5fb158f0bjohannkoenig@chromium.org uint8* dst_v, int dst_stride_v, 35441294d96d7dbf9bc215b09832a8336c5fb158f0bjohannkoenig@chromium.org int width, int height) { 35541294d96d7dbf9bc215b09832a8336c5fb158f0bjohannkoenig@chromium.org return X420ToI420(src_y, src_stride_y, src_stride_y, 35641294d96d7dbf9bc215b09832a8336c5fb158f0bjohannkoenig@chromium.org src_uv, src_stride_uv, 35741294d96d7dbf9bc215b09832a8336c5fb158f0bjohannkoenig@chromium.org dst_y, dst_stride_y, 35841294d96d7dbf9bc215b09832a8336c5fb158f0bjohannkoenig@chromium.org dst_u, dst_stride_u, 35941294d96d7dbf9bc215b09832a8336c5fb158f0bjohannkoenig@chromium.org dst_v, dst_stride_v, 36041294d96d7dbf9bc215b09832a8336c5fb158f0bjohannkoenig@chromium.org width, height); 36141294d96d7dbf9bc215b09832a8336c5fb158f0bjohannkoenig@chromium.org} 36241294d96d7dbf9bc215b09832a8336c5fb158f0bjohannkoenig@chromium.org 36341294d96d7dbf9bc215b09832a8336c5fb158f0bjohannkoenig@chromium.org// Convert NV21 to I420. Same as NV12 but u and v pointers swapped. 36441294d96d7dbf9bc215b09832a8336c5fb158f0bjohannkoenig@chromium.orgLIBYUV_API 36541294d96d7dbf9bc215b09832a8336c5fb158f0bjohannkoenig@chromium.orgint NV21ToI420(const uint8* src_y, int src_stride_y, 36641294d96d7dbf9bc215b09832a8336c5fb158f0bjohannkoenig@chromium.org const uint8* src_vu, int src_stride_vu, 36741294d96d7dbf9bc215b09832a8336c5fb158f0bjohannkoenig@chromium.org uint8* dst_y, int dst_stride_y, 36841294d96d7dbf9bc215b09832a8336c5fb158f0bjohannkoenig@chromium.org uint8* dst_u, int dst_stride_u, 36941294d96d7dbf9bc215b09832a8336c5fb158f0bjohannkoenig@chromium.org uint8* dst_v, int dst_stride_v, 37041294d96d7dbf9bc215b09832a8336c5fb158f0bjohannkoenig@chromium.org int width, int height) { 37141294d96d7dbf9bc215b09832a8336c5fb158f0bjohannkoenig@chromium.org return X420ToI420(src_y, src_stride_y, src_stride_y, 37241294d96d7dbf9bc215b09832a8336c5fb158f0bjohannkoenig@chromium.org src_vu, src_stride_vu, 37341294d96d7dbf9bc215b09832a8336c5fb158f0bjohannkoenig@chromium.org dst_y, dst_stride_y, 37441294d96d7dbf9bc215b09832a8336c5fb158f0bjohannkoenig@chromium.org dst_v, dst_stride_v, 37541294d96d7dbf9bc215b09832a8336c5fb158f0bjohannkoenig@chromium.org dst_u, dst_stride_u, 37641294d96d7dbf9bc215b09832a8336c5fb158f0bjohannkoenig@chromium.org width, height); 37741294d96d7dbf9bc215b09832a8336c5fb158f0bjohannkoenig@chromium.org} 37841294d96d7dbf9bc215b09832a8336c5fb158f0bjohannkoenig@chromium.org 37941294d96d7dbf9bc215b09832a8336c5fb158f0bjohannkoenig@chromium.org// Convert M420 to I420. 38041294d96d7dbf9bc215b09832a8336c5fb158f0bjohannkoenig@chromium.orgLIBYUV_API 38141294d96d7dbf9bc215b09832a8336c5fb158f0bjohannkoenig@chromium.orgint M420ToI420(const uint8* src_m420, int src_stride_m420, 38241294d96d7dbf9bc215b09832a8336c5fb158f0bjohannkoenig@chromium.org uint8* dst_y, int dst_stride_y, 38341294d96d7dbf9bc215b09832a8336c5fb158f0bjohannkoenig@chromium.org uint8* dst_u, int dst_stride_u, 38441294d96d7dbf9bc215b09832a8336c5fb158f0bjohannkoenig@chromium.org uint8* dst_v, int dst_stride_v, 38541294d96d7dbf9bc215b09832a8336c5fb158f0bjohannkoenig@chromium.org int width, int height) { 38641294d96d7dbf9bc215b09832a8336c5fb158f0bjohannkoenig@chromium.org return X420ToI420(src_m420, src_stride_m420, src_stride_m420 * 2, 38741294d96d7dbf9bc215b09832a8336c5fb158f0bjohannkoenig@chromium.org src_m420 + src_stride_m420 * 2, src_stride_m420 * 3, 38841294d96d7dbf9bc215b09832a8336c5fb158f0bjohannkoenig@chromium.org dst_y, dst_stride_y, 38941294d96d7dbf9bc215b09832a8336c5fb158f0bjohannkoenig@chromium.org dst_u, dst_stride_u, 39041294d96d7dbf9bc215b09832a8336c5fb158f0bjohannkoenig@chromium.org dst_v, dst_stride_v, 39141294d96d7dbf9bc215b09832a8336c5fb158f0bjohannkoenig@chromium.org width, height); 39241294d96d7dbf9bc215b09832a8336c5fb158f0bjohannkoenig@chromium.org} 39341294d96d7dbf9bc215b09832a8336c5fb158f0bjohannkoenig@chromium.org 39441294d96d7dbf9bc215b09832a8336c5fb158f0bjohannkoenig@chromium.org// Convert Q420 to I420. 39541294d96d7dbf9bc215b09832a8336c5fb158f0bjohannkoenig@chromium.org// Format is rows of YY/YUYV 39641294d96d7dbf9bc215b09832a8336c5fb158f0bjohannkoenig@chromium.orgLIBYUV_API 39741294d96d7dbf9bc215b09832a8336c5fb158f0bjohannkoenig@chromium.orgint Q420ToI420(const uint8* src_y, int src_stride_y, 39841294d96d7dbf9bc215b09832a8336c5fb158f0bjohannkoenig@chromium.org const uint8* src_yuy2, int src_stride_yuy2, 39941294d96d7dbf9bc215b09832a8336c5fb158f0bjohannkoenig@chromium.org uint8* dst_y, int dst_stride_y, 40041294d96d7dbf9bc215b09832a8336c5fb158f0bjohannkoenig@chromium.org uint8* dst_u, int dst_stride_u, 40141294d96d7dbf9bc215b09832a8336c5fb158f0bjohannkoenig@chromium.org uint8* dst_v, int dst_stride_v, 40241294d96d7dbf9bc215b09832a8336c5fb158f0bjohannkoenig@chromium.org int width, int height) { 40341294d96d7dbf9bc215b09832a8336c5fb158f0bjohannkoenig@chromium.org int y; 404d95585fb0ec024f6abd96f7b02e0df58019d46afjohannkoenig@chromium.org int halfheight; 40541294d96d7dbf9bc215b09832a8336c5fb158f0bjohannkoenig@chromium.org void (*CopyRow)(const uint8* src, uint8* dst, int width) = CopyRow_C; 40641294d96d7dbf9bc215b09832a8336c5fb158f0bjohannkoenig@chromium.org void (*YUY2ToUV422Row)(const uint8* src_yuy2, uint8* dst_u, uint8* dst_v, 40741294d96d7dbf9bc215b09832a8336c5fb158f0bjohannkoenig@chromium.org int pix) = YUY2ToUV422Row_C; 40841294d96d7dbf9bc215b09832a8336c5fb158f0bjohannkoenig@chromium.org void (*YUY2ToYRow)(const uint8* src_yuy2, uint8* dst_y, int pix) = 40941294d96d7dbf9bc215b09832a8336c5fb158f0bjohannkoenig@chromium.org YUY2ToYRow_C; 41041294d96d7dbf9bc215b09832a8336c5fb158f0bjohannkoenig@chromium.org if (!src_y || !src_yuy2 || 41141294d96d7dbf9bc215b09832a8336c5fb158f0bjohannkoenig@chromium.org !dst_y || !dst_u || !dst_v || 41241294d96d7dbf9bc215b09832a8336c5fb158f0bjohannkoenig@chromium.org width <= 0 || height == 0) { 41341294d96d7dbf9bc215b09832a8336c5fb158f0bjohannkoenig@chromium.org return -1; 41441294d96d7dbf9bc215b09832a8336c5fb158f0bjohannkoenig@chromium.org } 41541294d96d7dbf9bc215b09832a8336c5fb158f0bjohannkoenig@chromium.org // Negative height means invert the image. 41641294d96d7dbf9bc215b09832a8336c5fb158f0bjohannkoenig@chromium.org if (height < 0) { 41741294d96d7dbf9bc215b09832a8336c5fb158f0bjohannkoenig@chromium.org height = -height; 41841294d96d7dbf9bc215b09832a8336c5fb158f0bjohannkoenig@chromium.org halfheight = (height + 1) >> 1; 41941294d96d7dbf9bc215b09832a8336c5fb158f0bjohannkoenig@chromium.org dst_y = dst_y + (height - 1) * dst_stride_y; 42041294d96d7dbf9bc215b09832a8336c5fb158f0bjohannkoenig@chromium.org dst_u = dst_u + (halfheight - 1) * dst_stride_u; 42141294d96d7dbf9bc215b09832a8336c5fb158f0bjohannkoenig@chromium.org dst_v = dst_v + (halfheight - 1) * dst_stride_v; 42241294d96d7dbf9bc215b09832a8336c5fb158f0bjohannkoenig@chromium.org dst_stride_y = -dst_stride_y; 42341294d96d7dbf9bc215b09832a8336c5fb158f0bjohannkoenig@chromium.org dst_stride_u = -dst_stride_u; 42441294d96d7dbf9bc215b09832a8336c5fb158f0bjohannkoenig@chromium.org dst_stride_v = -dst_stride_v; 42541294d96d7dbf9bc215b09832a8336c5fb158f0bjohannkoenig@chromium.org } 42641294d96d7dbf9bc215b09832a8336c5fb158f0bjohannkoenig@chromium.org // CopyRow for rows of just Y in Q420 copied to Y plane of I420. 42741294d96d7dbf9bc215b09832a8336c5fb158f0bjohannkoenig@chromium.org#if defined(HAS_COPYROW_NEON) 42841294d96d7dbf9bc215b09832a8336c5fb158f0bjohannkoenig@chromium.org if (TestCpuFlag(kCpuHasNEON) && IS_ALIGNED(width, 32)) { 42941294d96d7dbf9bc215b09832a8336c5fb158f0bjohannkoenig@chromium.org CopyRow = CopyRow_NEON; 43041294d96d7dbf9bc215b09832a8336c5fb158f0bjohannkoenig@chromium.org } 43141294d96d7dbf9bc215b09832a8336c5fb158f0bjohannkoenig@chromium.org#endif 43241294d96d7dbf9bc215b09832a8336c5fb158f0bjohannkoenig@chromium.org#if defined(HAS_COPYROW_X86) 43341294d96d7dbf9bc215b09832a8336c5fb158f0bjohannkoenig@chromium.org if (IS_ALIGNED(width, 4)) { 43441294d96d7dbf9bc215b09832a8336c5fb158f0bjohannkoenig@chromium.org CopyRow = CopyRow_X86; 43541294d96d7dbf9bc215b09832a8336c5fb158f0bjohannkoenig@chromium.org } 43641294d96d7dbf9bc215b09832a8336c5fb158f0bjohannkoenig@chromium.org#endif 43741294d96d7dbf9bc215b09832a8336c5fb158f0bjohannkoenig@chromium.org#if defined(HAS_COPYROW_SSE2) 43841294d96d7dbf9bc215b09832a8336c5fb158f0bjohannkoenig@chromium.org if (TestCpuFlag(kCpuHasSSE2) && IS_ALIGNED(width, 32) && 43941294d96d7dbf9bc215b09832a8336c5fb158f0bjohannkoenig@chromium.org IS_ALIGNED(src_y, 16) && IS_ALIGNED(src_stride_y, 16) && 44041294d96d7dbf9bc215b09832a8336c5fb158f0bjohannkoenig@chromium.org IS_ALIGNED(dst_y, 16) && IS_ALIGNED(dst_stride_y, 16)) { 44141294d96d7dbf9bc215b09832a8336c5fb158f0bjohannkoenig@chromium.org CopyRow = CopyRow_SSE2; 44241294d96d7dbf9bc215b09832a8336c5fb158f0bjohannkoenig@chromium.org } 44341294d96d7dbf9bc215b09832a8336c5fb158f0bjohannkoenig@chromium.org#endif 44441294d96d7dbf9bc215b09832a8336c5fb158f0bjohannkoenig@chromium.org#if defined(HAS_COPYROW_ERMS) 44541294d96d7dbf9bc215b09832a8336c5fb158f0bjohannkoenig@chromium.org if (TestCpuFlag(kCpuHasERMS)) { 44641294d96d7dbf9bc215b09832a8336c5fb158f0bjohannkoenig@chromium.org CopyRow = CopyRow_ERMS; 44741294d96d7dbf9bc215b09832a8336c5fb158f0bjohannkoenig@chromium.org } 44841294d96d7dbf9bc215b09832a8336c5fb158f0bjohannkoenig@chromium.org#endif 44941294d96d7dbf9bc215b09832a8336c5fb158f0bjohannkoenig@chromium.org#if defined(HAS_COPYROW_MIPS) 45041294d96d7dbf9bc215b09832a8336c5fb158f0bjohannkoenig@chromium.org if (TestCpuFlag(kCpuHasMIPS)) { 45141294d96d7dbf9bc215b09832a8336c5fb158f0bjohannkoenig@chromium.org CopyRow = CopyRow_MIPS; 45241294d96d7dbf9bc215b09832a8336c5fb158f0bjohannkoenig@chromium.org } 45341294d96d7dbf9bc215b09832a8336c5fb158f0bjohannkoenig@chromium.org#endif 45441294d96d7dbf9bc215b09832a8336c5fb158f0bjohannkoenig@chromium.org 45541294d96d7dbf9bc215b09832a8336c5fb158f0bjohannkoenig@chromium.org#if defined(HAS_YUY2TOYROW_SSE2) 45641294d96d7dbf9bc215b09832a8336c5fb158f0bjohannkoenig@chromium.org if (TestCpuFlag(kCpuHasSSE2) && width >= 16) { 45741294d96d7dbf9bc215b09832a8336c5fb158f0bjohannkoenig@chromium.org YUY2ToUV422Row = YUY2ToUV422Row_Any_SSE2; 45841294d96d7dbf9bc215b09832a8336c5fb158f0bjohannkoenig@chromium.org YUY2ToYRow = YUY2ToYRow_Any_SSE2; 45941294d96d7dbf9bc215b09832a8336c5fb158f0bjohannkoenig@chromium.org if (IS_ALIGNED(width, 16)) { 46041294d96d7dbf9bc215b09832a8336c5fb158f0bjohannkoenig@chromium.org YUY2ToUV422Row = YUY2ToUV422Row_Unaligned_SSE2; 46141294d96d7dbf9bc215b09832a8336c5fb158f0bjohannkoenig@chromium.org YUY2ToYRow = YUY2ToYRow_Unaligned_SSE2; 46241294d96d7dbf9bc215b09832a8336c5fb158f0bjohannkoenig@chromium.org if (IS_ALIGNED(src_yuy2, 16) && IS_ALIGNED(src_stride_yuy2, 16)) { 46341294d96d7dbf9bc215b09832a8336c5fb158f0bjohannkoenig@chromium.org YUY2ToUV422Row = YUY2ToUV422Row_SSE2; 46441294d96d7dbf9bc215b09832a8336c5fb158f0bjohannkoenig@chromium.org if (IS_ALIGNED(dst_y, 16) && IS_ALIGNED(dst_stride_y, 16)) { 46541294d96d7dbf9bc215b09832a8336c5fb158f0bjohannkoenig@chromium.org YUY2ToYRow = YUY2ToYRow_SSE2; 46641294d96d7dbf9bc215b09832a8336c5fb158f0bjohannkoenig@chromium.org } 46741294d96d7dbf9bc215b09832a8336c5fb158f0bjohannkoenig@chromium.org } 46841294d96d7dbf9bc215b09832a8336c5fb158f0bjohannkoenig@chromium.org } 46941294d96d7dbf9bc215b09832a8336c5fb158f0bjohannkoenig@chromium.org } 47041294d96d7dbf9bc215b09832a8336c5fb158f0bjohannkoenig@chromium.org#endif 47141294d96d7dbf9bc215b09832a8336c5fb158f0bjohannkoenig@chromium.org#if defined(HAS_YUY2TOYROW_AVX2) 47241294d96d7dbf9bc215b09832a8336c5fb158f0bjohannkoenig@chromium.org if (TestCpuFlag(kCpuHasAVX2) && width >= 32) { 47341294d96d7dbf9bc215b09832a8336c5fb158f0bjohannkoenig@chromium.org YUY2ToUV422Row = YUY2ToUV422Row_Any_AVX2; 47441294d96d7dbf9bc215b09832a8336c5fb158f0bjohannkoenig@chromium.org YUY2ToYRow = YUY2ToYRow_Any_AVX2; 47541294d96d7dbf9bc215b09832a8336c5fb158f0bjohannkoenig@chromium.org if (IS_ALIGNED(width, 32)) { 47641294d96d7dbf9bc215b09832a8336c5fb158f0bjohannkoenig@chromium.org YUY2ToUV422Row = YUY2ToUV422Row_AVX2; 47741294d96d7dbf9bc215b09832a8336c5fb158f0bjohannkoenig@chromium.org YUY2ToYRow = YUY2ToYRow_AVX2; 47841294d96d7dbf9bc215b09832a8336c5fb158f0bjohannkoenig@chromium.org } 47941294d96d7dbf9bc215b09832a8336c5fb158f0bjohannkoenig@chromium.org } 48041294d96d7dbf9bc215b09832a8336c5fb158f0bjohannkoenig@chromium.org#endif 48141294d96d7dbf9bc215b09832a8336c5fb158f0bjohannkoenig@chromium.org#if defined(HAS_YUY2TOYROW_NEON) 48241294d96d7dbf9bc215b09832a8336c5fb158f0bjohannkoenig@chromium.org if (TestCpuFlag(kCpuHasNEON) && width >= 8) { 48341294d96d7dbf9bc215b09832a8336c5fb158f0bjohannkoenig@chromium.org YUY2ToYRow = YUY2ToYRow_Any_NEON; 48441294d96d7dbf9bc215b09832a8336c5fb158f0bjohannkoenig@chromium.org if (width >= 16) { 48541294d96d7dbf9bc215b09832a8336c5fb158f0bjohannkoenig@chromium.org YUY2ToUV422Row = YUY2ToUV422Row_Any_NEON; 48641294d96d7dbf9bc215b09832a8336c5fb158f0bjohannkoenig@chromium.org } 48741294d96d7dbf9bc215b09832a8336c5fb158f0bjohannkoenig@chromium.org if (IS_ALIGNED(width, 16)) { 48841294d96d7dbf9bc215b09832a8336c5fb158f0bjohannkoenig@chromium.org YUY2ToYRow = YUY2ToYRow_NEON; 48941294d96d7dbf9bc215b09832a8336c5fb158f0bjohannkoenig@chromium.org YUY2ToUV422Row = YUY2ToUV422Row_NEON; 49041294d96d7dbf9bc215b09832a8336c5fb158f0bjohannkoenig@chromium.org } 49141294d96d7dbf9bc215b09832a8336c5fb158f0bjohannkoenig@chromium.org } 49241294d96d7dbf9bc215b09832a8336c5fb158f0bjohannkoenig@chromium.org#endif 49341294d96d7dbf9bc215b09832a8336c5fb158f0bjohannkoenig@chromium.org 49441294d96d7dbf9bc215b09832a8336c5fb158f0bjohannkoenig@chromium.org for (y = 0; y < height - 1; y += 2) { 49541294d96d7dbf9bc215b09832a8336c5fb158f0bjohannkoenig@chromium.org CopyRow(src_y, dst_y, width); 49641294d96d7dbf9bc215b09832a8336c5fb158f0bjohannkoenig@chromium.org src_y += src_stride_y; 49741294d96d7dbf9bc215b09832a8336c5fb158f0bjohannkoenig@chromium.org dst_y += dst_stride_y; 49841294d96d7dbf9bc215b09832a8336c5fb158f0bjohannkoenig@chromium.org 49941294d96d7dbf9bc215b09832a8336c5fb158f0bjohannkoenig@chromium.org YUY2ToUV422Row(src_yuy2, dst_u, dst_v, width); 50041294d96d7dbf9bc215b09832a8336c5fb158f0bjohannkoenig@chromium.org YUY2ToYRow(src_yuy2, dst_y, width); 50141294d96d7dbf9bc215b09832a8336c5fb158f0bjohannkoenig@chromium.org src_yuy2 += src_stride_yuy2; 50241294d96d7dbf9bc215b09832a8336c5fb158f0bjohannkoenig@chromium.org dst_y += dst_stride_y; 50341294d96d7dbf9bc215b09832a8336c5fb158f0bjohannkoenig@chromium.org dst_u += dst_stride_u; 50441294d96d7dbf9bc215b09832a8336c5fb158f0bjohannkoenig@chromium.org dst_v += dst_stride_v; 50541294d96d7dbf9bc215b09832a8336c5fb158f0bjohannkoenig@chromium.org } 50641294d96d7dbf9bc215b09832a8336c5fb158f0bjohannkoenig@chromium.org if (height & 1) { 50741294d96d7dbf9bc215b09832a8336c5fb158f0bjohannkoenig@chromium.org CopyRow(src_y, dst_y, width); 50841294d96d7dbf9bc215b09832a8336c5fb158f0bjohannkoenig@chromium.org YUY2ToUV422Row(src_yuy2, dst_u, dst_v, width); 50941294d96d7dbf9bc215b09832a8336c5fb158f0bjohannkoenig@chromium.org } 51041294d96d7dbf9bc215b09832a8336c5fb158f0bjohannkoenig@chromium.org return 0; 51141294d96d7dbf9bc215b09832a8336c5fb158f0bjohannkoenig@chromium.org} 51241294d96d7dbf9bc215b09832a8336c5fb158f0bjohannkoenig@chromium.org 51341294d96d7dbf9bc215b09832a8336c5fb158f0bjohannkoenig@chromium.org// Convert YUY2 to I420. 51441294d96d7dbf9bc215b09832a8336c5fb158f0bjohannkoenig@chromium.orgLIBYUV_API 51541294d96d7dbf9bc215b09832a8336c5fb158f0bjohannkoenig@chromium.orgint YUY2ToI420(const uint8* src_yuy2, int src_stride_yuy2, 51641294d96d7dbf9bc215b09832a8336c5fb158f0bjohannkoenig@chromium.org uint8* dst_y, int dst_stride_y, 51741294d96d7dbf9bc215b09832a8336c5fb158f0bjohannkoenig@chromium.org uint8* dst_u, int dst_stride_u, 51841294d96d7dbf9bc215b09832a8336c5fb158f0bjohannkoenig@chromium.org uint8* dst_v, int dst_stride_v, 51941294d96d7dbf9bc215b09832a8336c5fb158f0bjohannkoenig@chromium.org int width, int height) { 52041294d96d7dbf9bc215b09832a8336c5fb158f0bjohannkoenig@chromium.org int y; 52141294d96d7dbf9bc215b09832a8336c5fb158f0bjohannkoenig@chromium.org void (*YUY2ToUVRow)(const uint8* src_yuy2, int src_stride_yuy2, 52241294d96d7dbf9bc215b09832a8336c5fb158f0bjohannkoenig@chromium.org uint8* dst_u, uint8* dst_v, int pix) = YUY2ToUVRow_C; 52341294d96d7dbf9bc215b09832a8336c5fb158f0bjohannkoenig@chromium.org void (*YUY2ToYRow)(const uint8* src_yuy2, 52441294d96d7dbf9bc215b09832a8336c5fb158f0bjohannkoenig@chromium.org uint8* dst_y, int pix) = YUY2ToYRow_C; 52541294d96d7dbf9bc215b09832a8336c5fb158f0bjohannkoenig@chromium.org // Negative height means invert the image. 52641294d96d7dbf9bc215b09832a8336c5fb158f0bjohannkoenig@chromium.org if (height < 0) { 52741294d96d7dbf9bc215b09832a8336c5fb158f0bjohannkoenig@chromium.org height = -height; 52841294d96d7dbf9bc215b09832a8336c5fb158f0bjohannkoenig@chromium.org src_yuy2 = src_yuy2 + (height - 1) * src_stride_yuy2; 52941294d96d7dbf9bc215b09832a8336c5fb158f0bjohannkoenig@chromium.org src_stride_yuy2 = -src_stride_yuy2; 53041294d96d7dbf9bc215b09832a8336c5fb158f0bjohannkoenig@chromium.org } 53141294d96d7dbf9bc215b09832a8336c5fb158f0bjohannkoenig@chromium.org#if defined(HAS_YUY2TOYROW_SSE2) 53241294d96d7dbf9bc215b09832a8336c5fb158f0bjohannkoenig@chromium.org if (TestCpuFlag(kCpuHasSSE2) && width >= 16) { 53341294d96d7dbf9bc215b09832a8336c5fb158f0bjohannkoenig@chromium.org YUY2ToUVRow = YUY2ToUVRow_Any_SSE2; 53441294d96d7dbf9bc215b09832a8336c5fb158f0bjohannkoenig@chromium.org YUY2ToYRow = YUY2ToYRow_Any_SSE2; 53541294d96d7dbf9bc215b09832a8336c5fb158f0bjohannkoenig@chromium.org if (IS_ALIGNED(width, 16)) { 53641294d96d7dbf9bc215b09832a8336c5fb158f0bjohannkoenig@chromium.org YUY2ToUVRow = YUY2ToUVRow_Unaligned_SSE2; 53741294d96d7dbf9bc215b09832a8336c5fb158f0bjohannkoenig@chromium.org YUY2ToYRow = YUY2ToYRow_Unaligned_SSE2; 53841294d96d7dbf9bc215b09832a8336c5fb158f0bjohannkoenig@chromium.org if (IS_ALIGNED(src_yuy2, 16) && IS_ALIGNED(src_stride_yuy2, 16)) { 53941294d96d7dbf9bc215b09832a8336c5fb158f0bjohannkoenig@chromium.org YUY2ToUVRow = YUY2ToUVRow_SSE2; 54041294d96d7dbf9bc215b09832a8336c5fb158f0bjohannkoenig@chromium.org if (IS_ALIGNED(dst_y, 16) && IS_ALIGNED(dst_stride_y, 16)) { 54141294d96d7dbf9bc215b09832a8336c5fb158f0bjohannkoenig@chromium.org YUY2ToYRow = YUY2ToYRow_SSE2; 54241294d96d7dbf9bc215b09832a8336c5fb158f0bjohannkoenig@chromium.org } 54341294d96d7dbf9bc215b09832a8336c5fb158f0bjohannkoenig@chromium.org } 54441294d96d7dbf9bc215b09832a8336c5fb158f0bjohannkoenig@chromium.org } 54541294d96d7dbf9bc215b09832a8336c5fb158f0bjohannkoenig@chromium.org } 54641294d96d7dbf9bc215b09832a8336c5fb158f0bjohannkoenig@chromium.org#endif 54741294d96d7dbf9bc215b09832a8336c5fb158f0bjohannkoenig@chromium.org#if defined(HAS_YUY2TOYROW_AVX2) 54841294d96d7dbf9bc215b09832a8336c5fb158f0bjohannkoenig@chromium.org if (TestCpuFlag(kCpuHasAVX2) && width >= 32) { 54941294d96d7dbf9bc215b09832a8336c5fb158f0bjohannkoenig@chromium.org YUY2ToUVRow = YUY2ToUVRow_Any_AVX2; 55041294d96d7dbf9bc215b09832a8336c5fb158f0bjohannkoenig@chromium.org YUY2ToYRow = YUY2ToYRow_Any_AVX2; 55141294d96d7dbf9bc215b09832a8336c5fb158f0bjohannkoenig@chromium.org if (IS_ALIGNED(width, 32)) { 55241294d96d7dbf9bc215b09832a8336c5fb158f0bjohannkoenig@chromium.org YUY2ToUVRow = YUY2ToUVRow_AVX2; 55341294d96d7dbf9bc215b09832a8336c5fb158f0bjohannkoenig@chromium.org YUY2ToYRow = YUY2ToYRow_AVX2; 55441294d96d7dbf9bc215b09832a8336c5fb158f0bjohannkoenig@chromium.org } 55541294d96d7dbf9bc215b09832a8336c5fb158f0bjohannkoenig@chromium.org } 55641294d96d7dbf9bc215b09832a8336c5fb158f0bjohannkoenig@chromium.org#endif 55741294d96d7dbf9bc215b09832a8336c5fb158f0bjohannkoenig@chromium.org#if defined(HAS_YUY2TOYROW_NEON) 55841294d96d7dbf9bc215b09832a8336c5fb158f0bjohannkoenig@chromium.org if (TestCpuFlag(kCpuHasNEON) && width >= 8) { 55941294d96d7dbf9bc215b09832a8336c5fb158f0bjohannkoenig@chromium.org YUY2ToYRow = YUY2ToYRow_Any_NEON; 56041294d96d7dbf9bc215b09832a8336c5fb158f0bjohannkoenig@chromium.org if (width >= 16) { 56141294d96d7dbf9bc215b09832a8336c5fb158f0bjohannkoenig@chromium.org YUY2ToUVRow = YUY2ToUVRow_Any_NEON; 56241294d96d7dbf9bc215b09832a8336c5fb158f0bjohannkoenig@chromium.org } 56341294d96d7dbf9bc215b09832a8336c5fb158f0bjohannkoenig@chromium.org if (IS_ALIGNED(width, 16)) { 56441294d96d7dbf9bc215b09832a8336c5fb158f0bjohannkoenig@chromium.org YUY2ToYRow = YUY2ToYRow_NEON; 56541294d96d7dbf9bc215b09832a8336c5fb158f0bjohannkoenig@chromium.org YUY2ToUVRow = YUY2ToUVRow_NEON; 56641294d96d7dbf9bc215b09832a8336c5fb158f0bjohannkoenig@chromium.org } 56741294d96d7dbf9bc215b09832a8336c5fb158f0bjohannkoenig@chromium.org } 56841294d96d7dbf9bc215b09832a8336c5fb158f0bjohannkoenig@chromium.org#endif 56941294d96d7dbf9bc215b09832a8336c5fb158f0bjohannkoenig@chromium.org 57041294d96d7dbf9bc215b09832a8336c5fb158f0bjohannkoenig@chromium.org for (y = 0; y < height - 1; y += 2) { 57141294d96d7dbf9bc215b09832a8336c5fb158f0bjohannkoenig@chromium.org YUY2ToUVRow(src_yuy2, src_stride_yuy2, dst_u, dst_v, width); 57241294d96d7dbf9bc215b09832a8336c5fb158f0bjohannkoenig@chromium.org YUY2ToYRow(src_yuy2, dst_y, width); 57341294d96d7dbf9bc215b09832a8336c5fb158f0bjohannkoenig@chromium.org YUY2ToYRow(src_yuy2 + src_stride_yuy2, dst_y + dst_stride_y, width); 57441294d96d7dbf9bc215b09832a8336c5fb158f0bjohannkoenig@chromium.org src_yuy2 += src_stride_yuy2 * 2; 57541294d96d7dbf9bc215b09832a8336c5fb158f0bjohannkoenig@chromium.org dst_y += dst_stride_y * 2; 57641294d96d7dbf9bc215b09832a8336c5fb158f0bjohannkoenig@chromium.org dst_u += dst_stride_u; 57741294d96d7dbf9bc215b09832a8336c5fb158f0bjohannkoenig@chromium.org dst_v += dst_stride_v; 57841294d96d7dbf9bc215b09832a8336c5fb158f0bjohannkoenig@chromium.org } 57941294d96d7dbf9bc215b09832a8336c5fb158f0bjohannkoenig@chromium.org if (height & 1) { 58041294d96d7dbf9bc215b09832a8336c5fb158f0bjohannkoenig@chromium.org YUY2ToUVRow(src_yuy2, 0, dst_u, dst_v, width); 58141294d96d7dbf9bc215b09832a8336c5fb158f0bjohannkoenig@chromium.org YUY2ToYRow(src_yuy2, dst_y, width); 58241294d96d7dbf9bc215b09832a8336c5fb158f0bjohannkoenig@chromium.org } 58341294d96d7dbf9bc215b09832a8336c5fb158f0bjohannkoenig@chromium.org return 0; 58441294d96d7dbf9bc215b09832a8336c5fb158f0bjohannkoenig@chromium.org} 58541294d96d7dbf9bc215b09832a8336c5fb158f0bjohannkoenig@chromium.org 58641294d96d7dbf9bc215b09832a8336c5fb158f0bjohannkoenig@chromium.org// Convert UYVY to I420. 58741294d96d7dbf9bc215b09832a8336c5fb158f0bjohannkoenig@chromium.orgLIBYUV_API 58841294d96d7dbf9bc215b09832a8336c5fb158f0bjohannkoenig@chromium.orgint UYVYToI420(const uint8* src_uyvy, int src_stride_uyvy, 58941294d96d7dbf9bc215b09832a8336c5fb158f0bjohannkoenig@chromium.org uint8* dst_y, int dst_stride_y, 59041294d96d7dbf9bc215b09832a8336c5fb158f0bjohannkoenig@chromium.org uint8* dst_u, int dst_stride_u, 59141294d96d7dbf9bc215b09832a8336c5fb158f0bjohannkoenig@chromium.org uint8* dst_v, int dst_stride_v, 59241294d96d7dbf9bc215b09832a8336c5fb158f0bjohannkoenig@chromium.org int width, int height) { 59341294d96d7dbf9bc215b09832a8336c5fb158f0bjohannkoenig@chromium.org int y; 59441294d96d7dbf9bc215b09832a8336c5fb158f0bjohannkoenig@chromium.org void (*UYVYToUVRow)(const uint8* src_uyvy, int src_stride_uyvy, 59541294d96d7dbf9bc215b09832a8336c5fb158f0bjohannkoenig@chromium.org uint8* dst_u, uint8* dst_v, int pix) = UYVYToUVRow_C; 59641294d96d7dbf9bc215b09832a8336c5fb158f0bjohannkoenig@chromium.org void (*UYVYToYRow)(const uint8* src_uyvy, 59741294d96d7dbf9bc215b09832a8336c5fb158f0bjohannkoenig@chromium.org uint8* dst_y, int pix) = UYVYToYRow_C; 59841294d96d7dbf9bc215b09832a8336c5fb158f0bjohannkoenig@chromium.org // Negative height means invert the image. 59941294d96d7dbf9bc215b09832a8336c5fb158f0bjohannkoenig@chromium.org if (height < 0) { 60041294d96d7dbf9bc215b09832a8336c5fb158f0bjohannkoenig@chromium.org height = -height; 60141294d96d7dbf9bc215b09832a8336c5fb158f0bjohannkoenig@chromium.org src_uyvy = src_uyvy + (height - 1) * src_stride_uyvy; 60241294d96d7dbf9bc215b09832a8336c5fb158f0bjohannkoenig@chromium.org src_stride_uyvy = -src_stride_uyvy; 60341294d96d7dbf9bc215b09832a8336c5fb158f0bjohannkoenig@chromium.org } 60441294d96d7dbf9bc215b09832a8336c5fb158f0bjohannkoenig@chromium.org#if defined(HAS_UYVYTOYROW_SSE2) 60541294d96d7dbf9bc215b09832a8336c5fb158f0bjohannkoenig@chromium.org if (TestCpuFlag(kCpuHasSSE2) && width >= 16) { 60641294d96d7dbf9bc215b09832a8336c5fb158f0bjohannkoenig@chromium.org UYVYToUVRow = UYVYToUVRow_Any_SSE2; 60741294d96d7dbf9bc215b09832a8336c5fb158f0bjohannkoenig@chromium.org UYVYToYRow = UYVYToYRow_Any_SSE2; 60841294d96d7dbf9bc215b09832a8336c5fb158f0bjohannkoenig@chromium.org if (IS_ALIGNED(width, 16)) { 60941294d96d7dbf9bc215b09832a8336c5fb158f0bjohannkoenig@chromium.org UYVYToUVRow = UYVYToUVRow_Unaligned_SSE2; 61041294d96d7dbf9bc215b09832a8336c5fb158f0bjohannkoenig@chromium.org UYVYToYRow = UYVYToYRow_Unaligned_SSE2; 61141294d96d7dbf9bc215b09832a8336c5fb158f0bjohannkoenig@chromium.org if (IS_ALIGNED(src_uyvy, 16) && IS_ALIGNED(src_stride_uyvy, 16)) { 61241294d96d7dbf9bc215b09832a8336c5fb158f0bjohannkoenig@chromium.org UYVYToUVRow = UYVYToUVRow_SSE2; 61341294d96d7dbf9bc215b09832a8336c5fb158f0bjohannkoenig@chromium.org if (IS_ALIGNED(dst_y, 16) && IS_ALIGNED(dst_stride_y, 16)) { 61441294d96d7dbf9bc215b09832a8336c5fb158f0bjohannkoenig@chromium.org UYVYToYRow = UYVYToYRow_SSE2; 61541294d96d7dbf9bc215b09832a8336c5fb158f0bjohannkoenig@chromium.org } 61641294d96d7dbf9bc215b09832a8336c5fb158f0bjohannkoenig@chromium.org } 61741294d96d7dbf9bc215b09832a8336c5fb158f0bjohannkoenig@chromium.org } 61841294d96d7dbf9bc215b09832a8336c5fb158f0bjohannkoenig@chromium.org } 61941294d96d7dbf9bc215b09832a8336c5fb158f0bjohannkoenig@chromium.org#endif 62041294d96d7dbf9bc215b09832a8336c5fb158f0bjohannkoenig@chromium.org#if defined(HAS_UYVYTOYROW_AVX2) 62141294d96d7dbf9bc215b09832a8336c5fb158f0bjohannkoenig@chromium.org if (TestCpuFlag(kCpuHasAVX2) && width >= 32) { 62241294d96d7dbf9bc215b09832a8336c5fb158f0bjohannkoenig@chromium.org UYVYToUVRow = UYVYToUVRow_Any_AVX2; 62341294d96d7dbf9bc215b09832a8336c5fb158f0bjohannkoenig@chromium.org UYVYToYRow = UYVYToYRow_Any_AVX2; 62441294d96d7dbf9bc215b09832a8336c5fb158f0bjohannkoenig@chromium.org if (IS_ALIGNED(width, 32)) { 62541294d96d7dbf9bc215b09832a8336c5fb158f0bjohannkoenig@chromium.org UYVYToUVRow = UYVYToUVRow_AVX2; 62641294d96d7dbf9bc215b09832a8336c5fb158f0bjohannkoenig@chromium.org UYVYToYRow = UYVYToYRow_AVX2; 62741294d96d7dbf9bc215b09832a8336c5fb158f0bjohannkoenig@chromium.org } 62841294d96d7dbf9bc215b09832a8336c5fb158f0bjohannkoenig@chromium.org } 62941294d96d7dbf9bc215b09832a8336c5fb158f0bjohannkoenig@chromium.org#endif 63041294d96d7dbf9bc215b09832a8336c5fb158f0bjohannkoenig@chromium.org#if defined(HAS_UYVYTOYROW_NEON) 63141294d96d7dbf9bc215b09832a8336c5fb158f0bjohannkoenig@chromium.org if (TestCpuFlag(kCpuHasNEON) && width >= 8) { 63241294d96d7dbf9bc215b09832a8336c5fb158f0bjohannkoenig@chromium.org UYVYToYRow = UYVYToYRow_Any_NEON; 63341294d96d7dbf9bc215b09832a8336c5fb158f0bjohannkoenig@chromium.org if (width >= 16) { 63441294d96d7dbf9bc215b09832a8336c5fb158f0bjohannkoenig@chromium.org UYVYToUVRow = UYVYToUVRow_Any_NEON; 63541294d96d7dbf9bc215b09832a8336c5fb158f0bjohannkoenig@chromium.org } 63641294d96d7dbf9bc215b09832a8336c5fb158f0bjohannkoenig@chromium.org if (IS_ALIGNED(width, 16)) { 63741294d96d7dbf9bc215b09832a8336c5fb158f0bjohannkoenig@chromium.org UYVYToYRow = UYVYToYRow_NEON; 63841294d96d7dbf9bc215b09832a8336c5fb158f0bjohannkoenig@chromium.org UYVYToUVRow = UYVYToUVRow_NEON; 63941294d96d7dbf9bc215b09832a8336c5fb158f0bjohannkoenig@chromium.org } 64041294d96d7dbf9bc215b09832a8336c5fb158f0bjohannkoenig@chromium.org } 64141294d96d7dbf9bc215b09832a8336c5fb158f0bjohannkoenig@chromium.org#endif 64241294d96d7dbf9bc215b09832a8336c5fb158f0bjohannkoenig@chromium.org 64341294d96d7dbf9bc215b09832a8336c5fb158f0bjohannkoenig@chromium.org for (y = 0; y < height - 1; y += 2) { 64441294d96d7dbf9bc215b09832a8336c5fb158f0bjohannkoenig@chromium.org UYVYToUVRow(src_uyvy, src_stride_uyvy, dst_u, dst_v, width); 64541294d96d7dbf9bc215b09832a8336c5fb158f0bjohannkoenig@chromium.org UYVYToYRow(src_uyvy, dst_y, width); 64641294d96d7dbf9bc215b09832a8336c5fb158f0bjohannkoenig@chromium.org UYVYToYRow(src_uyvy + src_stride_uyvy, dst_y + dst_stride_y, width); 64741294d96d7dbf9bc215b09832a8336c5fb158f0bjohannkoenig@chromium.org src_uyvy += src_stride_uyvy * 2; 64841294d96d7dbf9bc215b09832a8336c5fb158f0bjohannkoenig@chromium.org dst_y += dst_stride_y * 2; 64941294d96d7dbf9bc215b09832a8336c5fb158f0bjohannkoenig@chromium.org dst_u += dst_stride_u; 65041294d96d7dbf9bc215b09832a8336c5fb158f0bjohannkoenig@chromium.org dst_v += dst_stride_v; 65141294d96d7dbf9bc215b09832a8336c5fb158f0bjohannkoenig@chromium.org } 65241294d96d7dbf9bc215b09832a8336c5fb158f0bjohannkoenig@chromium.org if (height & 1) { 65341294d96d7dbf9bc215b09832a8336c5fb158f0bjohannkoenig@chromium.org UYVYToUVRow(src_uyvy, 0, dst_u, dst_v, width); 65441294d96d7dbf9bc215b09832a8336c5fb158f0bjohannkoenig@chromium.org UYVYToYRow(src_uyvy, dst_y, width); 65541294d96d7dbf9bc215b09832a8336c5fb158f0bjohannkoenig@chromium.org } 65641294d96d7dbf9bc215b09832a8336c5fb158f0bjohannkoenig@chromium.org return 0; 65741294d96d7dbf9bc215b09832a8336c5fb158f0bjohannkoenig@chromium.org} 65841294d96d7dbf9bc215b09832a8336c5fb158f0bjohannkoenig@chromium.org 65941294d96d7dbf9bc215b09832a8336c5fb158f0bjohannkoenig@chromium.org// Convert ARGB to I420. 66041294d96d7dbf9bc215b09832a8336c5fb158f0bjohannkoenig@chromium.orgLIBYUV_API 66141294d96d7dbf9bc215b09832a8336c5fb158f0bjohannkoenig@chromium.orgint ARGBToI420(const uint8* src_argb, int src_stride_argb, 66241294d96d7dbf9bc215b09832a8336c5fb158f0bjohannkoenig@chromium.org uint8* dst_y, int dst_stride_y, 66341294d96d7dbf9bc215b09832a8336c5fb158f0bjohannkoenig@chromium.org uint8* dst_u, int dst_stride_u, 66441294d96d7dbf9bc215b09832a8336c5fb158f0bjohannkoenig@chromium.org uint8* dst_v, int dst_stride_v, 66541294d96d7dbf9bc215b09832a8336c5fb158f0bjohannkoenig@chromium.org int width, int height) { 66641294d96d7dbf9bc215b09832a8336c5fb158f0bjohannkoenig@chromium.org int y; 66741294d96d7dbf9bc215b09832a8336c5fb158f0bjohannkoenig@chromium.org void (*ARGBToUVRow)(const uint8* src_argb0, int src_stride_argb, 66841294d96d7dbf9bc215b09832a8336c5fb158f0bjohannkoenig@chromium.org uint8* dst_u, uint8* dst_v, int width) = ARGBToUVRow_C; 66941294d96d7dbf9bc215b09832a8336c5fb158f0bjohannkoenig@chromium.org void (*ARGBToYRow)(const uint8* src_argb, uint8* dst_y, int pix) = 67041294d96d7dbf9bc215b09832a8336c5fb158f0bjohannkoenig@chromium.org ARGBToYRow_C; 67141294d96d7dbf9bc215b09832a8336c5fb158f0bjohannkoenig@chromium.org if (!src_argb || 67241294d96d7dbf9bc215b09832a8336c5fb158f0bjohannkoenig@chromium.org !dst_y || !dst_u || !dst_v || 67341294d96d7dbf9bc215b09832a8336c5fb158f0bjohannkoenig@chromium.org width <= 0 || height == 0) { 67441294d96d7dbf9bc215b09832a8336c5fb158f0bjohannkoenig@chromium.org return -1; 67541294d96d7dbf9bc215b09832a8336c5fb158f0bjohannkoenig@chromium.org } 67641294d96d7dbf9bc215b09832a8336c5fb158f0bjohannkoenig@chromium.org // Negative height means invert the image. 67741294d96d7dbf9bc215b09832a8336c5fb158f0bjohannkoenig@chromium.org if (height < 0) { 67841294d96d7dbf9bc215b09832a8336c5fb158f0bjohannkoenig@chromium.org height = -height; 67941294d96d7dbf9bc215b09832a8336c5fb158f0bjohannkoenig@chromium.org src_argb = src_argb + (height - 1) * src_stride_argb; 68041294d96d7dbf9bc215b09832a8336c5fb158f0bjohannkoenig@chromium.org src_stride_argb = -src_stride_argb; 68141294d96d7dbf9bc215b09832a8336c5fb158f0bjohannkoenig@chromium.org } 68241294d96d7dbf9bc215b09832a8336c5fb158f0bjohannkoenig@chromium.org#if defined(HAS_ARGBTOYROW_SSSE3) && defined(HAS_ARGBTOUVROW_SSSE3) 68341294d96d7dbf9bc215b09832a8336c5fb158f0bjohannkoenig@chromium.org if (TestCpuFlag(kCpuHasSSSE3) && width >= 16) { 68441294d96d7dbf9bc215b09832a8336c5fb158f0bjohannkoenig@chromium.org ARGBToUVRow = ARGBToUVRow_Any_SSSE3; 68541294d96d7dbf9bc215b09832a8336c5fb158f0bjohannkoenig@chromium.org ARGBToYRow = ARGBToYRow_Any_SSSE3; 68641294d96d7dbf9bc215b09832a8336c5fb158f0bjohannkoenig@chromium.org if (IS_ALIGNED(width, 16)) { 68741294d96d7dbf9bc215b09832a8336c5fb158f0bjohannkoenig@chromium.org ARGBToUVRow = ARGBToUVRow_Unaligned_SSSE3; 68841294d96d7dbf9bc215b09832a8336c5fb158f0bjohannkoenig@chromium.org ARGBToYRow = ARGBToYRow_Unaligned_SSSE3; 68941294d96d7dbf9bc215b09832a8336c5fb158f0bjohannkoenig@chromium.org if (IS_ALIGNED(src_argb, 16) && IS_ALIGNED(src_stride_argb, 16)) { 69041294d96d7dbf9bc215b09832a8336c5fb158f0bjohannkoenig@chromium.org ARGBToUVRow = ARGBToUVRow_SSSE3; 69141294d96d7dbf9bc215b09832a8336c5fb158f0bjohannkoenig@chromium.org if (IS_ALIGNED(dst_y, 16) && IS_ALIGNED(dst_stride_y, 16)) { 69241294d96d7dbf9bc215b09832a8336c5fb158f0bjohannkoenig@chromium.org ARGBToYRow = ARGBToYRow_SSSE3; 69341294d96d7dbf9bc215b09832a8336c5fb158f0bjohannkoenig@chromium.org } 69441294d96d7dbf9bc215b09832a8336c5fb158f0bjohannkoenig@chromium.org } 69541294d96d7dbf9bc215b09832a8336c5fb158f0bjohannkoenig@chromium.org } 69641294d96d7dbf9bc215b09832a8336c5fb158f0bjohannkoenig@chromium.org } 69741294d96d7dbf9bc215b09832a8336c5fb158f0bjohannkoenig@chromium.org#endif 69841294d96d7dbf9bc215b09832a8336c5fb158f0bjohannkoenig@chromium.org#if defined(HAS_ARGBTOYROW_AVX2) && defined(HAS_ARGBTOUVROW_AVX2) 69941294d96d7dbf9bc215b09832a8336c5fb158f0bjohannkoenig@chromium.org if (TestCpuFlag(kCpuHasAVX2) && width >= 32) { 70041294d96d7dbf9bc215b09832a8336c5fb158f0bjohannkoenig@chromium.org ARGBToUVRow = ARGBToUVRow_Any_AVX2; 70141294d96d7dbf9bc215b09832a8336c5fb158f0bjohannkoenig@chromium.org ARGBToYRow = ARGBToYRow_Any_AVX2; 70241294d96d7dbf9bc215b09832a8336c5fb158f0bjohannkoenig@chromium.org if (IS_ALIGNED(width, 32)) { 70341294d96d7dbf9bc215b09832a8336c5fb158f0bjohannkoenig@chromium.org ARGBToUVRow = ARGBToUVRow_AVX2; 70441294d96d7dbf9bc215b09832a8336c5fb158f0bjohannkoenig@chromium.org ARGBToYRow = ARGBToYRow_AVX2; 70541294d96d7dbf9bc215b09832a8336c5fb158f0bjohannkoenig@chromium.org } 70641294d96d7dbf9bc215b09832a8336c5fb158f0bjohannkoenig@chromium.org } 70741294d96d7dbf9bc215b09832a8336c5fb158f0bjohannkoenig@chromium.org#endif 70841294d96d7dbf9bc215b09832a8336c5fb158f0bjohannkoenig@chromium.org#if defined(HAS_ARGBTOYROW_NEON) 70941294d96d7dbf9bc215b09832a8336c5fb158f0bjohannkoenig@chromium.org if (TestCpuFlag(kCpuHasNEON) && width >= 8) { 71041294d96d7dbf9bc215b09832a8336c5fb158f0bjohannkoenig@chromium.org ARGBToYRow = ARGBToYRow_Any_NEON; 71141294d96d7dbf9bc215b09832a8336c5fb158f0bjohannkoenig@chromium.org if (IS_ALIGNED(width, 8)) { 71241294d96d7dbf9bc215b09832a8336c5fb158f0bjohannkoenig@chromium.org ARGBToYRow = ARGBToYRow_NEON; 71341294d96d7dbf9bc215b09832a8336c5fb158f0bjohannkoenig@chromium.org } 714d95585fb0ec024f6abd96f7b02e0df58019d46afjohannkoenig@chromium.org } 715d95585fb0ec024f6abd96f7b02e0df58019d46afjohannkoenig@chromium.org#endif 716d95585fb0ec024f6abd96f7b02e0df58019d46afjohannkoenig@chromium.org#if defined(HAS_ARGBTOUVROW_NEON) 717d95585fb0ec024f6abd96f7b02e0df58019d46afjohannkoenig@chromium.org if (TestCpuFlag(kCpuHasNEON) && width >= 16) { 718d95585fb0ec024f6abd96f7b02e0df58019d46afjohannkoenig@chromium.org ARGBToUVRow = ARGBToUVRow_Any_NEON; 719d95585fb0ec024f6abd96f7b02e0df58019d46afjohannkoenig@chromium.org if (IS_ALIGNED(width, 16)) { 720d95585fb0ec024f6abd96f7b02e0df58019d46afjohannkoenig@chromium.org ARGBToUVRow = ARGBToUVRow_NEON; 72141294d96d7dbf9bc215b09832a8336c5fb158f0bjohannkoenig@chromium.org } 72241294d96d7dbf9bc215b09832a8336c5fb158f0bjohannkoenig@chromium.org } 72341294d96d7dbf9bc215b09832a8336c5fb158f0bjohannkoenig@chromium.org#endif 72441294d96d7dbf9bc215b09832a8336c5fb158f0bjohannkoenig@chromium.org 72541294d96d7dbf9bc215b09832a8336c5fb158f0bjohannkoenig@chromium.org for (y = 0; y < height - 1; y += 2) { 72641294d96d7dbf9bc215b09832a8336c5fb158f0bjohannkoenig@chromium.org ARGBToUVRow(src_argb, src_stride_argb, dst_u, dst_v, width); 72741294d96d7dbf9bc215b09832a8336c5fb158f0bjohannkoenig@chromium.org ARGBToYRow(src_argb, dst_y, width); 72841294d96d7dbf9bc215b09832a8336c5fb158f0bjohannkoenig@chromium.org ARGBToYRow(src_argb + src_stride_argb, dst_y + dst_stride_y, width); 72941294d96d7dbf9bc215b09832a8336c5fb158f0bjohannkoenig@chromium.org src_argb += src_stride_argb * 2; 73041294d96d7dbf9bc215b09832a8336c5fb158f0bjohannkoenig@chromium.org dst_y += dst_stride_y * 2; 73141294d96d7dbf9bc215b09832a8336c5fb158f0bjohannkoenig@chromium.org dst_u += dst_stride_u; 73241294d96d7dbf9bc215b09832a8336c5fb158f0bjohannkoenig@chromium.org dst_v += dst_stride_v; 73341294d96d7dbf9bc215b09832a8336c5fb158f0bjohannkoenig@chromium.org } 73441294d96d7dbf9bc215b09832a8336c5fb158f0bjohannkoenig@chromium.org if (height & 1) { 73541294d96d7dbf9bc215b09832a8336c5fb158f0bjohannkoenig@chromium.org ARGBToUVRow(src_argb, 0, dst_u, dst_v, width); 73641294d96d7dbf9bc215b09832a8336c5fb158f0bjohannkoenig@chromium.org ARGBToYRow(src_argb, dst_y, width); 73741294d96d7dbf9bc215b09832a8336c5fb158f0bjohannkoenig@chromium.org } 73841294d96d7dbf9bc215b09832a8336c5fb158f0bjohannkoenig@chromium.org return 0; 73941294d96d7dbf9bc215b09832a8336c5fb158f0bjohannkoenig@chromium.org} 74041294d96d7dbf9bc215b09832a8336c5fb158f0bjohannkoenig@chromium.org 74141294d96d7dbf9bc215b09832a8336c5fb158f0bjohannkoenig@chromium.org// Convert BGRA to I420. 74241294d96d7dbf9bc215b09832a8336c5fb158f0bjohannkoenig@chromium.orgLIBYUV_API 74341294d96d7dbf9bc215b09832a8336c5fb158f0bjohannkoenig@chromium.orgint BGRAToI420(const uint8* src_bgra, int src_stride_bgra, 74441294d96d7dbf9bc215b09832a8336c5fb158f0bjohannkoenig@chromium.org uint8* dst_y, int dst_stride_y, 74541294d96d7dbf9bc215b09832a8336c5fb158f0bjohannkoenig@chromium.org uint8* dst_u, int dst_stride_u, 74641294d96d7dbf9bc215b09832a8336c5fb158f0bjohannkoenig@chromium.org uint8* dst_v, int dst_stride_v, 74741294d96d7dbf9bc215b09832a8336c5fb158f0bjohannkoenig@chromium.org int width, int height) { 74841294d96d7dbf9bc215b09832a8336c5fb158f0bjohannkoenig@chromium.org int y; 74941294d96d7dbf9bc215b09832a8336c5fb158f0bjohannkoenig@chromium.org void (*BGRAToUVRow)(const uint8* src_bgra0, int src_stride_bgra, 75041294d96d7dbf9bc215b09832a8336c5fb158f0bjohannkoenig@chromium.org uint8* dst_u, uint8* dst_v, int width) = BGRAToUVRow_C; 75141294d96d7dbf9bc215b09832a8336c5fb158f0bjohannkoenig@chromium.org void (*BGRAToYRow)(const uint8* src_bgra, uint8* dst_y, int pix) = 75241294d96d7dbf9bc215b09832a8336c5fb158f0bjohannkoenig@chromium.org BGRAToYRow_C; 75341294d96d7dbf9bc215b09832a8336c5fb158f0bjohannkoenig@chromium.org if (!src_bgra || 75441294d96d7dbf9bc215b09832a8336c5fb158f0bjohannkoenig@chromium.org !dst_y || !dst_u || !dst_v || 75541294d96d7dbf9bc215b09832a8336c5fb158f0bjohannkoenig@chromium.org width <= 0 || height == 0) { 75641294d96d7dbf9bc215b09832a8336c5fb158f0bjohannkoenig@chromium.org return -1; 75741294d96d7dbf9bc215b09832a8336c5fb158f0bjohannkoenig@chromium.org } 75841294d96d7dbf9bc215b09832a8336c5fb158f0bjohannkoenig@chromium.org // Negative height means invert the image. 75941294d96d7dbf9bc215b09832a8336c5fb158f0bjohannkoenig@chromium.org if (height < 0) { 76041294d96d7dbf9bc215b09832a8336c5fb158f0bjohannkoenig@chromium.org height = -height; 76141294d96d7dbf9bc215b09832a8336c5fb158f0bjohannkoenig@chromium.org src_bgra = src_bgra + (height - 1) * src_stride_bgra; 76241294d96d7dbf9bc215b09832a8336c5fb158f0bjohannkoenig@chromium.org src_stride_bgra = -src_stride_bgra; 76341294d96d7dbf9bc215b09832a8336c5fb158f0bjohannkoenig@chromium.org } 76441294d96d7dbf9bc215b09832a8336c5fb158f0bjohannkoenig@chromium.org#if defined(HAS_BGRATOYROW_SSSE3) 76541294d96d7dbf9bc215b09832a8336c5fb158f0bjohannkoenig@chromium.org if (TestCpuFlag(kCpuHasSSSE3) && width >= 16) { 76641294d96d7dbf9bc215b09832a8336c5fb158f0bjohannkoenig@chromium.org BGRAToUVRow = BGRAToUVRow_Any_SSSE3; 76741294d96d7dbf9bc215b09832a8336c5fb158f0bjohannkoenig@chromium.org BGRAToYRow = BGRAToYRow_Any_SSSE3; 76841294d96d7dbf9bc215b09832a8336c5fb158f0bjohannkoenig@chromium.org if (IS_ALIGNED(width, 16)) { 76941294d96d7dbf9bc215b09832a8336c5fb158f0bjohannkoenig@chromium.org BGRAToUVRow = BGRAToUVRow_Unaligned_SSSE3; 77041294d96d7dbf9bc215b09832a8336c5fb158f0bjohannkoenig@chromium.org BGRAToYRow = BGRAToYRow_Unaligned_SSSE3; 77141294d96d7dbf9bc215b09832a8336c5fb158f0bjohannkoenig@chromium.org if (IS_ALIGNED(src_bgra, 16) && IS_ALIGNED(src_stride_bgra, 16)) { 77241294d96d7dbf9bc215b09832a8336c5fb158f0bjohannkoenig@chromium.org BGRAToUVRow = BGRAToUVRow_SSSE3; 77341294d96d7dbf9bc215b09832a8336c5fb158f0bjohannkoenig@chromium.org if (IS_ALIGNED(dst_y, 16) && IS_ALIGNED(dst_stride_y, 16)) { 77441294d96d7dbf9bc215b09832a8336c5fb158f0bjohannkoenig@chromium.org BGRAToYRow = BGRAToYRow_SSSE3; 77541294d96d7dbf9bc215b09832a8336c5fb158f0bjohannkoenig@chromium.org } 77641294d96d7dbf9bc215b09832a8336c5fb158f0bjohannkoenig@chromium.org } 77741294d96d7dbf9bc215b09832a8336c5fb158f0bjohannkoenig@chromium.org } 77841294d96d7dbf9bc215b09832a8336c5fb158f0bjohannkoenig@chromium.org } 77941294d96d7dbf9bc215b09832a8336c5fb158f0bjohannkoenig@chromium.org#elif defined(HAS_BGRATOYROW_NEON) 78041294d96d7dbf9bc215b09832a8336c5fb158f0bjohannkoenig@chromium.org if (TestCpuFlag(kCpuHasNEON) && width >= 8) { 78141294d96d7dbf9bc215b09832a8336c5fb158f0bjohannkoenig@chromium.org BGRAToYRow = BGRAToYRow_Any_NEON; 78241294d96d7dbf9bc215b09832a8336c5fb158f0bjohannkoenig@chromium.org if (IS_ALIGNED(width, 8)) { 78341294d96d7dbf9bc215b09832a8336c5fb158f0bjohannkoenig@chromium.org BGRAToYRow = BGRAToYRow_NEON; 78441294d96d7dbf9bc215b09832a8336c5fb158f0bjohannkoenig@chromium.org } 78541294d96d7dbf9bc215b09832a8336c5fb158f0bjohannkoenig@chromium.org if (width >= 16) { 78641294d96d7dbf9bc215b09832a8336c5fb158f0bjohannkoenig@chromium.org BGRAToUVRow = BGRAToUVRow_Any_NEON; 78741294d96d7dbf9bc215b09832a8336c5fb158f0bjohannkoenig@chromium.org if (IS_ALIGNED(width, 16)) { 78841294d96d7dbf9bc215b09832a8336c5fb158f0bjohannkoenig@chromium.org BGRAToUVRow = BGRAToUVRow_NEON; 78941294d96d7dbf9bc215b09832a8336c5fb158f0bjohannkoenig@chromium.org } 79041294d96d7dbf9bc215b09832a8336c5fb158f0bjohannkoenig@chromium.org } 79141294d96d7dbf9bc215b09832a8336c5fb158f0bjohannkoenig@chromium.org } 79241294d96d7dbf9bc215b09832a8336c5fb158f0bjohannkoenig@chromium.org#endif 79341294d96d7dbf9bc215b09832a8336c5fb158f0bjohannkoenig@chromium.org 79441294d96d7dbf9bc215b09832a8336c5fb158f0bjohannkoenig@chromium.org for (y = 0; y < height - 1; y += 2) { 79541294d96d7dbf9bc215b09832a8336c5fb158f0bjohannkoenig@chromium.org BGRAToUVRow(src_bgra, src_stride_bgra, dst_u, dst_v, width); 79641294d96d7dbf9bc215b09832a8336c5fb158f0bjohannkoenig@chromium.org BGRAToYRow(src_bgra, dst_y, width); 79741294d96d7dbf9bc215b09832a8336c5fb158f0bjohannkoenig@chromium.org BGRAToYRow(src_bgra + src_stride_bgra, dst_y + dst_stride_y, width); 79841294d96d7dbf9bc215b09832a8336c5fb158f0bjohannkoenig@chromium.org src_bgra += src_stride_bgra * 2; 79941294d96d7dbf9bc215b09832a8336c5fb158f0bjohannkoenig@chromium.org dst_y += dst_stride_y * 2; 80041294d96d7dbf9bc215b09832a8336c5fb158f0bjohannkoenig@chromium.org dst_u += dst_stride_u; 80141294d96d7dbf9bc215b09832a8336c5fb158f0bjohannkoenig@chromium.org dst_v += dst_stride_v; 80241294d96d7dbf9bc215b09832a8336c5fb158f0bjohannkoenig@chromium.org } 80341294d96d7dbf9bc215b09832a8336c5fb158f0bjohannkoenig@chromium.org if (height & 1) { 80441294d96d7dbf9bc215b09832a8336c5fb158f0bjohannkoenig@chromium.org BGRAToUVRow(src_bgra, 0, dst_u, dst_v, width); 80541294d96d7dbf9bc215b09832a8336c5fb158f0bjohannkoenig@chromium.org BGRAToYRow(src_bgra, dst_y, width); 80641294d96d7dbf9bc215b09832a8336c5fb158f0bjohannkoenig@chromium.org } 80741294d96d7dbf9bc215b09832a8336c5fb158f0bjohannkoenig@chromium.org return 0; 80841294d96d7dbf9bc215b09832a8336c5fb158f0bjohannkoenig@chromium.org} 80941294d96d7dbf9bc215b09832a8336c5fb158f0bjohannkoenig@chromium.org 81041294d96d7dbf9bc215b09832a8336c5fb158f0bjohannkoenig@chromium.org// Convert ABGR to I420. 81141294d96d7dbf9bc215b09832a8336c5fb158f0bjohannkoenig@chromium.orgLIBYUV_API 81241294d96d7dbf9bc215b09832a8336c5fb158f0bjohannkoenig@chromium.orgint ABGRToI420(const uint8* src_abgr, int src_stride_abgr, 81341294d96d7dbf9bc215b09832a8336c5fb158f0bjohannkoenig@chromium.org uint8* dst_y, int dst_stride_y, 81441294d96d7dbf9bc215b09832a8336c5fb158f0bjohannkoenig@chromium.org uint8* dst_u, int dst_stride_u, 81541294d96d7dbf9bc215b09832a8336c5fb158f0bjohannkoenig@chromium.org uint8* dst_v, int dst_stride_v, 81641294d96d7dbf9bc215b09832a8336c5fb158f0bjohannkoenig@chromium.org int width, int height) { 81741294d96d7dbf9bc215b09832a8336c5fb158f0bjohannkoenig@chromium.org int y; 81841294d96d7dbf9bc215b09832a8336c5fb158f0bjohannkoenig@chromium.org void (*ABGRToUVRow)(const uint8* src_abgr0, int src_stride_abgr, 81941294d96d7dbf9bc215b09832a8336c5fb158f0bjohannkoenig@chromium.org uint8* dst_u, uint8* dst_v, int width) = ABGRToUVRow_C; 82041294d96d7dbf9bc215b09832a8336c5fb158f0bjohannkoenig@chromium.org void (*ABGRToYRow)(const uint8* src_abgr, uint8* dst_y, int pix) = 82141294d96d7dbf9bc215b09832a8336c5fb158f0bjohannkoenig@chromium.org ABGRToYRow_C; 82241294d96d7dbf9bc215b09832a8336c5fb158f0bjohannkoenig@chromium.org if (!src_abgr || 82341294d96d7dbf9bc215b09832a8336c5fb158f0bjohannkoenig@chromium.org !dst_y || !dst_u || !dst_v || 82441294d96d7dbf9bc215b09832a8336c5fb158f0bjohannkoenig@chromium.org width <= 0 || height == 0) { 82541294d96d7dbf9bc215b09832a8336c5fb158f0bjohannkoenig@chromium.org return -1; 82641294d96d7dbf9bc215b09832a8336c5fb158f0bjohannkoenig@chromium.org } 82741294d96d7dbf9bc215b09832a8336c5fb158f0bjohannkoenig@chromium.org // Negative height means invert the image. 82841294d96d7dbf9bc215b09832a8336c5fb158f0bjohannkoenig@chromium.org if (height < 0) { 82941294d96d7dbf9bc215b09832a8336c5fb158f0bjohannkoenig@chromium.org height = -height; 83041294d96d7dbf9bc215b09832a8336c5fb158f0bjohannkoenig@chromium.org src_abgr = src_abgr + (height - 1) * src_stride_abgr; 83141294d96d7dbf9bc215b09832a8336c5fb158f0bjohannkoenig@chromium.org src_stride_abgr = -src_stride_abgr; 83241294d96d7dbf9bc215b09832a8336c5fb158f0bjohannkoenig@chromium.org } 83341294d96d7dbf9bc215b09832a8336c5fb158f0bjohannkoenig@chromium.org#if defined(HAS_ABGRTOYROW_SSSE3) 83441294d96d7dbf9bc215b09832a8336c5fb158f0bjohannkoenig@chromium.org if (TestCpuFlag(kCpuHasSSSE3) && width >= 16) { 83541294d96d7dbf9bc215b09832a8336c5fb158f0bjohannkoenig@chromium.org ABGRToUVRow = ABGRToUVRow_Any_SSSE3; 83641294d96d7dbf9bc215b09832a8336c5fb158f0bjohannkoenig@chromium.org ABGRToYRow = ABGRToYRow_Any_SSSE3; 83741294d96d7dbf9bc215b09832a8336c5fb158f0bjohannkoenig@chromium.org if (IS_ALIGNED(width, 16)) { 83841294d96d7dbf9bc215b09832a8336c5fb158f0bjohannkoenig@chromium.org ABGRToUVRow = ABGRToUVRow_Unaligned_SSSE3; 83941294d96d7dbf9bc215b09832a8336c5fb158f0bjohannkoenig@chromium.org ABGRToYRow = ABGRToYRow_Unaligned_SSSE3; 84041294d96d7dbf9bc215b09832a8336c5fb158f0bjohannkoenig@chromium.org if (IS_ALIGNED(src_abgr, 16) && IS_ALIGNED(src_stride_abgr, 16)) { 84141294d96d7dbf9bc215b09832a8336c5fb158f0bjohannkoenig@chromium.org ABGRToUVRow = ABGRToUVRow_SSSE3; 84241294d96d7dbf9bc215b09832a8336c5fb158f0bjohannkoenig@chromium.org if (IS_ALIGNED(dst_y, 16) && IS_ALIGNED(dst_stride_y, 16)) { 84341294d96d7dbf9bc215b09832a8336c5fb158f0bjohannkoenig@chromium.org ABGRToYRow = ABGRToYRow_SSSE3; 84441294d96d7dbf9bc215b09832a8336c5fb158f0bjohannkoenig@chromium.org } 84541294d96d7dbf9bc215b09832a8336c5fb158f0bjohannkoenig@chromium.org } 84641294d96d7dbf9bc215b09832a8336c5fb158f0bjohannkoenig@chromium.org } 84741294d96d7dbf9bc215b09832a8336c5fb158f0bjohannkoenig@chromium.org } 84841294d96d7dbf9bc215b09832a8336c5fb158f0bjohannkoenig@chromium.org#elif defined(HAS_ABGRTOYROW_NEON) 84941294d96d7dbf9bc215b09832a8336c5fb158f0bjohannkoenig@chromium.org if (TestCpuFlag(kCpuHasNEON) && width >= 8) { 85041294d96d7dbf9bc215b09832a8336c5fb158f0bjohannkoenig@chromium.org ABGRToYRow = ABGRToYRow_Any_NEON; 85141294d96d7dbf9bc215b09832a8336c5fb158f0bjohannkoenig@chromium.org if (IS_ALIGNED(width, 8)) { 85241294d96d7dbf9bc215b09832a8336c5fb158f0bjohannkoenig@chromium.org ABGRToYRow = ABGRToYRow_NEON; 85341294d96d7dbf9bc215b09832a8336c5fb158f0bjohannkoenig@chromium.org } 85441294d96d7dbf9bc215b09832a8336c5fb158f0bjohannkoenig@chromium.org if (width >= 16) { 85541294d96d7dbf9bc215b09832a8336c5fb158f0bjohannkoenig@chromium.org ABGRToUVRow = ABGRToUVRow_Any_NEON; 85641294d96d7dbf9bc215b09832a8336c5fb158f0bjohannkoenig@chromium.org if (IS_ALIGNED(width, 16)) { 85741294d96d7dbf9bc215b09832a8336c5fb158f0bjohannkoenig@chromium.org ABGRToUVRow = ABGRToUVRow_NEON; 85841294d96d7dbf9bc215b09832a8336c5fb158f0bjohannkoenig@chromium.org } 85941294d96d7dbf9bc215b09832a8336c5fb158f0bjohannkoenig@chromium.org } 86041294d96d7dbf9bc215b09832a8336c5fb158f0bjohannkoenig@chromium.org } 86141294d96d7dbf9bc215b09832a8336c5fb158f0bjohannkoenig@chromium.org#endif 86241294d96d7dbf9bc215b09832a8336c5fb158f0bjohannkoenig@chromium.org 86341294d96d7dbf9bc215b09832a8336c5fb158f0bjohannkoenig@chromium.org for (y = 0; y < height - 1; y += 2) { 86441294d96d7dbf9bc215b09832a8336c5fb158f0bjohannkoenig@chromium.org ABGRToUVRow(src_abgr, src_stride_abgr, dst_u, dst_v, width); 86541294d96d7dbf9bc215b09832a8336c5fb158f0bjohannkoenig@chromium.org ABGRToYRow(src_abgr, dst_y, width); 86641294d96d7dbf9bc215b09832a8336c5fb158f0bjohannkoenig@chromium.org ABGRToYRow(src_abgr + src_stride_abgr, dst_y + dst_stride_y, width); 86741294d96d7dbf9bc215b09832a8336c5fb158f0bjohannkoenig@chromium.org src_abgr += src_stride_abgr * 2; 86841294d96d7dbf9bc215b09832a8336c5fb158f0bjohannkoenig@chromium.org dst_y += dst_stride_y * 2; 86941294d96d7dbf9bc215b09832a8336c5fb158f0bjohannkoenig@chromium.org dst_u += dst_stride_u; 87041294d96d7dbf9bc215b09832a8336c5fb158f0bjohannkoenig@chromium.org dst_v += dst_stride_v; 87141294d96d7dbf9bc215b09832a8336c5fb158f0bjohannkoenig@chromium.org } 87241294d96d7dbf9bc215b09832a8336c5fb158f0bjohannkoenig@chromium.org if (height & 1) { 87341294d96d7dbf9bc215b09832a8336c5fb158f0bjohannkoenig@chromium.org ABGRToUVRow(src_abgr, 0, dst_u, dst_v, width); 87441294d96d7dbf9bc215b09832a8336c5fb158f0bjohannkoenig@chromium.org ABGRToYRow(src_abgr, dst_y, width); 87541294d96d7dbf9bc215b09832a8336c5fb158f0bjohannkoenig@chromium.org } 87641294d96d7dbf9bc215b09832a8336c5fb158f0bjohannkoenig@chromium.org return 0; 87741294d96d7dbf9bc215b09832a8336c5fb158f0bjohannkoenig@chromium.org} 87841294d96d7dbf9bc215b09832a8336c5fb158f0bjohannkoenig@chromium.org 87941294d96d7dbf9bc215b09832a8336c5fb158f0bjohannkoenig@chromium.org// Convert RGBA to I420. 88041294d96d7dbf9bc215b09832a8336c5fb158f0bjohannkoenig@chromium.orgLIBYUV_API 88141294d96d7dbf9bc215b09832a8336c5fb158f0bjohannkoenig@chromium.orgint RGBAToI420(const uint8* src_rgba, int src_stride_rgba, 88241294d96d7dbf9bc215b09832a8336c5fb158f0bjohannkoenig@chromium.org uint8* dst_y, int dst_stride_y, 88341294d96d7dbf9bc215b09832a8336c5fb158f0bjohannkoenig@chromium.org uint8* dst_u, int dst_stride_u, 88441294d96d7dbf9bc215b09832a8336c5fb158f0bjohannkoenig@chromium.org uint8* dst_v, int dst_stride_v, 88541294d96d7dbf9bc215b09832a8336c5fb158f0bjohannkoenig@chromium.org int width, int height) { 88641294d96d7dbf9bc215b09832a8336c5fb158f0bjohannkoenig@chromium.org int y; 88741294d96d7dbf9bc215b09832a8336c5fb158f0bjohannkoenig@chromium.org void (*RGBAToUVRow)(const uint8* src_rgba0, int src_stride_rgba, 88841294d96d7dbf9bc215b09832a8336c5fb158f0bjohannkoenig@chromium.org uint8* dst_u, uint8* dst_v, int width) = RGBAToUVRow_C; 88941294d96d7dbf9bc215b09832a8336c5fb158f0bjohannkoenig@chromium.org void (*RGBAToYRow)(const uint8* src_rgba, uint8* dst_y, int pix) = 89041294d96d7dbf9bc215b09832a8336c5fb158f0bjohannkoenig@chromium.org RGBAToYRow_C; 89141294d96d7dbf9bc215b09832a8336c5fb158f0bjohannkoenig@chromium.org if (!src_rgba || 89241294d96d7dbf9bc215b09832a8336c5fb158f0bjohannkoenig@chromium.org !dst_y || !dst_u || !dst_v || 89341294d96d7dbf9bc215b09832a8336c5fb158f0bjohannkoenig@chromium.org width <= 0 || height == 0) { 89441294d96d7dbf9bc215b09832a8336c5fb158f0bjohannkoenig@chromium.org return -1; 89541294d96d7dbf9bc215b09832a8336c5fb158f0bjohannkoenig@chromium.org } 89641294d96d7dbf9bc215b09832a8336c5fb158f0bjohannkoenig@chromium.org // Negative height means invert the image. 89741294d96d7dbf9bc215b09832a8336c5fb158f0bjohannkoenig@chromium.org if (height < 0) { 89841294d96d7dbf9bc215b09832a8336c5fb158f0bjohannkoenig@chromium.org height = -height; 89941294d96d7dbf9bc215b09832a8336c5fb158f0bjohannkoenig@chromium.org src_rgba = src_rgba + (height - 1) * src_stride_rgba; 90041294d96d7dbf9bc215b09832a8336c5fb158f0bjohannkoenig@chromium.org src_stride_rgba = -src_stride_rgba; 90141294d96d7dbf9bc215b09832a8336c5fb158f0bjohannkoenig@chromium.org } 90241294d96d7dbf9bc215b09832a8336c5fb158f0bjohannkoenig@chromium.org#if defined(HAS_RGBATOYROW_SSSE3) 90341294d96d7dbf9bc215b09832a8336c5fb158f0bjohannkoenig@chromium.org if (TestCpuFlag(kCpuHasSSSE3) && width >= 16) { 90441294d96d7dbf9bc215b09832a8336c5fb158f0bjohannkoenig@chromium.org RGBAToUVRow = RGBAToUVRow_Any_SSSE3; 90541294d96d7dbf9bc215b09832a8336c5fb158f0bjohannkoenig@chromium.org RGBAToYRow = RGBAToYRow_Any_SSSE3; 90641294d96d7dbf9bc215b09832a8336c5fb158f0bjohannkoenig@chromium.org if (IS_ALIGNED(width, 16)) { 90741294d96d7dbf9bc215b09832a8336c5fb158f0bjohannkoenig@chromium.org RGBAToUVRow = RGBAToUVRow_Unaligned_SSSE3; 90841294d96d7dbf9bc215b09832a8336c5fb158f0bjohannkoenig@chromium.org RGBAToYRow = RGBAToYRow_Unaligned_SSSE3; 90941294d96d7dbf9bc215b09832a8336c5fb158f0bjohannkoenig@chromium.org if (IS_ALIGNED(src_rgba, 16) && IS_ALIGNED(src_stride_rgba, 16)) { 91041294d96d7dbf9bc215b09832a8336c5fb158f0bjohannkoenig@chromium.org RGBAToUVRow = RGBAToUVRow_SSSE3; 91141294d96d7dbf9bc215b09832a8336c5fb158f0bjohannkoenig@chromium.org if (IS_ALIGNED(dst_y, 16) && IS_ALIGNED(dst_stride_y, 16)) { 91241294d96d7dbf9bc215b09832a8336c5fb158f0bjohannkoenig@chromium.org RGBAToYRow = RGBAToYRow_SSSE3; 91341294d96d7dbf9bc215b09832a8336c5fb158f0bjohannkoenig@chromium.org } 91441294d96d7dbf9bc215b09832a8336c5fb158f0bjohannkoenig@chromium.org } 91541294d96d7dbf9bc215b09832a8336c5fb158f0bjohannkoenig@chromium.org } 91641294d96d7dbf9bc215b09832a8336c5fb158f0bjohannkoenig@chromium.org } 91741294d96d7dbf9bc215b09832a8336c5fb158f0bjohannkoenig@chromium.org#elif defined(HAS_RGBATOYROW_NEON) 91841294d96d7dbf9bc215b09832a8336c5fb158f0bjohannkoenig@chromium.org if (TestCpuFlag(kCpuHasNEON) && width >= 8) { 91941294d96d7dbf9bc215b09832a8336c5fb158f0bjohannkoenig@chromium.org RGBAToYRow = RGBAToYRow_Any_NEON; 92041294d96d7dbf9bc215b09832a8336c5fb158f0bjohannkoenig@chromium.org if (IS_ALIGNED(width, 8)) { 92141294d96d7dbf9bc215b09832a8336c5fb158f0bjohannkoenig@chromium.org RGBAToYRow = RGBAToYRow_NEON; 92241294d96d7dbf9bc215b09832a8336c5fb158f0bjohannkoenig@chromium.org } 92341294d96d7dbf9bc215b09832a8336c5fb158f0bjohannkoenig@chromium.org if (width >= 16) { 92441294d96d7dbf9bc215b09832a8336c5fb158f0bjohannkoenig@chromium.org RGBAToUVRow = RGBAToUVRow_Any_NEON; 92541294d96d7dbf9bc215b09832a8336c5fb158f0bjohannkoenig@chromium.org if (IS_ALIGNED(width, 16)) { 92641294d96d7dbf9bc215b09832a8336c5fb158f0bjohannkoenig@chromium.org RGBAToUVRow = RGBAToUVRow_NEON; 92741294d96d7dbf9bc215b09832a8336c5fb158f0bjohannkoenig@chromium.org } 92841294d96d7dbf9bc215b09832a8336c5fb158f0bjohannkoenig@chromium.org } 92941294d96d7dbf9bc215b09832a8336c5fb158f0bjohannkoenig@chromium.org } 93041294d96d7dbf9bc215b09832a8336c5fb158f0bjohannkoenig@chromium.org#endif 93141294d96d7dbf9bc215b09832a8336c5fb158f0bjohannkoenig@chromium.org 93241294d96d7dbf9bc215b09832a8336c5fb158f0bjohannkoenig@chromium.org for (y = 0; y < height - 1; y += 2) { 93341294d96d7dbf9bc215b09832a8336c5fb158f0bjohannkoenig@chromium.org RGBAToUVRow(src_rgba, src_stride_rgba, dst_u, dst_v, width); 93441294d96d7dbf9bc215b09832a8336c5fb158f0bjohannkoenig@chromium.org RGBAToYRow(src_rgba, dst_y, width); 93541294d96d7dbf9bc215b09832a8336c5fb158f0bjohannkoenig@chromium.org RGBAToYRow(src_rgba + src_stride_rgba, dst_y + dst_stride_y, width); 93641294d96d7dbf9bc215b09832a8336c5fb158f0bjohannkoenig@chromium.org src_rgba += src_stride_rgba * 2; 93741294d96d7dbf9bc215b09832a8336c5fb158f0bjohannkoenig@chromium.org dst_y += dst_stride_y * 2; 93841294d96d7dbf9bc215b09832a8336c5fb158f0bjohannkoenig@chromium.org dst_u += dst_stride_u; 93941294d96d7dbf9bc215b09832a8336c5fb158f0bjohannkoenig@chromium.org dst_v += dst_stride_v; 94041294d96d7dbf9bc215b09832a8336c5fb158f0bjohannkoenig@chromium.org } 94141294d96d7dbf9bc215b09832a8336c5fb158f0bjohannkoenig@chromium.org if (height & 1) { 94241294d96d7dbf9bc215b09832a8336c5fb158f0bjohannkoenig@chromium.org RGBAToUVRow(src_rgba, 0, dst_u, dst_v, width); 94341294d96d7dbf9bc215b09832a8336c5fb158f0bjohannkoenig@chromium.org RGBAToYRow(src_rgba, dst_y, width); 94441294d96d7dbf9bc215b09832a8336c5fb158f0bjohannkoenig@chromium.org } 94541294d96d7dbf9bc215b09832a8336c5fb158f0bjohannkoenig@chromium.org return 0; 94641294d96d7dbf9bc215b09832a8336c5fb158f0bjohannkoenig@chromium.org} 94741294d96d7dbf9bc215b09832a8336c5fb158f0bjohannkoenig@chromium.org 94841294d96d7dbf9bc215b09832a8336c5fb158f0bjohannkoenig@chromium.org// Convert RGB24 to I420. 94941294d96d7dbf9bc215b09832a8336c5fb158f0bjohannkoenig@chromium.orgLIBYUV_API 95041294d96d7dbf9bc215b09832a8336c5fb158f0bjohannkoenig@chromium.orgint RGB24ToI420(const uint8* src_rgb24, int src_stride_rgb24, 95141294d96d7dbf9bc215b09832a8336c5fb158f0bjohannkoenig@chromium.org uint8* dst_y, int dst_stride_y, 95241294d96d7dbf9bc215b09832a8336c5fb158f0bjohannkoenig@chromium.org uint8* dst_u, int dst_stride_u, 95341294d96d7dbf9bc215b09832a8336c5fb158f0bjohannkoenig@chromium.org uint8* dst_v, int dst_stride_v, 95441294d96d7dbf9bc215b09832a8336c5fb158f0bjohannkoenig@chromium.org int width, int height) { 95541294d96d7dbf9bc215b09832a8336c5fb158f0bjohannkoenig@chromium.org int y; 95641294d96d7dbf9bc215b09832a8336c5fb158f0bjohannkoenig@chromium.org#if defined(HAS_RGB24TOYROW_NEON) 95741294d96d7dbf9bc215b09832a8336c5fb158f0bjohannkoenig@chromium.org void (*RGB24ToUVRow)(const uint8* src_rgb24, int src_stride_rgb24, 95841294d96d7dbf9bc215b09832a8336c5fb158f0bjohannkoenig@chromium.org uint8* dst_u, uint8* dst_v, int width) = RGB24ToUVRow_C; 95941294d96d7dbf9bc215b09832a8336c5fb158f0bjohannkoenig@chromium.org void (*RGB24ToYRow)(const uint8* src_rgb24, uint8* dst_y, int pix) = 96041294d96d7dbf9bc215b09832a8336c5fb158f0bjohannkoenig@chromium.org RGB24ToYRow_C; 96141294d96d7dbf9bc215b09832a8336c5fb158f0bjohannkoenig@chromium.org#else 96241294d96d7dbf9bc215b09832a8336c5fb158f0bjohannkoenig@chromium.org void (*RGB24ToARGBRow)(const uint8* src_rgb, uint8* dst_argb, int pix) = 96341294d96d7dbf9bc215b09832a8336c5fb158f0bjohannkoenig@chromium.org RGB24ToARGBRow_C; 96441294d96d7dbf9bc215b09832a8336c5fb158f0bjohannkoenig@chromium.org void (*ARGBToUVRow)(const uint8* src_argb0, int src_stride_argb, 96541294d96d7dbf9bc215b09832a8336c5fb158f0bjohannkoenig@chromium.org uint8* dst_u, uint8* dst_v, int width) = ARGBToUVRow_C; 96641294d96d7dbf9bc215b09832a8336c5fb158f0bjohannkoenig@chromium.org void (*ARGBToYRow)(const uint8* src_argb, uint8* dst_y, int pix) = 96741294d96d7dbf9bc215b09832a8336c5fb158f0bjohannkoenig@chromium.org ARGBToYRow_C; 96841294d96d7dbf9bc215b09832a8336c5fb158f0bjohannkoenig@chromium.org#endif 96941294d96d7dbf9bc215b09832a8336c5fb158f0bjohannkoenig@chromium.org if (!src_rgb24 || !dst_y || !dst_u || !dst_v || 97041294d96d7dbf9bc215b09832a8336c5fb158f0bjohannkoenig@chromium.org width <= 0 || height == 0) { 97141294d96d7dbf9bc215b09832a8336c5fb158f0bjohannkoenig@chromium.org return -1; 97241294d96d7dbf9bc215b09832a8336c5fb158f0bjohannkoenig@chromium.org } 97341294d96d7dbf9bc215b09832a8336c5fb158f0bjohannkoenig@chromium.org // Negative height means invert the image. 97441294d96d7dbf9bc215b09832a8336c5fb158f0bjohannkoenig@chromium.org if (height < 0) { 97541294d96d7dbf9bc215b09832a8336c5fb158f0bjohannkoenig@chromium.org height = -height; 97641294d96d7dbf9bc215b09832a8336c5fb158f0bjohannkoenig@chromium.org src_rgb24 = src_rgb24 + (height - 1) * src_stride_rgb24; 97741294d96d7dbf9bc215b09832a8336c5fb158f0bjohannkoenig@chromium.org src_stride_rgb24 = -src_stride_rgb24; 97841294d96d7dbf9bc215b09832a8336c5fb158f0bjohannkoenig@chromium.org } 97941294d96d7dbf9bc215b09832a8336c5fb158f0bjohannkoenig@chromium.org 98041294d96d7dbf9bc215b09832a8336c5fb158f0bjohannkoenig@chromium.org#if defined(HAS_RGB24TOYROW_NEON) 98141294d96d7dbf9bc215b09832a8336c5fb158f0bjohannkoenig@chromium.org if (TestCpuFlag(kCpuHasNEON) && width >= 8) { 98241294d96d7dbf9bc215b09832a8336c5fb158f0bjohannkoenig@chromium.org RGB24ToYRow = RGB24ToYRow_Any_NEON; 98341294d96d7dbf9bc215b09832a8336c5fb158f0bjohannkoenig@chromium.org if (IS_ALIGNED(width, 8)) { 98441294d96d7dbf9bc215b09832a8336c5fb158f0bjohannkoenig@chromium.org RGB24ToYRow = RGB24ToYRow_NEON; 98541294d96d7dbf9bc215b09832a8336c5fb158f0bjohannkoenig@chromium.org } 98641294d96d7dbf9bc215b09832a8336c5fb158f0bjohannkoenig@chromium.org if (width >= 16) { 98741294d96d7dbf9bc215b09832a8336c5fb158f0bjohannkoenig@chromium.org RGB24ToUVRow = RGB24ToUVRow_Any_NEON; 98841294d96d7dbf9bc215b09832a8336c5fb158f0bjohannkoenig@chromium.org if (IS_ALIGNED(width, 16)) { 98941294d96d7dbf9bc215b09832a8336c5fb158f0bjohannkoenig@chromium.org RGB24ToUVRow = RGB24ToUVRow_NEON; 99041294d96d7dbf9bc215b09832a8336c5fb158f0bjohannkoenig@chromium.org } 99141294d96d7dbf9bc215b09832a8336c5fb158f0bjohannkoenig@chromium.org } 99241294d96d7dbf9bc215b09832a8336c5fb158f0bjohannkoenig@chromium.org } 99341294d96d7dbf9bc215b09832a8336c5fb158f0bjohannkoenig@chromium.org#else // HAS_RGB24TOYROW_NEON 99441294d96d7dbf9bc215b09832a8336c5fb158f0bjohannkoenig@chromium.org 99541294d96d7dbf9bc215b09832a8336c5fb158f0bjohannkoenig@chromium.org#if defined(HAS_RGB24TOARGBROW_SSSE3) 99641294d96d7dbf9bc215b09832a8336c5fb158f0bjohannkoenig@chromium.org if (TestCpuFlag(kCpuHasSSSE3) && width >= 16) { 99741294d96d7dbf9bc215b09832a8336c5fb158f0bjohannkoenig@chromium.org RGB24ToARGBRow = RGB24ToARGBRow_Any_SSSE3; 99841294d96d7dbf9bc215b09832a8336c5fb158f0bjohannkoenig@chromium.org if (IS_ALIGNED(width, 16)) { 99941294d96d7dbf9bc215b09832a8336c5fb158f0bjohannkoenig@chromium.org RGB24ToARGBRow = RGB24ToARGBRow_SSSE3; 100041294d96d7dbf9bc215b09832a8336c5fb158f0bjohannkoenig@chromium.org } 100141294d96d7dbf9bc215b09832a8336c5fb158f0bjohannkoenig@chromium.org } 100241294d96d7dbf9bc215b09832a8336c5fb158f0bjohannkoenig@chromium.org#endif 100341294d96d7dbf9bc215b09832a8336c5fb158f0bjohannkoenig@chromium.org#if defined(HAS_ARGBTOUVROW_SSSE3) 100441294d96d7dbf9bc215b09832a8336c5fb158f0bjohannkoenig@chromium.org if (TestCpuFlag(kCpuHasSSSE3) && width >= 16) { 100541294d96d7dbf9bc215b09832a8336c5fb158f0bjohannkoenig@chromium.org ARGBToUVRow = ARGBToUVRow_Any_SSSE3; 100641294d96d7dbf9bc215b09832a8336c5fb158f0bjohannkoenig@chromium.org if (IS_ALIGNED(width, 16)) { 100741294d96d7dbf9bc215b09832a8336c5fb158f0bjohannkoenig@chromium.org ARGBToUVRow = ARGBToUVRow_SSSE3; 100841294d96d7dbf9bc215b09832a8336c5fb158f0bjohannkoenig@chromium.org } 100941294d96d7dbf9bc215b09832a8336c5fb158f0bjohannkoenig@chromium.org } 101041294d96d7dbf9bc215b09832a8336c5fb158f0bjohannkoenig@chromium.org#endif 101141294d96d7dbf9bc215b09832a8336c5fb158f0bjohannkoenig@chromium.org#if defined(HAS_ARGBTOUVROW_SSSE3) 101241294d96d7dbf9bc215b09832a8336c5fb158f0bjohannkoenig@chromium.org if (TestCpuFlag(kCpuHasSSSE3) && width >= 16) { 101341294d96d7dbf9bc215b09832a8336c5fb158f0bjohannkoenig@chromium.org ARGBToYRow = ARGBToYRow_Any_SSSE3; 101441294d96d7dbf9bc215b09832a8336c5fb158f0bjohannkoenig@chromium.org if (IS_ALIGNED(width, 16)) { 101541294d96d7dbf9bc215b09832a8336c5fb158f0bjohannkoenig@chromium.org ARGBToYRow = ARGBToYRow_Unaligned_SSSE3; 101641294d96d7dbf9bc215b09832a8336c5fb158f0bjohannkoenig@chromium.org if (IS_ALIGNED(dst_y, 16) && IS_ALIGNED(dst_stride_y, 16)) { 101741294d96d7dbf9bc215b09832a8336c5fb158f0bjohannkoenig@chromium.org ARGBToYRow = ARGBToYRow_SSSE3; 101841294d96d7dbf9bc215b09832a8336c5fb158f0bjohannkoenig@chromium.org } 101941294d96d7dbf9bc215b09832a8336c5fb158f0bjohannkoenig@chromium.org } 102041294d96d7dbf9bc215b09832a8336c5fb158f0bjohannkoenig@chromium.org } 102141294d96d7dbf9bc215b09832a8336c5fb158f0bjohannkoenig@chromium.org#endif // HAS_ARGBTOUVROW_SSSE3 102241294d96d7dbf9bc215b09832a8336c5fb158f0bjohannkoenig@chromium.org#endif // HAS_RGB24TOYROW_NEON 102341294d96d7dbf9bc215b09832a8336c5fb158f0bjohannkoenig@chromium.org 1024d95585fb0ec024f6abd96f7b02e0df58019d46afjohannkoenig@chromium.org { 1025d95585fb0ec024f6abd96f7b02e0df58019d46afjohannkoenig@chromium.org#if !defined(HAS_RGB24TOYROW_NEON) 1026d95585fb0ec024f6abd96f7b02e0df58019d46afjohannkoenig@chromium.org // Allocate 2 rows of ARGB. 1027d95585fb0ec024f6abd96f7b02e0df58019d46afjohannkoenig@chromium.org const int kRowSize = (width * 4 + 15) & ~15; 1028d95585fb0ec024f6abd96f7b02e0df58019d46afjohannkoenig@chromium.org align_buffer_64(row, kRowSize * 2); 1029d95585fb0ec024f6abd96f7b02e0df58019d46afjohannkoenig@chromium.org#endif 1030d95585fb0ec024f6abd96f7b02e0df58019d46afjohannkoenig@chromium.org 1031d95585fb0ec024f6abd96f7b02e0df58019d46afjohannkoenig@chromium.org for (y = 0; y < height - 1; y += 2) { 103241294d96d7dbf9bc215b09832a8336c5fb158f0bjohannkoenig@chromium.org#if defined(HAS_RGB24TOYROW_NEON) 1033d95585fb0ec024f6abd96f7b02e0df58019d46afjohannkoenig@chromium.org RGB24ToUVRow(src_rgb24, src_stride_rgb24, dst_u, dst_v, width); 1034d95585fb0ec024f6abd96f7b02e0df58019d46afjohannkoenig@chromium.org RGB24ToYRow(src_rgb24, dst_y, width); 1035d95585fb0ec024f6abd96f7b02e0df58019d46afjohannkoenig@chromium.org RGB24ToYRow(src_rgb24 + src_stride_rgb24, dst_y + dst_stride_y, width); 103641294d96d7dbf9bc215b09832a8336c5fb158f0bjohannkoenig@chromium.org#else 1037d95585fb0ec024f6abd96f7b02e0df58019d46afjohannkoenig@chromium.org RGB24ToARGBRow(src_rgb24, row, width); 1038d95585fb0ec024f6abd96f7b02e0df58019d46afjohannkoenig@chromium.org RGB24ToARGBRow(src_rgb24 + src_stride_rgb24, row + kRowSize, width); 1039d95585fb0ec024f6abd96f7b02e0df58019d46afjohannkoenig@chromium.org ARGBToUVRow(row, kRowSize, dst_u, dst_v, width); 1040d95585fb0ec024f6abd96f7b02e0df58019d46afjohannkoenig@chromium.org ARGBToYRow(row, dst_y, width); 1041d95585fb0ec024f6abd96f7b02e0df58019d46afjohannkoenig@chromium.org ARGBToYRow(row + kRowSize, dst_y + dst_stride_y, width); 104241294d96d7dbf9bc215b09832a8336c5fb158f0bjohannkoenig@chromium.org#endif 1043d95585fb0ec024f6abd96f7b02e0df58019d46afjohannkoenig@chromium.org src_rgb24 += src_stride_rgb24 * 2; 1044d95585fb0ec024f6abd96f7b02e0df58019d46afjohannkoenig@chromium.org dst_y += dst_stride_y * 2; 1045d95585fb0ec024f6abd96f7b02e0df58019d46afjohannkoenig@chromium.org dst_u += dst_stride_u; 1046d95585fb0ec024f6abd96f7b02e0df58019d46afjohannkoenig@chromium.org dst_v += dst_stride_v; 1047d95585fb0ec024f6abd96f7b02e0df58019d46afjohannkoenig@chromium.org } 1048d95585fb0ec024f6abd96f7b02e0df58019d46afjohannkoenig@chromium.org if (height & 1) { 104941294d96d7dbf9bc215b09832a8336c5fb158f0bjohannkoenig@chromium.org#if defined(HAS_RGB24TOYROW_NEON) 1050d95585fb0ec024f6abd96f7b02e0df58019d46afjohannkoenig@chromium.org RGB24ToUVRow(src_rgb24, 0, dst_u, dst_v, width); 1051d95585fb0ec024f6abd96f7b02e0df58019d46afjohannkoenig@chromium.org RGB24ToYRow(src_rgb24, dst_y, width); 105241294d96d7dbf9bc215b09832a8336c5fb158f0bjohannkoenig@chromium.org#else 1053d95585fb0ec024f6abd96f7b02e0df58019d46afjohannkoenig@chromium.org RGB24ToARGBRow(src_rgb24, row, width); 1054d95585fb0ec024f6abd96f7b02e0df58019d46afjohannkoenig@chromium.org ARGBToUVRow(row, 0, dst_u, dst_v, width); 1055d95585fb0ec024f6abd96f7b02e0df58019d46afjohannkoenig@chromium.org ARGBToYRow(row, dst_y, width); 105641294d96d7dbf9bc215b09832a8336c5fb158f0bjohannkoenig@chromium.org#endif 1057d95585fb0ec024f6abd96f7b02e0df58019d46afjohannkoenig@chromium.org } 105841294d96d7dbf9bc215b09832a8336c5fb158f0bjohannkoenig@chromium.org#if !defined(HAS_RGB24TOYROW_NEON) 1059d95585fb0ec024f6abd96f7b02e0df58019d46afjohannkoenig@chromium.org free_aligned_buffer_64(row); 106041294d96d7dbf9bc215b09832a8336c5fb158f0bjohannkoenig@chromium.org#endif 1061d95585fb0ec024f6abd96f7b02e0df58019d46afjohannkoenig@chromium.org } 106241294d96d7dbf9bc215b09832a8336c5fb158f0bjohannkoenig@chromium.org return 0; 106341294d96d7dbf9bc215b09832a8336c5fb158f0bjohannkoenig@chromium.org} 106441294d96d7dbf9bc215b09832a8336c5fb158f0bjohannkoenig@chromium.org 106541294d96d7dbf9bc215b09832a8336c5fb158f0bjohannkoenig@chromium.org// Convert RAW to I420. 106641294d96d7dbf9bc215b09832a8336c5fb158f0bjohannkoenig@chromium.orgLIBYUV_API 106741294d96d7dbf9bc215b09832a8336c5fb158f0bjohannkoenig@chromium.orgint RAWToI420(const uint8* src_raw, int src_stride_raw, 106841294d96d7dbf9bc215b09832a8336c5fb158f0bjohannkoenig@chromium.org uint8* dst_y, int dst_stride_y, 106941294d96d7dbf9bc215b09832a8336c5fb158f0bjohannkoenig@chromium.org uint8* dst_u, int dst_stride_u, 107041294d96d7dbf9bc215b09832a8336c5fb158f0bjohannkoenig@chromium.org uint8* dst_v, int dst_stride_v, 107141294d96d7dbf9bc215b09832a8336c5fb158f0bjohannkoenig@chromium.org int width, int height) { 107241294d96d7dbf9bc215b09832a8336c5fb158f0bjohannkoenig@chromium.org int y; 107341294d96d7dbf9bc215b09832a8336c5fb158f0bjohannkoenig@chromium.org#if defined(HAS_RAWTOYROW_NEON) 107441294d96d7dbf9bc215b09832a8336c5fb158f0bjohannkoenig@chromium.org void (*RAWToUVRow)(const uint8* src_raw, int src_stride_raw, 107541294d96d7dbf9bc215b09832a8336c5fb158f0bjohannkoenig@chromium.org uint8* dst_u, uint8* dst_v, int width) = RAWToUVRow_C; 107641294d96d7dbf9bc215b09832a8336c5fb158f0bjohannkoenig@chromium.org void (*RAWToYRow)(const uint8* src_raw, uint8* dst_y, int pix) = 107741294d96d7dbf9bc215b09832a8336c5fb158f0bjohannkoenig@chromium.org RAWToYRow_C; 107841294d96d7dbf9bc215b09832a8336c5fb158f0bjohannkoenig@chromium.org#else 107941294d96d7dbf9bc215b09832a8336c5fb158f0bjohannkoenig@chromium.org void (*RAWToARGBRow)(const uint8* src_rgb, uint8* dst_argb, int pix) = 108041294d96d7dbf9bc215b09832a8336c5fb158f0bjohannkoenig@chromium.org RAWToARGBRow_C; 108141294d96d7dbf9bc215b09832a8336c5fb158f0bjohannkoenig@chromium.org void (*ARGBToUVRow)(const uint8* src_argb0, int src_stride_argb, 108241294d96d7dbf9bc215b09832a8336c5fb158f0bjohannkoenig@chromium.org uint8* dst_u, uint8* dst_v, int width) = ARGBToUVRow_C; 108341294d96d7dbf9bc215b09832a8336c5fb158f0bjohannkoenig@chromium.org void (*ARGBToYRow)(const uint8* src_argb, uint8* dst_y, int pix) = 108441294d96d7dbf9bc215b09832a8336c5fb158f0bjohannkoenig@chromium.org ARGBToYRow_C; 108541294d96d7dbf9bc215b09832a8336c5fb158f0bjohannkoenig@chromium.org#endif 108641294d96d7dbf9bc215b09832a8336c5fb158f0bjohannkoenig@chromium.org if (!src_raw || !dst_y || !dst_u || !dst_v || 108741294d96d7dbf9bc215b09832a8336c5fb158f0bjohannkoenig@chromium.org width <= 0 || height == 0) { 108841294d96d7dbf9bc215b09832a8336c5fb158f0bjohannkoenig@chromium.org return -1; 108941294d96d7dbf9bc215b09832a8336c5fb158f0bjohannkoenig@chromium.org } 109041294d96d7dbf9bc215b09832a8336c5fb158f0bjohannkoenig@chromium.org // Negative height means invert the image. 109141294d96d7dbf9bc215b09832a8336c5fb158f0bjohannkoenig@chromium.org if (height < 0) { 109241294d96d7dbf9bc215b09832a8336c5fb158f0bjohannkoenig@chromium.org height = -height; 109341294d96d7dbf9bc215b09832a8336c5fb158f0bjohannkoenig@chromium.org src_raw = src_raw + (height - 1) * src_stride_raw; 109441294d96d7dbf9bc215b09832a8336c5fb158f0bjohannkoenig@chromium.org src_stride_raw = -src_stride_raw; 109541294d96d7dbf9bc215b09832a8336c5fb158f0bjohannkoenig@chromium.org } 109641294d96d7dbf9bc215b09832a8336c5fb158f0bjohannkoenig@chromium.org 109741294d96d7dbf9bc215b09832a8336c5fb158f0bjohannkoenig@chromium.org#if defined(HAS_RAWTOYROW_NEON) 109841294d96d7dbf9bc215b09832a8336c5fb158f0bjohannkoenig@chromium.org if (TestCpuFlag(kCpuHasNEON) && width >= 8) { 109941294d96d7dbf9bc215b09832a8336c5fb158f0bjohannkoenig@chromium.org RAWToYRow = RAWToYRow_Any_NEON; 110041294d96d7dbf9bc215b09832a8336c5fb158f0bjohannkoenig@chromium.org if (IS_ALIGNED(width, 8)) { 110141294d96d7dbf9bc215b09832a8336c5fb158f0bjohannkoenig@chromium.org RAWToYRow = RAWToYRow_NEON; 110241294d96d7dbf9bc215b09832a8336c5fb158f0bjohannkoenig@chromium.org } 110341294d96d7dbf9bc215b09832a8336c5fb158f0bjohannkoenig@chromium.org if (width >= 16) { 110441294d96d7dbf9bc215b09832a8336c5fb158f0bjohannkoenig@chromium.org RAWToUVRow = RAWToUVRow_Any_NEON; 110541294d96d7dbf9bc215b09832a8336c5fb158f0bjohannkoenig@chromium.org if (IS_ALIGNED(width, 16)) { 110641294d96d7dbf9bc215b09832a8336c5fb158f0bjohannkoenig@chromium.org RAWToUVRow = RAWToUVRow_NEON; 110741294d96d7dbf9bc215b09832a8336c5fb158f0bjohannkoenig@chromium.org } 110841294d96d7dbf9bc215b09832a8336c5fb158f0bjohannkoenig@chromium.org } 110941294d96d7dbf9bc215b09832a8336c5fb158f0bjohannkoenig@chromium.org } 111041294d96d7dbf9bc215b09832a8336c5fb158f0bjohannkoenig@chromium.org#else // HAS_RAWTOYROW_NEON 111141294d96d7dbf9bc215b09832a8336c5fb158f0bjohannkoenig@chromium.org 111241294d96d7dbf9bc215b09832a8336c5fb158f0bjohannkoenig@chromium.org#if defined(HAS_RAWTOARGBROW_SSSE3) 111341294d96d7dbf9bc215b09832a8336c5fb158f0bjohannkoenig@chromium.org if (TestCpuFlag(kCpuHasSSSE3) && width >= 16) { 111441294d96d7dbf9bc215b09832a8336c5fb158f0bjohannkoenig@chromium.org RAWToARGBRow = RAWToARGBRow_Any_SSSE3; 111541294d96d7dbf9bc215b09832a8336c5fb158f0bjohannkoenig@chromium.org if (IS_ALIGNED(width, 16)) { 111641294d96d7dbf9bc215b09832a8336c5fb158f0bjohannkoenig@chromium.org RAWToARGBRow = RAWToARGBRow_SSSE3; 111741294d96d7dbf9bc215b09832a8336c5fb158f0bjohannkoenig@chromium.org } 111841294d96d7dbf9bc215b09832a8336c5fb158f0bjohannkoenig@chromium.org } 111941294d96d7dbf9bc215b09832a8336c5fb158f0bjohannkoenig@chromium.org#endif 112041294d96d7dbf9bc215b09832a8336c5fb158f0bjohannkoenig@chromium.org#if defined(HAS_ARGBTOUVROW_SSSE3) 112141294d96d7dbf9bc215b09832a8336c5fb158f0bjohannkoenig@chromium.org if (TestCpuFlag(kCpuHasSSSE3) && width >= 16) { 112241294d96d7dbf9bc215b09832a8336c5fb158f0bjohannkoenig@chromium.org ARGBToUVRow = ARGBToUVRow_Any_SSSE3; 112341294d96d7dbf9bc215b09832a8336c5fb158f0bjohannkoenig@chromium.org if (IS_ALIGNED(width, 16)) { 112441294d96d7dbf9bc215b09832a8336c5fb158f0bjohannkoenig@chromium.org ARGBToUVRow = ARGBToUVRow_SSSE3; 112541294d96d7dbf9bc215b09832a8336c5fb158f0bjohannkoenig@chromium.org } 112641294d96d7dbf9bc215b09832a8336c5fb158f0bjohannkoenig@chromium.org } 112741294d96d7dbf9bc215b09832a8336c5fb158f0bjohannkoenig@chromium.org#endif 112841294d96d7dbf9bc215b09832a8336c5fb158f0bjohannkoenig@chromium.org#if defined(HAS_ARGBTOUVROW_SSSE3) 112941294d96d7dbf9bc215b09832a8336c5fb158f0bjohannkoenig@chromium.org if (TestCpuFlag(kCpuHasSSSE3) && width >= 16) { 113041294d96d7dbf9bc215b09832a8336c5fb158f0bjohannkoenig@chromium.org ARGBToYRow = ARGBToYRow_Any_SSSE3; 113141294d96d7dbf9bc215b09832a8336c5fb158f0bjohannkoenig@chromium.org if (IS_ALIGNED(width, 16)) { 113241294d96d7dbf9bc215b09832a8336c5fb158f0bjohannkoenig@chromium.org ARGBToYRow = ARGBToYRow_Unaligned_SSSE3; 113341294d96d7dbf9bc215b09832a8336c5fb158f0bjohannkoenig@chromium.org if (IS_ALIGNED(dst_y, 16) && IS_ALIGNED(dst_stride_y, 16)) { 113441294d96d7dbf9bc215b09832a8336c5fb158f0bjohannkoenig@chromium.org ARGBToYRow = ARGBToYRow_SSSE3; 113541294d96d7dbf9bc215b09832a8336c5fb158f0bjohannkoenig@chromium.org } 113641294d96d7dbf9bc215b09832a8336c5fb158f0bjohannkoenig@chromium.org } 113741294d96d7dbf9bc215b09832a8336c5fb158f0bjohannkoenig@chromium.org } 113841294d96d7dbf9bc215b09832a8336c5fb158f0bjohannkoenig@chromium.org#endif // HAS_ARGBTOUVROW_SSSE3 113941294d96d7dbf9bc215b09832a8336c5fb158f0bjohannkoenig@chromium.org#endif // HAS_RAWTOYROW_NEON 114041294d96d7dbf9bc215b09832a8336c5fb158f0bjohannkoenig@chromium.org 1141d95585fb0ec024f6abd96f7b02e0df58019d46afjohannkoenig@chromium.org { 1142d95585fb0ec024f6abd96f7b02e0df58019d46afjohannkoenig@chromium.org // Allocate 2 rows of ARGB. 1143d95585fb0ec024f6abd96f7b02e0df58019d46afjohannkoenig@chromium.org const int kRowSize = (width * 4 + 15) & ~15; 1144d95585fb0ec024f6abd96f7b02e0df58019d46afjohannkoenig@chromium.org align_buffer_64(row, kRowSize * 2); 1145d95585fb0ec024f6abd96f7b02e0df58019d46afjohannkoenig@chromium.org 1146d95585fb0ec024f6abd96f7b02e0df58019d46afjohannkoenig@chromium.org for (y = 0; y < height - 1; y += 2) { 1147d95585fb0ec024f6abd96f7b02e0df58019d46afjohannkoenig@chromium.org #if defined(HAS_RAWTOYROW_NEON) 1148d95585fb0ec024f6abd96f7b02e0df58019d46afjohannkoenig@chromium.org RAWToUVRow(src_raw, src_stride_raw, dst_u, dst_v, width); 1149d95585fb0ec024f6abd96f7b02e0df58019d46afjohannkoenig@chromium.org RAWToYRow(src_raw, dst_y, width); 1150d95585fb0ec024f6abd96f7b02e0df58019d46afjohannkoenig@chromium.org RAWToYRow(src_raw + src_stride_raw, dst_y + dst_stride_y, width); 1151d95585fb0ec024f6abd96f7b02e0df58019d46afjohannkoenig@chromium.org #else 1152d95585fb0ec024f6abd96f7b02e0df58019d46afjohannkoenig@chromium.org RAWToARGBRow(src_raw, row, width); 1153d95585fb0ec024f6abd96f7b02e0df58019d46afjohannkoenig@chromium.org RAWToARGBRow(src_raw + src_stride_raw, row + kRowSize, width); 1154d95585fb0ec024f6abd96f7b02e0df58019d46afjohannkoenig@chromium.org ARGBToUVRow(row, kRowSize, dst_u, dst_v, width); 1155d95585fb0ec024f6abd96f7b02e0df58019d46afjohannkoenig@chromium.org ARGBToYRow(row, dst_y, width); 1156d95585fb0ec024f6abd96f7b02e0df58019d46afjohannkoenig@chromium.org ARGBToYRow(row + kRowSize, dst_y + dst_stride_y, width); 1157d95585fb0ec024f6abd96f7b02e0df58019d46afjohannkoenig@chromium.org #endif 1158d95585fb0ec024f6abd96f7b02e0df58019d46afjohannkoenig@chromium.org src_raw += src_stride_raw * 2; 1159d95585fb0ec024f6abd96f7b02e0df58019d46afjohannkoenig@chromium.org dst_y += dst_stride_y * 2; 1160d95585fb0ec024f6abd96f7b02e0df58019d46afjohannkoenig@chromium.org dst_u += dst_stride_u; 1161d95585fb0ec024f6abd96f7b02e0df58019d46afjohannkoenig@chromium.org dst_v += dst_stride_v; 1162d95585fb0ec024f6abd96f7b02e0df58019d46afjohannkoenig@chromium.org } 1163d95585fb0ec024f6abd96f7b02e0df58019d46afjohannkoenig@chromium.org if (height & 1) { 1164d95585fb0ec024f6abd96f7b02e0df58019d46afjohannkoenig@chromium.org #if defined(HAS_RAWTOYROW_NEON) 1165d95585fb0ec024f6abd96f7b02e0df58019d46afjohannkoenig@chromium.org RAWToUVRow(src_raw, 0, dst_u, dst_v, width); 1166d95585fb0ec024f6abd96f7b02e0df58019d46afjohannkoenig@chromium.org RAWToYRow(src_raw, dst_y, width); 1167d95585fb0ec024f6abd96f7b02e0df58019d46afjohannkoenig@chromium.org #else 1168d95585fb0ec024f6abd96f7b02e0df58019d46afjohannkoenig@chromium.org RAWToARGBRow(src_raw, row, width); 1169d95585fb0ec024f6abd96f7b02e0df58019d46afjohannkoenig@chromium.org ARGBToUVRow(row, 0, dst_u, dst_v, width); 1170d95585fb0ec024f6abd96f7b02e0df58019d46afjohannkoenig@chromium.org ARGBToYRow(row, dst_y, width); 1171d95585fb0ec024f6abd96f7b02e0df58019d46afjohannkoenig@chromium.org #endif 1172d95585fb0ec024f6abd96f7b02e0df58019d46afjohannkoenig@chromium.org } 1173d95585fb0ec024f6abd96f7b02e0df58019d46afjohannkoenig@chromium.org #if !defined(HAS_RAWTOYROW_NEON) 1174d95585fb0ec024f6abd96f7b02e0df58019d46afjohannkoenig@chromium.org free_aligned_buffer_64(row); 1175d95585fb0ec024f6abd96f7b02e0df58019d46afjohannkoenig@chromium.org #endif 117641294d96d7dbf9bc215b09832a8336c5fb158f0bjohannkoenig@chromium.org } 117741294d96d7dbf9bc215b09832a8336c5fb158f0bjohannkoenig@chromium.org return 0; 117841294d96d7dbf9bc215b09832a8336c5fb158f0bjohannkoenig@chromium.org} 117941294d96d7dbf9bc215b09832a8336c5fb158f0bjohannkoenig@chromium.org 118041294d96d7dbf9bc215b09832a8336c5fb158f0bjohannkoenig@chromium.org// Convert RGB565 to I420. 118141294d96d7dbf9bc215b09832a8336c5fb158f0bjohannkoenig@chromium.orgLIBYUV_API 118241294d96d7dbf9bc215b09832a8336c5fb158f0bjohannkoenig@chromium.orgint RGB565ToI420(const uint8* src_rgb565, int src_stride_rgb565, 118341294d96d7dbf9bc215b09832a8336c5fb158f0bjohannkoenig@chromium.org uint8* dst_y, int dst_stride_y, 118441294d96d7dbf9bc215b09832a8336c5fb158f0bjohannkoenig@chromium.org uint8* dst_u, int dst_stride_u, 118541294d96d7dbf9bc215b09832a8336c5fb158f0bjohannkoenig@chromium.org uint8* dst_v, int dst_stride_v, 118641294d96d7dbf9bc215b09832a8336c5fb158f0bjohannkoenig@chromium.org int width, int height) { 118741294d96d7dbf9bc215b09832a8336c5fb158f0bjohannkoenig@chromium.org int y; 118841294d96d7dbf9bc215b09832a8336c5fb158f0bjohannkoenig@chromium.org#if defined(HAS_RGB565TOYROW_NEON) 118941294d96d7dbf9bc215b09832a8336c5fb158f0bjohannkoenig@chromium.org void (*RGB565ToUVRow)(const uint8* src_rgb565, int src_stride_rgb565, 119041294d96d7dbf9bc215b09832a8336c5fb158f0bjohannkoenig@chromium.org uint8* dst_u, uint8* dst_v, int width) = RGB565ToUVRow_C; 119141294d96d7dbf9bc215b09832a8336c5fb158f0bjohannkoenig@chromium.org void (*RGB565ToYRow)(const uint8* src_rgb565, uint8* dst_y, int pix) = 119241294d96d7dbf9bc215b09832a8336c5fb158f0bjohannkoenig@chromium.org RGB565ToYRow_C; 119341294d96d7dbf9bc215b09832a8336c5fb158f0bjohannkoenig@chromium.org#else 119441294d96d7dbf9bc215b09832a8336c5fb158f0bjohannkoenig@chromium.org void (*RGB565ToARGBRow)(const uint8* src_rgb, uint8* dst_argb, int pix) = 119541294d96d7dbf9bc215b09832a8336c5fb158f0bjohannkoenig@chromium.org RGB565ToARGBRow_C; 119641294d96d7dbf9bc215b09832a8336c5fb158f0bjohannkoenig@chromium.org void (*ARGBToUVRow)(const uint8* src_argb0, int src_stride_argb, 119741294d96d7dbf9bc215b09832a8336c5fb158f0bjohannkoenig@chromium.org uint8* dst_u, uint8* dst_v, int width) = ARGBToUVRow_C; 119841294d96d7dbf9bc215b09832a8336c5fb158f0bjohannkoenig@chromium.org void (*ARGBToYRow)(const uint8* src_argb, uint8* dst_y, int pix) = 119941294d96d7dbf9bc215b09832a8336c5fb158f0bjohannkoenig@chromium.org ARGBToYRow_C; 120041294d96d7dbf9bc215b09832a8336c5fb158f0bjohannkoenig@chromium.org#endif 120141294d96d7dbf9bc215b09832a8336c5fb158f0bjohannkoenig@chromium.org if (!src_rgb565 || !dst_y || !dst_u || !dst_v || 120241294d96d7dbf9bc215b09832a8336c5fb158f0bjohannkoenig@chromium.org width <= 0 || height == 0) { 120341294d96d7dbf9bc215b09832a8336c5fb158f0bjohannkoenig@chromium.org return -1; 120441294d96d7dbf9bc215b09832a8336c5fb158f0bjohannkoenig@chromium.org } 120541294d96d7dbf9bc215b09832a8336c5fb158f0bjohannkoenig@chromium.org // Negative height means invert the image. 120641294d96d7dbf9bc215b09832a8336c5fb158f0bjohannkoenig@chromium.org if (height < 0) { 120741294d96d7dbf9bc215b09832a8336c5fb158f0bjohannkoenig@chromium.org height = -height; 120841294d96d7dbf9bc215b09832a8336c5fb158f0bjohannkoenig@chromium.org src_rgb565 = src_rgb565 + (height - 1) * src_stride_rgb565; 120941294d96d7dbf9bc215b09832a8336c5fb158f0bjohannkoenig@chromium.org src_stride_rgb565 = -src_stride_rgb565; 121041294d96d7dbf9bc215b09832a8336c5fb158f0bjohannkoenig@chromium.org } 121141294d96d7dbf9bc215b09832a8336c5fb158f0bjohannkoenig@chromium.org 121241294d96d7dbf9bc215b09832a8336c5fb158f0bjohannkoenig@chromium.org#if defined(HAS_RGB565TOYROW_NEON) 121341294d96d7dbf9bc215b09832a8336c5fb158f0bjohannkoenig@chromium.org if (TestCpuFlag(kCpuHasNEON) && width >= 8) { 121441294d96d7dbf9bc215b09832a8336c5fb158f0bjohannkoenig@chromium.org RGB565ToYRow = RGB565ToYRow_Any_NEON; 121541294d96d7dbf9bc215b09832a8336c5fb158f0bjohannkoenig@chromium.org if (IS_ALIGNED(width, 8)) { 121641294d96d7dbf9bc215b09832a8336c5fb158f0bjohannkoenig@chromium.org RGB565ToYRow = RGB565ToYRow_NEON; 121741294d96d7dbf9bc215b09832a8336c5fb158f0bjohannkoenig@chromium.org } 121841294d96d7dbf9bc215b09832a8336c5fb158f0bjohannkoenig@chromium.org if (width >= 16) { 121941294d96d7dbf9bc215b09832a8336c5fb158f0bjohannkoenig@chromium.org RGB565ToUVRow = RGB565ToUVRow_Any_NEON; 122041294d96d7dbf9bc215b09832a8336c5fb158f0bjohannkoenig@chromium.org if (IS_ALIGNED(width, 16)) { 122141294d96d7dbf9bc215b09832a8336c5fb158f0bjohannkoenig@chromium.org RGB565ToUVRow = RGB565ToUVRow_NEON; 122241294d96d7dbf9bc215b09832a8336c5fb158f0bjohannkoenig@chromium.org } 122341294d96d7dbf9bc215b09832a8336c5fb158f0bjohannkoenig@chromium.org } 122441294d96d7dbf9bc215b09832a8336c5fb158f0bjohannkoenig@chromium.org } 122541294d96d7dbf9bc215b09832a8336c5fb158f0bjohannkoenig@chromium.org#else // HAS_RGB565TOYROW_NEON 122641294d96d7dbf9bc215b09832a8336c5fb158f0bjohannkoenig@chromium.org 122741294d96d7dbf9bc215b09832a8336c5fb158f0bjohannkoenig@chromium.org#if defined(HAS_RGB565TOARGBROW_SSE2) 122841294d96d7dbf9bc215b09832a8336c5fb158f0bjohannkoenig@chromium.org if (TestCpuFlag(kCpuHasSSE2) && width >= 8) { 122941294d96d7dbf9bc215b09832a8336c5fb158f0bjohannkoenig@chromium.org RGB565ToARGBRow = RGB565ToARGBRow_Any_SSE2; 123041294d96d7dbf9bc215b09832a8336c5fb158f0bjohannkoenig@chromium.org if (IS_ALIGNED(width, 8)) { 123141294d96d7dbf9bc215b09832a8336c5fb158f0bjohannkoenig@chromium.org RGB565ToARGBRow = RGB565ToARGBRow_SSE2; 123241294d96d7dbf9bc215b09832a8336c5fb158f0bjohannkoenig@chromium.org } 123341294d96d7dbf9bc215b09832a8336c5fb158f0bjohannkoenig@chromium.org } 123441294d96d7dbf9bc215b09832a8336c5fb158f0bjohannkoenig@chromium.org#endif 123541294d96d7dbf9bc215b09832a8336c5fb158f0bjohannkoenig@chromium.org#if defined(HAS_ARGBTOUVROW_SSSE3) 123641294d96d7dbf9bc215b09832a8336c5fb158f0bjohannkoenig@chromium.org if (TestCpuFlag(kCpuHasSSSE3) && width >= 16) { 123741294d96d7dbf9bc215b09832a8336c5fb158f0bjohannkoenig@chromium.org ARGBToUVRow = ARGBToUVRow_Any_SSSE3; 123841294d96d7dbf9bc215b09832a8336c5fb158f0bjohannkoenig@chromium.org if (IS_ALIGNED(width, 16)) { 123941294d96d7dbf9bc215b09832a8336c5fb158f0bjohannkoenig@chromium.org ARGBToUVRow = ARGBToUVRow_SSSE3; 124041294d96d7dbf9bc215b09832a8336c5fb158f0bjohannkoenig@chromium.org } 124141294d96d7dbf9bc215b09832a8336c5fb158f0bjohannkoenig@chromium.org } 124241294d96d7dbf9bc215b09832a8336c5fb158f0bjohannkoenig@chromium.org#endif 124341294d96d7dbf9bc215b09832a8336c5fb158f0bjohannkoenig@chromium.org#if defined(HAS_ARGBTOUVROW_SSSE3) 124441294d96d7dbf9bc215b09832a8336c5fb158f0bjohannkoenig@chromium.org if (TestCpuFlag(kCpuHasSSSE3) && width >= 16) { 124541294d96d7dbf9bc215b09832a8336c5fb158f0bjohannkoenig@chromium.org ARGBToYRow = ARGBToYRow_Any_SSSE3; 124641294d96d7dbf9bc215b09832a8336c5fb158f0bjohannkoenig@chromium.org if (IS_ALIGNED(width, 16)) { 124741294d96d7dbf9bc215b09832a8336c5fb158f0bjohannkoenig@chromium.org ARGBToYRow = ARGBToYRow_Unaligned_SSSE3; 124841294d96d7dbf9bc215b09832a8336c5fb158f0bjohannkoenig@chromium.org if (IS_ALIGNED(dst_y, 16) && IS_ALIGNED(dst_stride_y, 16)) { 124941294d96d7dbf9bc215b09832a8336c5fb158f0bjohannkoenig@chromium.org ARGBToYRow = ARGBToYRow_SSSE3; 125041294d96d7dbf9bc215b09832a8336c5fb158f0bjohannkoenig@chromium.org } 125141294d96d7dbf9bc215b09832a8336c5fb158f0bjohannkoenig@chromium.org } 125241294d96d7dbf9bc215b09832a8336c5fb158f0bjohannkoenig@chromium.org } 125341294d96d7dbf9bc215b09832a8336c5fb158f0bjohannkoenig@chromium.org#endif // HAS_ARGBTOUVROW_SSSE3 125441294d96d7dbf9bc215b09832a8336c5fb158f0bjohannkoenig@chromium.org#endif // HAS_RGB565TOYROW_NEON 125541294d96d7dbf9bc215b09832a8336c5fb158f0bjohannkoenig@chromium.org 1256d95585fb0ec024f6abd96f7b02e0df58019d46afjohannkoenig@chromium.org { 1257d95585fb0ec024f6abd96f7b02e0df58019d46afjohannkoenig@chromium.org#if !defined(HAS_RGB565TOYROW_NEON) 1258d95585fb0ec024f6abd96f7b02e0df58019d46afjohannkoenig@chromium.org // Allocate 2 rows of ARGB. 1259d95585fb0ec024f6abd96f7b02e0df58019d46afjohannkoenig@chromium.org const int kRowSize = (width * 4 + 15) & ~15; 1260d95585fb0ec024f6abd96f7b02e0df58019d46afjohannkoenig@chromium.org align_buffer_64(row, kRowSize * 2); 1261d95585fb0ec024f6abd96f7b02e0df58019d46afjohannkoenig@chromium.org#endif 1262d95585fb0ec024f6abd96f7b02e0df58019d46afjohannkoenig@chromium.org 1263d95585fb0ec024f6abd96f7b02e0df58019d46afjohannkoenig@chromium.org for (y = 0; y < height - 1; y += 2) { 126441294d96d7dbf9bc215b09832a8336c5fb158f0bjohannkoenig@chromium.org#if defined(HAS_RGB565TOYROW_NEON) 1265d95585fb0ec024f6abd96f7b02e0df58019d46afjohannkoenig@chromium.org RGB565ToUVRow(src_rgb565, src_stride_rgb565, dst_u, dst_v, width); 1266d95585fb0ec024f6abd96f7b02e0df58019d46afjohannkoenig@chromium.org RGB565ToYRow(src_rgb565, dst_y, width); 1267d95585fb0ec024f6abd96f7b02e0df58019d46afjohannkoenig@chromium.org RGB565ToYRow(src_rgb565 + src_stride_rgb565, dst_y + dst_stride_y, width); 126841294d96d7dbf9bc215b09832a8336c5fb158f0bjohannkoenig@chromium.org#else 1269d95585fb0ec024f6abd96f7b02e0df58019d46afjohannkoenig@chromium.org RGB565ToARGBRow(src_rgb565, row, width); 1270d95585fb0ec024f6abd96f7b02e0df58019d46afjohannkoenig@chromium.org RGB565ToARGBRow(src_rgb565 + src_stride_rgb565, row + kRowSize, width); 1271d95585fb0ec024f6abd96f7b02e0df58019d46afjohannkoenig@chromium.org ARGBToUVRow(row, kRowSize, dst_u, dst_v, width); 1272d95585fb0ec024f6abd96f7b02e0df58019d46afjohannkoenig@chromium.org ARGBToYRow(row, dst_y, width); 1273d95585fb0ec024f6abd96f7b02e0df58019d46afjohannkoenig@chromium.org ARGBToYRow(row + kRowSize, dst_y + dst_stride_y, width); 127441294d96d7dbf9bc215b09832a8336c5fb158f0bjohannkoenig@chromium.org#endif 1275d95585fb0ec024f6abd96f7b02e0df58019d46afjohannkoenig@chromium.org src_rgb565 += src_stride_rgb565 * 2; 1276d95585fb0ec024f6abd96f7b02e0df58019d46afjohannkoenig@chromium.org dst_y += dst_stride_y * 2; 1277d95585fb0ec024f6abd96f7b02e0df58019d46afjohannkoenig@chromium.org dst_u += dst_stride_u; 1278d95585fb0ec024f6abd96f7b02e0df58019d46afjohannkoenig@chromium.org dst_v += dst_stride_v; 1279d95585fb0ec024f6abd96f7b02e0df58019d46afjohannkoenig@chromium.org } 1280d95585fb0ec024f6abd96f7b02e0df58019d46afjohannkoenig@chromium.org if (height & 1) { 128141294d96d7dbf9bc215b09832a8336c5fb158f0bjohannkoenig@chromium.org#if defined(HAS_RGB565TOYROW_NEON) 1282d95585fb0ec024f6abd96f7b02e0df58019d46afjohannkoenig@chromium.org RGB565ToUVRow(src_rgb565, 0, dst_u, dst_v, width); 1283d95585fb0ec024f6abd96f7b02e0df58019d46afjohannkoenig@chromium.org RGB565ToYRow(src_rgb565, dst_y, width); 128441294d96d7dbf9bc215b09832a8336c5fb158f0bjohannkoenig@chromium.org#else 1285d95585fb0ec024f6abd96f7b02e0df58019d46afjohannkoenig@chromium.org RGB565ToARGBRow(src_rgb565, row, width); 1286d95585fb0ec024f6abd96f7b02e0df58019d46afjohannkoenig@chromium.org ARGBToUVRow(row, 0, dst_u, dst_v, width); 1287d95585fb0ec024f6abd96f7b02e0df58019d46afjohannkoenig@chromium.org ARGBToYRow(row, dst_y, width); 128841294d96d7dbf9bc215b09832a8336c5fb158f0bjohannkoenig@chromium.org#endif 1289d95585fb0ec024f6abd96f7b02e0df58019d46afjohannkoenig@chromium.org } 129041294d96d7dbf9bc215b09832a8336c5fb158f0bjohannkoenig@chromium.org#if !defined(HAS_RGB565TOYROW_NEON) 1291d95585fb0ec024f6abd96f7b02e0df58019d46afjohannkoenig@chromium.org free_aligned_buffer_64(row); 129241294d96d7dbf9bc215b09832a8336c5fb158f0bjohannkoenig@chromium.org#endif 1293d95585fb0ec024f6abd96f7b02e0df58019d46afjohannkoenig@chromium.org } 129441294d96d7dbf9bc215b09832a8336c5fb158f0bjohannkoenig@chromium.org return 0; 129541294d96d7dbf9bc215b09832a8336c5fb158f0bjohannkoenig@chromium.org} 129641294d96d7dbf9bc215b09832a8336c5fb158f0bjohannkoenig@chromium.org 129741294d96d7dbf9bc215b09832a8336c5fb158f0bjohannkoenig@chromium.org// Convert ARGB1555 to I420. 129841294d96d7dbf9bc215b09832a8336c5fb158f0bjohannkoenig@chromium.orgLIBYUV_API 129941294d96d7dbf9bc215b09832a8336c5fb158f0bjohannkoenig@chromium.orgint ARGB1555ToI420(const uint8* src_argb1555, int src_stride_argb1555, 130041294d96d7dbf9bc215b09832a8336c5fb158f0bjohannkoenig@chromium.org uint8* dst_y, int dst_stride_y, 130141294d96d7dbf9bc215b09832a8336c5fb158f0bjohannkoenig@chromium.org uint8* dst_u, int dst_stride_u, 130241294d96d7dbf9bc215b09832a8336c5fb158f0bjohannkoenig@chromium.org uint8* dst_v, int dst_stride_v, 130341294d96d7dbf9bc215b09832a8336c5fb158f0bjohannkoenig@chromium.org int width, int height) { 130441294d96d7dbf9bc215b09832a8336c5fb158f0bjohannkoenig@chromium.org int y; 130541294d96d7dbf9bc215b09832a8336c5fb158f0bjohannkoenig@chromium.org#if defined(HAS_ARGB1555TOYROW_NEON) 130641294d96d7dbf9bc215b09832a8336c5fb158f0bjohannkoenig@chromium.org void (*ARGB1555ToUVRow)(const uint8* src_argb1555, int src_stride_argb1555, 130741294d96d7dbf9bc215b09832a8336c5fb158f0bjohannkoenig@chromium.org uint8* dst_u, uint8* dst_v, int width) = ARGB1555ToUVRow_C; 130841294d96d7dbf9bc215b09832a8336c5fb158f0bjohannkoenig@chromium.org void (*ARGB1555ToYRow)(const uint8* src_argb1555, uint8* dst_y, int pix) = 130941294d96d7dbf9bc215b09832a8336c5fb158f0bjohannkoenig@chromium.org ARGB1555ToYRow_C; 131041294d96d7dbf9bc215b09832a8336c5fb158f0bjohannkoenig@chromium.org#else 131141294d96d7dbf9bc215b09832a8336c5fb158f0bjohannkoenig@chromium.org void (*ARGB1555ToARGBRow)(const uint8* src_rgb, uint8* dst_argb, int pix) = 131241294d96d7dbf9bc215b09832a8336c5fb158f0bjohannkoenig@chromium.org ARGB1555ToARGBRow_C; 131341294d96d7dbf9bc215b09832a8336c5fb158f0bjohannkoenig@chromium.org void (*ARGBToUVRow)(const uint8* src_argb0, int src_stride_argb, 131441294d96d7dbf9bc215b09832a8336c5fb158f0bjohannkoenig@chromium.org uint8* dst_u, uint8* dst_v, int width) = ARGBToUVRow_C; 131541294d96d7dbf9bc215b09832a8336c5fb158f0bjohannkoenig@chromium.org void (*ARGBToYRow)(const uint8* src_argb, uint8* dst_y, int pix) = 131641294d96d7dbf9bc215b09832a8336c5fb158f0bjohannkoenig@chromium.org ARGBToYRow_C; 131741294d96d7dbf9bc215b09832a8336c5fb158f0bjohannkoenig@chromium.org#endif 131841294d96d7dbf9bc215b09832a8336c5fb158f0bjohannkoenig@chromium.org if (!src_argb1555 || !dst_y || !dst_u || !dst_v || 131941294d96d7dbf9bc215b09832a8336c5fb158f0bjohannkoenig@chromium.org width <= 0 || height == 0) { 132041294d96d7dbf9bc215b09832a8336c5fb158f0bjohannkoenig@chromium.org return -1; 132141294d96d7dbf9bc215b09832a8336c5fb158f0bjohannkoenig@chromium.org } 132241294d96d7dbf9bc215b09832a8336c5fb158f0bjohannkoenig@chromium.org // Negative height means invert the image. 132341294d96d7dbf9bc215b09832a8336c5fb158f0bjohannkoenig@chromium.org if (height < 0) { 132441294d96d7dbf9bc215b09832a8336c5fb158f0bjohannkoenig@chromium.org height = -height; 132541294d96d7dbf9bc215b09832a8336c5fb158f0bjohannkoenig@chromium.org src_argb1555 = src_argb1555 + (height - 1) * src_stride_argb1555; 132641294d96d7dbf9bc215b09832a8336c5fb158f0bjohannkoenig@chromium.org src_stride_argb1555 = -src_stride_argb1555; 132741294d96d7dbf9bc215b09832a8336c5fb158f0bjohannkoenig@chromium.org } 132841294d96d7dbf9bc215b09832a8336c5fb158f0bjohannkoenig@chromium.org 132941294d96d7dbf9bc215b09832a8336c5fb158f0bjohannkoenig@chromium.org#if defined(HAS_ARGB1555TOYROW_NEON) 133041294d96d7dbf9bc215b09832a8336c5fb158f0bjohannkoenig@chromium.org if (TestCpuFlag(kCpuHasNEON) && width >= 8) { 133141294d96d7dbf9bc215b09832a8336c5fb158f0bjohannkoenig@chromium.org ARGB1555ToYRow = ARGB1555ToYRow_Any_NEON; 133241294d96d7dbf9bc215b09832a8336c5fb158f0bjohannkoenig@chromium.org if (IS_ALIGNED(width, 8)) { 133341294d96d7dbf9bc215b09832a8336c5fb158f0bjohannkoenig@chromium.org ARGB1555ToYRow = ARGB1555ToYRow_NEON; 133441294d96d7dbf9bc215b09832a8336c5fb158f0bjohannkoenig@chromium.org } 133541294d96d7dbf9bc215b09832a8336c5fb158f0bjohannkoenig@chromium.org if (width >= 16) { 133641294d96d7dbf9bc215b09832a8336c5fb158f0bjohannkoenig@chromium.org ARGB1555ToUVRow = ARGB1555ToUVRow_Any_NEON; 133741294d96d7dbf9bc215b09832a8336c5fb158f0bjohannkoenig@chromium.org if (IS_ALIGNED(width, 16)) { 133841294d96d7dbf9bc215b09832a8336c5fb158f0bjohannkoenig@chromium.org ARGB1555ToUVRow = ARGB1555ToUVRow_NEON; 133941294d96d7dbf9bc215b09832a8336c5fb158f0bjohannkoenig@chromium.org } 134041294d96d7dbf9bc215b09832a8336c5fb158f0bjohannkoenig@chromium.org } 134141294d96d7dbf9bc215b09832a8336c5fb158f0bjohannkoenig@chromium.org } 134241294d96d7dbf9bc215b09832a8336c5fb158f0bjohannkoenig@chromium.org#else // HAS_ARGB1555TOYROW_NEON 134341294d96d7dbf9bc215b09832a8336c5fb158f0bjohannkoenig@chromium.org 134441294d96d7dbf9bc215b09832a8336c5fb158f0bjohannkoenig@chromium.org#if defined(HAS_ARGB1555TOARGBROW_SSE2) 134541294d96d7dbf9bc215b09832a8336c5fb158f0bjohannkoenig@chromium.org if (TestCpuFlag(kCpuHasSSE2) && width >= 8) { 134641294d96d7dbf9bc215b09832a8336c5fb158f0bjohannkoenig@chromium.org ARGB1555ToARGBRow = ARGB1555ToARGBRow_Any_SSE2; 134741294d96d7dbf9bc215b09832a8336c5fb158f0bjohannkoenig@chromium.org if (IS_ALIGNED(width, 8)) { 134841294d96d7dbf9bc215b09832a8336c5fb158f0bjohannkoenig@chromium.org ARGB1555ToARGBRow = ARGB1555ToARGBRow_SSE2; 134941294d96d7dbf9bc215b09832a8336c5fb158f0bjohannkoenig@chromium.org } 135041294d96d7dbf9bc215b09832a8336c5fb158f0bjohannkoenig@chromium.org } 135141294d96d7dbf9bc215b09832a8336c5fb158f0bjohannkoenig@chromium.org#endif 135241294d96d7dbf9bc215b09832a8336c5fb158f0bjohannkoenig@chromium.org#if defined(HAS_ARGBTOUVROW_SSSE3) 135341294d96d7dbf9bc215b09832a8336c5fb158f0bjohannkoenig@chromium.org if (TestCpuFlag(kCpuHasSSSE3) && width >= 16) { 135441294d96d7dbf9bc215b09832a8336c5fb158f0bjohannkoenig@chromium.org ARGBToUVRow = ARGBToUVRow_Any_SSSE3; 135541294d96d7dbf9bc215b09832a8336c5fb158f0bjohannkoenig@chromium.org if (IS_ALIGNED(width, 16)) { 135641294d96d7dbf9bc215b09832a8336c5fb158f0bjohannkoenig@chromium.org ARGBToUVRow = ARGBToUVRow_SSSE3; 135741294d96d7dbf9bc215b09832a8336c5fb158f0bjohannkoenig@chromium.org } 135841294d96d7dbf9bc215b09832a8336c5fb158f0bjohannkoenig@chromium.org } 135941294d96d7dbf9bc215b09832a8336c5fb158f0bjohannkoenig@chromium.org#endif 136041294d96d7dbf9bc215b09832a8336c5fb158f0bjohannkoenig@chromium.org#if defined(HAS_ARGBTOUVROW_SSSE3) 136141294d96d7dbf9bc215b09832a8336c5fb158f0bjohannkoenig@chromium.org if (TestCpuFlag(kCpuHasSSSE3) && width >= 16) { 136241294d96d7dbf9bc215b09832a8336c5fb158f0bjohannkoenig@chromium.org ARGBToYRow = ARGBToYRow_Any_SSSE3; 136341294d96d7dbf9bc215b09832a8336c5fb158f0bjohannkoenig@chromium.org if (IS_ALIGNED(width, 16)) { 136441294d96d7dbf9bc215b09832a8336c5fb158f0bjohannkoenig@chromium.org ARGBToYRow = ARGBToYRow_Unaligned_SSSE3; 136541294d96d7dbf9bc215b09832a8336c5fb158f0bjohannkoenig@chromium.org if (IS_ALIGNED(dst_y, 16) && IS_ALIGNED(dst_stride_y, 16)) { 136641294d96d7dbf9bc215b09832a8336c5fb158f0bjohannkoenig@chromium.org ARGBToYRow = ARGBToYRow_SSSE3; 136741294d96d7dbf9bc215b09832a8336c5fb158f0bjohannkoenig@chromium.org } 136841294d96d7dbf9bc215b09832a8336c5fb158f0bjohannkoenig@chromium.org } 136941294d96d7dbf9bc215b09832a8336c5fb158f0bjohannkoenig@chromium.org } 137041294d96d7dbf9bc215b09832a8336c5fb158f0bjohannkoenig@chromium.org#endif // HAS_ARGBTOUVROW_SSSE3 137141294d96d7dbf9bc215b09832a8336c5fb158f0bjohannkoenig@chromium.org#endif // HAS_ARGB1555TOYROW_NEON 137241294d96d7dbf9bc215b09832a8336c5fb158f0bjohannkoenig@chromium.org 1373d95585fb0ec024f6abd96f7b02e0df58019d46afjohannkoenig@chromium.org { 1374d95585fb0ec024f6abd96f7b02e0df58019d46afjohannkoenig@chromium.org#if !defined(HAS_ARGB1555TOYROW_NEON) 1375d95585fb0ec024f6abd96f7b02e0df58019d46afjohannkoenig@chromium.org // Allocate 2 rows of ARGB. 1376d95585fb0ec024f6abd96f7b02e0df58019d46afjohannkoenig@chromium.org const int kRowSize = (width * 4 + 15) & ~15; 1377d95585fb0ec024f6abd96f7b02e0df58019d46afjohannkoenig@chromium.org align_buffer_64(row, kRowSize * 2); 1378d95585fb0ec024f6abd96f7b02e0df58019d46afjohannkoenig@chromium.org#endif 1379d95585fb0ec024f6abd96f7b02e0df58019d46afjohannkoenig@chromium.org for (y = 0; y < height - 1; y += 2) { 138041294d96d7dbf9bc215b09832a8336c5fb158f0bjohannkoenig@chromium.org#if defined(HAS_ARGB1555TOYROW_NEON) 1381d95585fb0ec024f6abd96f7b02e0df58019d46afjohannkoenig@chromium.org ARGB1555ToUVRow(src_argb1555, src_stride_argb1555, dst_u, dst_v, width); 1382d95585fb0ec024f6abd96f7b02e0df58019d46afjohannkoenig@chromium.org ARGB1555ToYRow(src_argb1555, dst_y, width); 1383d95585fb0ec024f6abd96f7b02e0df58019d46afjohannkoenig@chromium.org ARGB1555ToYRow(src_argb1555 + src_stride_argb1555, dst_y + dst_stride_y, 1384d95585fb0ec024f6abd96f7b02e0df58019d46afjohannkoenig@chromium.org width); 138541294d96d7dbf9bc215b09832a8336c5fb158f0bjohannkoenig@chromium.org#else 1386d95585fb0ec024f6abd96f7b02e0df58019d46afjohannkoenig@chromium.org ARGB1555ToARGBRow(src_argb1555, row, width); 1387d95585fb0ec024f6abd96f7b02e0df58019d46afjohannkoenig@chromium.org ARGB1555ToARGBRow(src_argb1555 + src_stride_argb1555, row + kRowSize, 1388d95585fb0ec024f6abd96f7b02e0df58019d46afjohannkoenig@chromium.org width); 1389d95585fb0ec024f6abd96f7b02e0df58019d46afjohannkoenig@chromium.org ARGBToUVRow(row, kRowSize, dst_u, dst_v, width); 1390d95585fb0ec024f6abd96f7b02e0df58019d46afjohannkoenig@chromium.org ARGBToYRow(row, dst_y, width); 1391d95585fb0ec024f6abd96f7b02e0df58019d46afjohannkoenig@chromium.org ARGBToYRow(row + kRowSize, dst_y + dst_stride_y, width); 139241294d96d7dbf9bc215b09832a8336c5fb158f0bjohannkoenig@chromium.org#endif 1393d95585fb0ec024f6abd96f7b02e0df58019d46afjohannkoenig@chromium.org src_argb1555 += src_stride_argb1555 * 2; 1394d95585fb0ec024f6abd96f7b02e0df58019d46afjohannkoenig@chromium.org dst_y += dst_stride_y * 2; 1395d95585fb0ec024f6abd96f7b02e0df58019d46afjohannkoenig@chromium.org dst_u += dst_stride_u; 1396d95585fb0ec024f6abd96f7b02e0df58019d46afjohannkoenig@chromium.org dst_v += dst_stride_v; 1397d95585fb0ec024f6abd96f7b02e0df58019d46afjohannkoenig@chromium.org } 1398d95585fb0ec024f6abd96f7b02e0df58019d46afjohannkoenig@chromium.org if (height & 1) { 139941294d96d7dbf9bc215b09832a8336c5fb158f0bjohannkoenig@chromium.org#if defined(HAS_ARGB1555TOYROW_NEON) 1400d95585fb0ec024f6abd96f7b02e0df58019d46afjohannkoenig@chromium.org ARGB1555ToUVRow(src_argb1555, 0, dst_u, dst_v, width); 1401d95585fb0ec024f6abd96f7b02e0df58019d46afjohannkoenig@chromium.org ARGB1555ToYRow(src_argb1555, dst_y, width); 140241294d96d7dbf9bc215b09832a8336c5fb158f0bjohannkoenig@chromium.org#else 1403d95585fb0ec024f6abd96f7b02e0df58019d46afjohannkoenig@chromium.org ARGB1555ToARGBRow(src_argb1555, row, width); 1404d95585fb0ec024f6abd96f7b02e0df58019d46afjohannkoenig@chromium.org ARGBToUVRow(row, 0, dst_u, dst_v, width); 1405d95585fb0ec024f6abd96f7b02e0df58019d46afjohannkoenig@chromium.org ARGBToYRow(row, dst_y, width); 140641294d96d7dbf9bc215b09832a8336c5fb158f0bjohannkoenig@chromium.org#endif 1407d95585fb0ec024f6abd96f7b02e0df58019d46afjohannkoenig@chromium.org } 140841294d96d7dbf9bc215b09832a8336c5fb158f0bjohannkoenig@chromium.org#if !defined(HAS_ARGB1555TOYROW_NEON) 140941294d96d7dbf9bc215b09832a8336c5fb158f0bjohannkoenig@chromium.org free_aligned_buffer_64(row); 141041294d96d7dbf9bc215b09832a8336c5fb158f0bjohannkoenig@chromium.org#endif 1411d95585fb0ec024f6abd96f7b02e0df58019d46afjohannkoenig@chromium.org } 141241294d96d7dbf9bc215b09832a8336c5fb158f0bjohannkoenig@chromium.org return 0; 141341294d96d7dbf9bc215b09832a8336c5fb158f0bjohannkoenig@chromium.org} 141441294d96d7dbf9bc215b09832a8336c5fb158f0bjohannkoenig@chromium.org 141541294d96d7dbf9bc215b09832a8336c5fb158f0bjohannkoenig@chromium.org// Convert ARGB4444 to I420. 141641294d96d7dbf9bc215b09832a8336c5fb158f0bjohannkoenig@chromium.orgLIBYUV_API 141741294d96d7dbf9bc215b09832a8336c5fb158f0bjohannkoenig@chromium.orgint ARGB4444ToI420(const uint8* src_argb4444, int src_stride_argb4444, 141841294d96d7dbf9bc215b09832a8336c5fb158f0bjohannkoenig@chromium.org uint8* dst_y, int dst_stride_y, 141941294d96d7dbf9bc215b09832a8336c5fb158f0bjohannkoenig@chromium.org uint8* dst_u, int dst_stride_u, 142041294d96d7dbf9bc215b09832a8336c5fb158f0bjohannkoenig@chromium.org uint8* dst_v, int dst_stride_v, 142141294d96d7dbf9bc215b09832a8336c5fb158f0bjohannkoenig@chromium.org int width, int height) { 142241294d96d7dbf9bc215b09832a8336c5fb158f0bjohannkoenig@chromium.org int y; 142341294d96d7dbf9bc215b09832a8336c5fb158f0bjohannkoenig@chromium.org#if defined(HAS_ARGB4444TOYROW_NEON) 142441294d96d7dbf9bc215b09832a8336c5fb158f0bjohannkoenig@chromium.org void (*ARGB4444ToUVRow)(const uint8* src_argb4444, int src_stride_argb4444, 142541294d96d7dbf9bc215b09832a8336c5fb158f0bjohannkoenig@chromium.org uint8* dst_u, uint8* dst_v, int width) = ARGB4444ToUVRow_C; 142641294d96d7dbf9bc215b09832a8336c5fb158f0bjohannkoenig@chromium.org void (*ARGB4444ToYRow)(const uint8* src_argb4444, uint8* dst_y, int pix) = 142741294d96d7dbf9bc215b09832a8336c5fb158f0bjohannkoenig@chromium.org ARGB4444ToYRow_C; 142841294d96d7dbf9bc215b09832a8336c5fb158f0bjohannkoenig@chromium.org#else 142941294d96d7dbf9bc215b09832a8336c5fb158f0bjohannkoenig@chromium.org void (*ARGB4444ToARGBRow)(const uint8* src_rgb, uint8* dst_argb, int pix) = 143041294d96d7dbf9bc215b09832a8336c5fb158f0bjohannkoenig@chromium.org ARGB4444ToARGBRow_C; 143141294d96d7dbf9bc215b09832a8336c5fb158f0bjohannkoenig@chromium.org void (*ARGBToUVRow)(const uint8* src_argb0, int src_stride_argb, 143241294d96d7dbf9bc215b09832a8336c5fb158f0bjohannkoenig@chromium.org uint8* dst_u, uint8* dst_v, int width) = ARGBToUVRow_C; 143341294d96d7dbf9bc215b09832a8336c5fb158f0bjohannkoenig@chromium.org void (*ARGBToYRow)(const uint8* src_argb, uint8* dst_y, int pix) = 143441294d96d7dbf9bc215b09832a8336c5fb158f0bjohannkoenig@chromium.org ARGBToYRow_C; 143541294d96d7dbf9bc215b09832a8336c5fb158f0bjohannkoenig@chromium.org#endif 143641294d96d7dbf9bc215b09832a8336c5fb158f0bjohannkoenig@chromium.org if (!src_argb4444 || !dst_y || !dst_u || !dst_v || 143741294d96d7dbf9bc215b09832a8336c5fb158f0bjohannkoenig@chromium.org width <= 0 || height == 0) { 143841294d96d7dbf9bc215b09832a8336c5fb158f0bjohannkoenig@chromium.org return -1; 143941294d96d7dbf9bc215b09832a8336c5fb158f0bjohannkoenig@chromium.org } 144041294d96d7dbf9bc215b09832a8336c5fb158f0bjohannkoenig@chromium.org // Negative height means invert the image. 144141294d96d7dbf9bc215b09832a8336c5fb158f0bjohannkoenig@chromium.org if (height < 0) { 144241294d96d7dbf9bc215b09832a8336c5fb158f0bjohannkoenig@chromium.org height = -height; 144341294d96d7dbf9bc215b09832a8336c5fb158f0bjohannkoenig@chromium.org src_argb4444 = src_argb4444 + (height - 1) * src_stride_argb4444; 144441294d96d7dbf9bc215b09832a8336c5fb158f0bjohannkoenig@chromium.org src_stride_argb4444 = -src_stride_argb4444; 144541294d96d7dbf9bc215b09832a8336c5fb158f0bjohannkoenig@chromium.org } 144641294d96d7dbf9bc215b09832a8336c5fb158f0bjohannkoenig@chromium.org 144741294d96d7dbf9bc215b09832a8336c5fb158f0bjohannkoenig@chromium.org#if defined(HAS_ARGB4444TOYROW_NEON) 144841294d96d7dbf9bc215b09832a8336c5fb158f0bjohannkoenig@chromium.org if (TestCpuFlag(kCpuHasNEON) && width >= 8) { 144941294d96d7dbf9bc215b09832a8336c5fb158f0bjohannkoenig@chromium.org ARGB4444ToYRow = ARGB4444ToYRow_Any_NEON; 145041294d96d7dbf9bc215b09832a8336c5fb158f0bjohannkoenig@chromium.org if (IS_ALIGNED(width, 8)) { 145141294d96d7dbf9bc215b09832a8336c5fb158f0bjohannkoenig@chromium.org ARGB4444ToYRow = ARGB4444ToYRow_NEON; 145241294d96d7dbf9bc215b09832a8336c5fb158f0bjohannkoenig@chromium.org } 145341294d96d7dbf9bc215b09832a8336c5fb158f0bjohannkoenig@chromium.org if (width >= 16) { 145441294d96d7dbf9bc215b09832a8336c5fb158f0bjohannkoenig@chromium.org ARGB4444ToUVRow = ARGB4444ToUVRow_Any_NEON; 145541294d96d7dbf9bc215b09832a8336c5fb158f0bjohannkoenig@chromium.org if (IS_ALIGNED(width, 16)) { 145641294d96d7dbf9bc215b09832a8336c5fb158f0bjohannkoenig@chromium.org ARGB4444ToUVRow = ARGB4444ToUVRow_NEON; 145741294d96d7dbf9bc215b09832a8336c5fb158f0bjohannkoenig@chromium.org } 145841294d96d7dbf9bc215b09832a8336c5fb158f0bjohannkoenig@chromium.org } 145941294d96d7dbf9bc215b09832a8336c5fb158f0bjohannkoenig@chromium.org } 146041294d96d7dbf9bc215b09832a8336c5fb158f0bjohannkoenig@chromium.org#else // HAS_ARGB4444TOYROW_NEON 146141294d96d7dbf9bc215b09832a8336c5fb158f0bjohannkoenig@chromium.org 146241294d96d7dbf9bc215b09832a8336c5fb158f0bjohannkoenig@chromium.org#if defined(HAS_ARGB4444TOARGBROW_SSE2) 146341294d96d7dbf9bc215b09832a8336c5fb158f0bjohannkoenig@chromium.org if (TestCpuFlag(kCpuHasSSE2) && width >= 8) { 146441294d96d7dbf9bc215b09832a8336c5fb158f0bjohannkoenig@chromium.org ARGB4444ToARGBRow = ARGB4444ToARGBRow_Any_SSE2; 146541294d96d7dbf9bc215b09832a8336c5fb158f0bjohannkoenig@chromium.org if (IS_ALIGNED(width, 8)) { 146641294d96d7dbf9bc215b09832a8336c5fb158f0bjohannkoenig@chromium.org ARGB4444ToARGBRow = ARGB4444ToARGBRow_SSE2; 146741294d96d7dbf9bc215b09832a8336c5fb158f0bjohannkoenig@chromium.org } 146841294d96d7dbf9bc215b09832a8336c5fb158f0bjohannkoenig@chromium.org } 146941294d96d7dbf9bc215b09832a8336c5fb158f0bjohannkoenig@chromium.org#endif 147041294d96d7dbf9bc215b09832a8336c5fb158f0bjohannkoenig@chromium.org#if defined(HAS_ARGBTOUVROW_SSSE3) 147141294d96d7dbf9bc215b09832a8336c5fb158f0bjohannkoenig@chromium.org if (TestCpuFlag(kCpuHasSSSE3) && width >= 16) { 147241294d96d7dbf9bc215b09832a8336c5fb158f0bjohannkoenig@chromium.org ARGBToUVRow = ARGBToUVRow_Any_SSSE3; 147341294d96d7dbf9bc215b09832a8336c5fb158f0bjohannkoenig@chromium.org if (IS_ALIGNED(width, 16)) { 147441294d96d7dbf9bc215b09832a8336c5fb158f0bjohannkoenig@chromium.org ARGBToUVRow = ARGBToUVRow_SSSE3; 147541294d96d7dbf9bc215b09832a8336c5fb158f0bjohannkoenig@chromium.org } 147641294d96d7dbf9bc215b09832a8336c5fb158f0bjohannkoenig@chromium.org } 147741294d96d7dbf9bc215b09832a8336c5fb158f0bjohannkoenig@chromium.org#endif 147841294d96d7dbf9bc215b09832a8336c5fb158f0bjohannkoenig@chromium.org#if defined(HAS_ARGBTOUVROW_SSSE3) 147941294d96d7dbf9bc215b09832a8336c5fb158f0bjohannkoenig@chromium.org if (TestCpuFlag(kCpuHasSSSE3) && width >= 16) { 148041294d96d7dbf9bc215b09832a8336c5fb158f0bjohannkoenig@chromium.org ARGBToYRow = ARGBToYRow_Any_SSSE3; 148141294d96d7dbf9bc215b09832a8336c5fb158f0bjohannkoenig@chromium.org if (IS_ALIGNED(width, 16)) { 148241294d96d7dbf9bc215b09832a8336c5fb158f0bjohannkoenig@chromium.org ARGBToYRow = ARGBToYRow_Unaligned_SSSE3; 148341294d96d7dbf9bc215b09832a8336c5fb158f0bjohannkoenig@chromium.org if (IS_ALIGNED(dst_y, 16) && IS_ALIGNED(dst_stride_y, 16)) { 148441294d96d7dbf9bc215b09832a8336c5fb158f0bjohannkoenig@chromium.org ARGBToYRow = ARGBToYRow_SSSE3; 148541294d96d7dbf9bc215b09832a8336c5fb158f0bjohannkoenig@chromium.org } 148641294d96d7dbf9bc215b09832a8336c5fb158f0bjohannkoenig@chromium.org } 148741294d96d7dbf9bc215b09832a8336c5fb158f0bjohannkoenig@chromium.org } 148841294d96d7dbf9bc215b09832a8336c5fb158f0bjohannkoenig@chromium.org#endif // HAS_ARGBTOUVROW_SSSE3 148941294d96d7dbf9bc215b09832a8336c5fb158f0bjohannkoenig@chromium.org#endif // HAS_ARGB4444TOYROW_NEON 149041294d96d7dbf9bc215b09832a8336c5fb158f0bjohannkoenig@chromium.org 1491d95585fb0ec024f6abd96f7b02e0df58019d46afjohannkoenig@chromium.org { 1492d95585fb0ec024f6abd96f7b02e0df58019d46afjohannkoenig@chromium.org#if !defined(HAS_ARGB4444TOYROW_NEON) 1493d95585fb0ec024f6abd96f7b02e0df58019d46afjohannkoenig@chromium.org // Allocate 2 rows of ARGB. 1494d95585fb0ec024f6abd96f7b02e0df58019d46afjohannkoenig@chromium.org const int kRowSize = (width * 4 + 15) & ~15; 1495d95585fb0ec024f6abd96f7b02e0df58019d46afjohannkoenig@chromium.org align_buffer_64(row, kRowSize * 2); 1496d95585fb0ec024f6abd96f7b02e0df58019d46afjohannkoenig@chromium.org#endif 1497d95585fb0ec024f6abd96f7b02e0df58019d46afjohannkoenig@chromium.org 1498d95585fb0ec024f6abd96f7b02e0df58019d46afjohannkoenig@chromium.org for (y = 0; y < height - 1; y += 2) { 149941294d96d7dbf9bc215b09832a8336c5fb158f0bjohannkoenig@chromium.org#if defined(HAS_ARGB4444TOYROW_NEON) 1500d95585fb0ec024f6abd96f7b02e0df58019d46afjohannkoenig@chromium.org ARGB4444ToUVRow(src_argb4444, src_stride_argb4444, dst_u, dst_v, width); 1501d95585fb0ec024f6abd96f7b02e0df58019d46afjohannkoenig@chromium.org ARGB4444ToYRow(src_argb4444, dst_y, width); 1502d95585fb0ec024f6abd96f7b02e0df58019d46afjohannkoenig@chromium.org ARGB4444ToYRow(src_argb4444 + src_stride_argb4444, dst_y + dst_stride_y, 1503d95585fb0ec024f6abd96f7b02e0df58019d46afjohannkoenig@chromium.org width); 150441294d96d7dbf9bc215b09832a8336c5fb158f0bjohannkoenig@chromium.org#else 1505d95585fb0ec024f6abd96f7b02e0df58019d46afjohannkoenig@chromium.org ARGB4444ToARGBRow(src_argb4444, row, width); 1506d95585fb0ec024f6abd96f7b02e0df58019d46afjohannkoenig@chromium.org ARGB4444ToARGBRow(src_argb4444 + src_stride_argb4444, row + kRowSize, 1507d95585fb0ec024f6abd96f7b02e0df58019d46afjohannkoenig@chromium.org width); 1508d95585fb0ec024f6abd96f7b02e0df58019d46afjohannkoenig@chromium.org ARGBToUVRow(row, kRowSize, dst_u, dst_v, width); 1509d95585fb0ec024f6abd96f7b02e0df58019d46afjohannkoenig@chromium.org ARGBToYRow(row, dst_y, width); 1510d95585fb0ec024f6abd96f7b02e0df58019d46afjohannkoenig@chromium.org ARGBToYRow(row + kRowSize, dst_y + dst_stride_y, width); 151141294d96d7dbf9bc215b09832a8336c5fb158f0bjohannkoenig@chromium.org#endif 1512d95585fb0ec024f6abd96f7b02e0df58019d46afjohannkoenig@chromium.org src_argb4444 += src_stride_argb4444 * 2; 1513d95585fb0ec024f6abd96f7b02e0df58019d46afjohannkoenig@chromium.org dst_y += dst_stride_y * 2; 1514d95585fb0ec024f6abd96f7b02e0df58019d46afjohannkoenig@chromium.org dst_u += dst_stride_u; 1515d95585fb0ec024f6abd96f7b02e0df58019d46afjohannkoenig@chromium.org dst_v += dst_stride_v; 1516d95585fb0ec024f6abd96f7b02e0df58019d46afjohannkoenig@chromium.org } 1517d95585fb0ec024f6abd96f7b02e0df58019d46afjohannkoenig@chromium.org if (height & 1) { 151841294d96d7dbf9bc215b09832a8336c5fb158f0bjohannkoenig@chromium.org#if defined(HAS_ARGB4444TOYROW_NEON) 1519d95585fb0ec024f6abd96f7b02e0df58019d46afjohannkoenig@chromium.org ARGB4444ToUVRow(src_argb4444, 0, dst_u, dst_v, width); 1520d95585fb0ec024f6abd96f7b02e0df58019d46afjohannkoenig@chromium.org ARGB4444ToYRow(src_argb4444, dst_y, width); 152141294d96d7dbf9bc215b09832a8336c5fb158f0bjohannkoenig@chromium.org#else 1522d95585fb0ec024f6abd96f7b02e0df58019d46afjohannkoenig@chromium.org ARGB4444ToARGBRow(src_argb4444, row, width); 1523d95585fb0ec024f6abd96f7b02e0df58019d46afjohannkoenig@chromium.org ARGBToUVRow(row, 0, dst_u, dst_v, width); 1524d95585fb0ec024f6abd96f7b02e0df58019d46afjohannkoenig@chromium.org ARGBToYRow(row, dst_y, width); 152541294d96d7dbf9bc215b09832a8336c5fb158f0bjohannkoenig@chromium.org#endif 1526d95585fb0ec024f6abd96f7b02e0df58019d46afjohannkoenig@chromium.org } 152741294d96d7dbf9bc215b09832a8336c5fb158f0bjohannkoenig@chromium.org#if !defined(HAS_ARGB4444TOYROW_NEON) 1528d95585fb0ec024f6abd96f7b02e0df58019d46afjohannkoenig@chromium.org free_aligned_buffer_64(row); 152941294d96d7dbf9bc215b09832a8336c5fb158f0bjohannkoenig@chromium.org#endif 1530d95585fb0ec024f6abd96f7b02e0df58019d46afjohannkoenig@chromium.org } 153141294d96d7dbf9bc215b09832a8336c5fb158f0bjohannkoenig@chromium.org return 0; 153241294d96d7dbf9bc215b09832a8336c5fb158f0bjohannkoenig@chromium.org} 153341294d96d7dbf9bc215b09832a8336c5fb158f0bjohannkoenig@chromium.org 153441294d96d7dbf9bc215b09832a8336c5fb158f0bjohannkoenig@chromium.org#ifdef __cplusplus 153541294d96d7dbf9bc215b09832a8336c5fb158f0bjohannkoenig@chromium.org} // extern "C" 153641294d96d7dbf9bc215b09832a8336c5fb158f0bjohannkoenig@chromium.org} // namespace libyuv 153741294d96d7dbf9bc215b09832a8336c5fb158f0bjohannkoenig@chromium.org#endif 1538