/*
 * Copyright (c) 2011-2016,2018-2019, The Linux Foundation. All rights reserved.

 * Redistribution and use in source and binary forms, with or without
 * modification, are permitted provided that the following conditions are
 * met:
 *   * Redistributions of source code must retain the above copyright
 *     notice, this list of conditions and the following disclaimer.
 *   * Redistributions in binary form must reproduce the above
 *     copyright notice, this list of conditions and the following
 *     disclaimer in the documentation and/or other materials provided
 *     with the distribution.
 *   * Neither the name of The Linux Foundation nor the names of its
 *     contributors may be used to endorse or promote products derived
 *     from this software without specific prior written permission.
 *
 * THIS SOFTWARE IS PROVIDED "AS IS" AND ANY EXPRESS OR IMPLIED
 * WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED WARRANTIES OF
 * MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE AND NON-INFRINGEMENT
 * ARE DISCLAIMED.  IN NO EVENT SHALL THE COPYRIGHT OWNER OR CONTRIBUTORS
 * BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR
 * CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF
 * SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR
 * BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY,
 * WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING NEGLIGENCE
 * OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN
 * IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
 */

#ifndef __GR_UTILS_H__
#define __GR_UTILS_H__

#include <android/hardware/graphics/common/1.1/types.h>
#include "gralloc_priv.h"
#include "qdMetaData.h"

#define SZ_2M 0x200000
#define SZ_1M 0x100000
#define SZ_4K 0x1000

#define SIZE_4K 4096
#define SIZE_8K 8192

#ifdef SLAVE_SIDE_CP
#define SECURE_ALIGN SZ_1M
#else  // MASTER_SIDE_CP
#define SECURE_ALIGN SZ_4K
#endif

#define INT(exp) static_cast<int>(exp)
#define UINT(exp) static_cast<unsigned int>(exp)

using android::hardware::graphics::common::V1_1::BufferUsage;

namespace gralloc {
struct BufferInfo {
  BufferInfo(int w, int h, int f, uint64_t usage = 0)
      : width(w), height(h), format(f), layer_count(1), usage(usage) {}
  int width;
  int height;
  int format;
  int layer_count;
  uint64_t usage;
};

template <class Type1, class Type2>
inline Type1 ALIGN(Type1 x, Type2 align) {
  return (Type1)((x + (Type1)align - 1) & ~((Type1)align - 1));
}

enum PlaneComponent {
  /* luma */
  PLANE_COMPONENT_Y = 1 << 0,
  /* chroma blue */
  PLANE_COMPONENT_Cb = 1 << 1,
  /* chroma red */
  PLANE_COMPONENT_Cr = 1 << 2,

  /* red */
  PLANE_COMPONENT_R = 1 << 10,
  /* green */
  PLANE_COMPONENT_G = 1 << 11,
  /* blue */
  PLANE_COMPONENT_B = 1 << 12,

  /* alpha */
  PLANE_COMPONENT_A = 1 << 20,

  /* raw data plane */
  PLANE_COMPONENT_RAW = 1 << 30,

  /* meta information plane */
  PLANE_COMPONENT_META = 1 << 31,
};

struct PlaneLayoutInfo {
  /** Components represented the type of plane. */
  PlaneComponent component;

  /** horizontal subsampling. Must be a positive power of 2. */
  uint32_t h_subsampling;

  /** vertical subsampling. Must be a positive power of 2. */
  uint32_t v_subsampling;

  /** offset to the first byte of the top-left pixel of the plane
   *  and it is calculated from the start of the buffer.
   *  Add base of the handle with offset to get the first byte of the plane.
   */
  uint32_t offset;

  /** step is the distance in bytes from one pixel value to the next. */
  int32_t step;

  /** stride of the plane in pixels */
  int32_t stride;

  /** stride of the plane in in bytes */
  int32_t stride_bytes;

  /** plane height or vertical stride */
  int32_t scanlines;

  /** size of the plane in bytes */
  uint32_t size;
};

bool IsYuvFormat(int format);
bool IsCompressedRGBFormat(int format);
bool IsUncompressedRGBFormat(int format);
uint32_t GetBppForUncompressedRGB(int format);
bool CpuCanAccess(uint64_t usage);
bool CpuCanRead(uint64_t usage);
bool CpuCanWrite(uint64_t usage);
unsigned int GetSize(const BufferInfo &d, unsigned int alignedw, unsigned int alignedh);
int GetBufferSizeAndDimensions(const BufferInfo &d, unsigned int *size, unsigned int *alignedw,
                               unsigned int *alignedh);
int GetBufferSizeAndDimensions(const BufferInfo &d, unsigned int *size, unsigned int *alignedw,
                               unsigned int *alignedh, GraphicsMetadata *graphics_metadata);
void GetCustomDimensions(private_handle_t *hnd, int *stride, int *height);
void GetColorSpaceFromMetadata(private_handle_t *hnd, int *color_space);
void GetAlignedWidthAndHeight(const BufferInfo &d, unsigned int *aligned_w,
                              unsigned int *aligned_h);
int GetYUVPlaneInfo(const private_handle_t *hnd, struct android_ycbcr ycbcr[2]);
int GetYUVPlaneInfo(const BufferInfo &info, int32_t format, int32_t width, int32_t height,
                    int32_t flags, int *plane_count, PlaneLayoutInfo plane_info[8]);
void GetYuvSubSamplingFactor(int32_t format, int *h_subsampling, int *v_subsampling);
void CopyPlaneLayoutInfotoAndroidYcbcr(uint64_t base, int plane_count, PlaneLayoutInfo *plane_info,
                                       struct android_ycbcr *ycbcr);
int GetRgbDataAddress(private_handle_t *hnd, void **rgb_data);
bool IsUBwcFormat(int format);
bool IsUBwcSupported(int format);
bool IsUBwcPISupported(int format, uint64_t usage);
bool IsUBwcEnabled(int format, uint64_t usage);
void GetYuvUBwcWidthAndHeight(int width, int height, int format, unsigned int *aligned_w,
                              unsigned int *aligned_h);
void GetYuvSPPlaneInfo(const BufferInfo &info, int format, uint32_t width, uint32_t height,
                       uint32_t bpp, PlaneLayoutInfo *plane_info);
void GetYuvUbwcSPPlaneInfo(uint32_t width, uint32_t height, int color_format,
                           PlaneLayoutInfo *plane_info);
void GetYuvUbwcInterlacedSPPlaneInfo(uint32_t width, uint32_t height,
                                     PlaneLayoutInfo plane_info[8]);
void GetRgbUBwcBlockSize(uint32_t bpp, int *block_width, int *block_height);
unsigned int GetRgbUBwcMetaBufferSize(int width, int height, uint32_t bpp);
unsigned int GetUBwcSize(int width, int height, int format, unsigned int alignedw,
                         unsigned int alignedh);
int GetBufferLayout(private_handle_t *hnd, uint32_t stride[4], uint32_t offset[4],
                    uint32_t *num_planes);
uint32_t GetDataAlignment(int format, uint64_t usage);
int GetGpuResourceSizeAndDimensions(const BufferInfo &info, unsigned int *size,
                                    unsigned int *alignedw, unsigned int *alignedh,
                                    GraphicsMetadata *graphics_metadata);
bool CanUseAdrenoForSize(int buffer_type, uint64_t usage);
bool GetAdrenoSizeAPIStatus();
bool UseUncached(int format, uint64_t usage);
uint64_t GetHandleFlags(int format, uint64_t usage);
int GetImplDefinedFormat(uint64_t usage, int format);
int GetCustomFormatFlags(int format, uint64_t usage, int *custom_format, uint64_t *priv_flags);
int GetBufferType(int inputFormat);
bool IsGPUFlagSupported(uint64_t usage);
}  // namespace gralloc

#endif  // __GR_UTILS_H__
