godot/thirdparty/libktx/lib/texture.c

/* -*- tab-width: 4; -*- */
/* vi: set sw=2 ts=4 expandtab: */

/*
 * Copyright 2018-2020 Mark Callow.
 * SPDX-License-Identifier: Apache-2.0
 */

/**
 * @internal
 * @file texture.c
 * @~English
 *
 * @brief ktxTexture implementation.
 *
 * @author Mark Callow, www.edgewise-consulting.com
 */

#if defined(_WIN32)
  #define _CRT_SECURE_NO_WARNINGS
  #ifndef __cplusplus
    #undef inline
    #define inline __inline
  #endif // __cplusplus
#endif

#include <assert.h>
#include <math.h>
#include <stdlib.h>
#include <string.h>

#include "ktx.h"
#include "ktxint.h"
#include "formatsize.h"
#include "filestream.h"
#include "memstream.h"
#include "texture1.h"
#include "texture2.h"
#include "unused.h"

ktx_size_t ktxTexture_GetDataSize(ktxTexture* This);

static ktx_uint32_t padRow(ktx_uint32_t* rowBytes);

/**
 * @memberof ktxTexture @private
 * @~English
 * @brief Construct (initialize) a ktxTexture base class instance.
 *
 * @param[in] This pointer to a ktxTexture-sized block of memory to
 *                 initialize.
 * @param[in] createInfo pointer to a ktxTextureCreateInfo struct with
 *                       information describing the texture.
 * @param[in] formatSize pointer to a ktxFormatSize giving size information
 *                       about the texture's elements.
 *
 * @return      KTX_SUCCESS on success, other KTX_* enum values on error.
 *
 * @exception KTX_INVALID_VALUE @c glInternalFormat in @p createInfo is not a
 *                              valid OpenGL internal format value.
 * @exception KTX_INVALID_VALUE @c numDimensions in @p createInfo is not 1, 2
 *                              or 3.
 * @exception KTX_INVALID_VALUE One of <tt>base{Width,Height,Depth}</tt> in
 *                              @p createInfo is 0.
 * @exception KTX_INVALID_VALUE @c numFaces in @p createInfo is not 1 or 6.
 * @exception KTX_INVALID_VALUE @c numLevels in @p createInfo is 0.
 * @exception KTX_INVALID_OPERATION
 *                              The <tt>base{Width,Height,Depth}</tt> specified
 *                              in @p createInfo are inconsistent with
 *                              @c numDimensions.
 * @exception KTX_INVALID_OPERATION
 *                              @p createInfo is requesting a 3D array or
 *                              3D cubemap texture.
 * @exception KTX_INVALID_OPERATION
 *                              @p createInfo is requesting a cubemap with
 *                              non-square or non-2D images.
 * @exception KTX_INVALID_OPERATION
 *                              @p createInfo is requesting more mip levels
 *                              than needed for the specified
 *                              <tt>base{Width,Height,Depth}</tt>.
 * @exception KTX_OUT_OF_MEMORY Not enough memory for the texture.
 */
KTX_error_code
ktxTexture_construct(ktxTexture* This, ktxTextureCreateInfo* createInfo,
                     ktxFormatSize* formatSize)
{}

/**
 * @memberof ktxTexture @private
 * @~English
 * @brief Construct (initialize) the part of a ktxTexture base class that is
 *        not related to the stream contents.
 *
 * @param[in] This pointer to a ktxTexture-sized block of memory to
 *                 initialize.
 *
 * @return      KTX_SUCCESS on success, other KTX_* enum values on error.
 */
KTX_error_code
ktxTexture_constructFromStream(ktxTexture* This, ktxStream* pStream,
                               ktxTextureCreateFlags createFlags)
{}


/**
 * @memberof ktxTexture @private
 * @~English
 * @brief Free the memory associated with the texture contents
 *
 * @param[in] This pointer to the ktxTextureInt whose texture contents are
 *                 to be freed.
 */
void
ktxTexture_destruct(ktxTexture* This)
{}


/**
 * @defgroup reader Reader
 * @brief Read KTX-formatted data.
 * @{
 */

ktxFileType_;
ktxHeaderUnion_;

/**
 * @memberof ktxTexture @private
 * @~English
 * @brief Determine if stream data is KTX1 or KTX2.
 *
 * @param pStream   pointer to the ktxStream to examine.
 * @param pFileType pointer to a ktxFileType enum where the type of the data
 *                  will be written.
 * @param pHeader   pointer to a ktxHeaderUnion where the header info. will be
 *                  written.
 */
static KTX_error_code
ktxDetermineFileType_(ktxStream* pStream, ktxFileType_* pFileType,
                      ktxHeaderUnion_* pHeader)
{}

/**
 * @memberof ktxTexture
 * @~English
 * @brief Create a ktx1 or ktx2 texture according to the stream
 *        data.
 *
 * See @ref ktxTexture1::ktxTexture1_CreateFromStream
 * "ktxTexture1_CreateFromStream" or
 * @ref ktxTexture2::ktxTexture2_CreateFromStream
 * "ktxTexture2_CreateFromStream" for details.
 */
KTX_error_code
ktxTexture_CreateFromStream(ktxStream* pStream,
                            ktxTextureCreateFlags createFlags,
                            ktxTexture** newTex)
{}

/**
 * @memberof ktxTexture
 * @~English
 * @brief Create a ktxTexture1 or ktxTexture2 from a stdio stream according
 *        to the stream data.
 *
 * See @ref ktxTexture1::ktxTexture1_CreateFromStdioStream
 * "ktxTexture1_CreateFromStdioStream" or
 * @ref ktxTexture2::ktxTexture2_CreateFromStdioStream
 * "ktxTexture2_CreateFromStdioStream" for details.
 */
KTX_error_code
ktxTexture_CreateFromStdioStream(FILE* stdioStream,
                                 ktxTextureCreateFlags createFlags,
                                 ktxTexture** newTex)
{}

/**
 * @memberof ktxTexture
 * @~English
 * @brief Create a ktxTexture1 or ktxTexture2 from a named KTX file according
 *        to the file contents.
 *
 * See @ref ktxTexture1::ktxTexture1_CreateFromNamedFile
 * "ktxTexture1_CreateFromNamedFile" or
 * @ref ktxTexture2::ktxTexture2_CreateFromNamedFile
 * "ktxTexture2_CreateFromNamedFile" for details.
 */
KTX_error_code
ktxTexture_CreateFromNamedFile(const char* const filename,
                               ktxTextureCreateFlags createFlags,
                               ktxTexture** newTex)
{}

/**
 * @memberof ktxTexture
 * @~English
 * @brief Create a ktxTexture1 or ktxTexture2 from KTX-formatted data in memory
 *        according to the data contents.
 *
 * See @ref ktxTexture1::ktxTexture1_CreateFromMemory
 * "ktxTexture1_CreateFromMemory" or
 * @ref ktxTexture2::ktxTexture2_CreateFromMemory
 * "ktxTexture2_CreateFromMemory" for details.
 */
KTX_error_code
ktxTexture_CreateFromMemory(const ktx_uint8_t* bytes, ktx_size_t size,
                            ktxTextureCreateFlags createFlags,
                            ktxTexture** newTex)
{}


/**
 * @memberof ktxTexture
 * @~English
 * @brief Return a pointer to the texture image data.
 *
 * @param[in] This pointer to the ktxTexture object of interest.
 */
ktx_uint8_t*
ktxTexture_GetData(ktxTexture* This)
{}

/**
 * @memberof ktxTexture
 * @~English
 * @brief Return the total size of the texture image data in bytes.
 *
 * For a ktxTexture2 with supercompressionScheme != KTX_SS_NONE this will
 * return the deflated size of the data.
 *
 * @param[in] This pointer to the ktxTexture object of interest.
 */
ktx_size_t
ktxTexture_GetDataSize(ktxTexture* This)
{}

/**
 * @memberof ktxTexture
 * @~English
 * @brief Return the size in bytes of an elements of a texture's
 *        images.
 *
 * For uncompressed textures an element is one texel. For compressed
 * textures it is one block.
 *
 * @param[in]     This     pointer to the ktxTexture object of interest.
 */
ktx_uint32_t
ktxTexture_GetElementSize(ktxTexture* This)
{}

/**
 * @memberof ktxTexture @private
 * @~English
 * @brief Calculate & return the size in bytes of an image at the specified
 *        mip level.
 *
 * For arrays, this is the size of layer, for cubemaps, the size of a face
 * and for 3D textures, the size of a depth slice.
 *
 * The size reflects the padding of each row to KTX_GL_UNPACK_ALIGNMENT.
 *
 * @param[in]     This     pointer to the ktxTexture object of interest.
 * @param[in]     level    level of interest.
 * @param[in]     fv       enum specifying format version for which to calculate
 *                         image size.
 */
ktx_size_t
ktxTexture_calcImageSize(ktxTexture* This, ktx_uint32_t level,
                         ktxFormatVersionEnum fv)
{}

/**
 * @memberof ktxTexture
 * @~English
 * @brief Iterate over the levels or faces in a ktxTexture object.
 *
 * Blocks of image data are passed to an application-supplied callback
 * function. This is not a strict per-image iteration. Rather it reflects how
 * OpenGL needs the images. For most textures the block of data includes all
 * images of a mip level which implies all layers of an array. However, for
 * non-array cube map textures the block is a single face of the mip level,
 * i.e the callback is called once for each face.
 *
 * This function works even if @p This->pData == 0 so it can be used to
 * obtain offsets and sizes for each level by callers who have loaded the data
 * externally.
 *
 * @param[in]     This      pointer to the ktxTexture object of interest.
 * @param[in,out] iterCb    the address of a callback function which is called
 *                          with the data for each image block.
 * @param[in,out] userdata  the address of application-specific data which is
 *                          passed to the callback along with the image data.
 *
 * @return  KTX_SUCCESS on success, other KTX_* enum values on error. The
 *          following are returned directly by this function. @p iterCb may
 *          return these for other causes or may return additional errors.
 *
 * @exception KTX_FILE_DATA_ERROR   Mip level sizes are increasing not
 *                                  decreasing
 * @exception KTX_INVALID_VALUE     @p This is @c NULL or @p iterCb is @c NULL.
 *
 */
KTX_error_code
ktxTexture_IterateLevelFaces(ktxTexture* This, PFNKTXITERCB iterCb,
                             void* userdata)
{}

/**
 * @internal
 * @brief  Calculate and apply the padding needed to comply with
 *         KTX_GL_UNPACK_ALIGNMENT.
 *
 * For uncompressed textures, KTX format specifies KTX_GL_UNPACK_ALIGNMENT = 4.
 *
 * @param[in,out] rowBytes    pointer to variable containing the packed no. of
 *                            bytes in a row. The no. of bytes after padding
 *                            is written into this location.
 * @return the no. of bytes of padding.
 */
static ktx_uint32_t
padRow(ktx_uint32_t* rowBytes)
{}

/**
 * @memberof ktxTexture @private
 * @~English
 * @brief Calculate the size of an array layer at the specified mip level.
 *
 * The size of a layer is the size of an image * either the number of faces
 * or the number of depth slices. This is the size of a layer as needed to
 * find the offset within the array of images of a level and layer so the size
 * reflects any @c cubePadding.
 *
 * @param[in]  This     pointer to the ktxTexture object of interest.
 * @param[in] level     level whose layer size to return.
 *
 * @return the layer size in bytes.
 */
ktx_size_t
ktxTexture_layerSize(ktxTexture* This, ktx_uint32_t level,
                    ktxFormatVersionEnum fv)
{}

/**
 * @memberof ktxTexture @private
 * @~English
 * @brief Calculate the size of the specified mip level.
 *
 * The size of a level is the size of a layer * the number of layers.
 *
 * @param[in]  This     pointer to the ktxTexture object of interest.
 * @param[in] level     level whose layer size to return.
 *
 * @return the level size in bytes.
 */
ktx_size_t
ktxTexture_calcLevelSize(ktxTexture* This, ktx_uint32_t level,
                         ktxFormatVersionEnum fv)
{}

/**
 * @memberof ktxTexture @private
 * @~English
 * @brief Calculate the faceLodSize of the specified mip level.
 *
 * The faceLodSize of a level for most textures is the size of a level. For
 * non-array cube map textures is the size of a face. This is the size that
 * must be provided to OpenGL when uploading textures. Faces get uploaded 1
 * at a time while all layers of an array or all slices of a 3D texture are
 * uploaded together.
 *
 * @param[in]  This     pointer to the ktxTexture object of interest.
 * @param[in] level     level whose layer size to return.
 *
 * @return the faceLodSize size in bytes.
 */
ktx_size_t
ktxTexture_doCalcFaceLodSize(ktxTexture* This, ktx_uint32_t level,
                             ktxFormatVersionEnum fv)
{}


/**
 * @memberof ktxTexture @private
 * @~English
 * @brief Return the number of bytes needed to store all the image data for
 *        a ktxTexture.
 *
 * The caclulated size does not include space for storing the @c imageSize
 * fields of each mip level.
 *
 * @param[in]     This  pointer to the ktxTexture object of interest.
 * @param[in]     fv    enum specifying format version for which to calculate
 *                      image size.
 *
 * @return the data size in bytes.
 */
ktx_size_t
ktxTexture_calcDataSizeTexture(ktxTexture* This)
{}

/**
 * @memberof ktxTexture @private
 * @~English
 * @brief Get information about rows of an uncompresssed texture image at a
 *        specified level.
 *
 * For an image at @p level of a ktxTexture provide the number of rows, the
 * packed (unpadded) number of bytes in a row and the padding necessary to
 * comply with KTX_GL_UNPACK_ALIGNMENT.
 *
 * @param[in]     This     pointer to the ktxTexture object of interest.
 * @param[in]     level    level of interest.
 * @param[in,out] numRows  pointer to location to store the number of rows.
 * @param[in,out] pRowLengthBytes pointer to location to store number of bytes
 *                                in a row.
 * @param[in.out] pRowPadding pointer to location to store the number of bytes
 *                            of padding.
 */
void
ktxTexture_rowInfo(ktxTexture* This, ktx_uint32_t level,
                   ktx_uint32_t* numRows, ktx_uint32_t* pRowLengthBytes,
                   ktx_uint32_t* pRowPadding)
{}

/**
 * @memberof ktxTexture
 * @~English
 * @brief Return pitch betweeb rows of a texture image level in bytes.
 *
 * For uncompressed textures the pitch is the number of bytes between
 * rows of texels. For compressed textures it is the number of bytes
 * between rows of blocks. The value is padded to GL_UNPACK_ALIGNMENT,
 * if necessary. For all currently known compressed formats padding
 * will not be necessary.
 *
 * @param[in]     This     pointer to the ktxTexture object of interest.
 * @param[in]     level    level of interest.
 *
 * @return  the row pitch in bytes.
 */
 ktx_uint32_t
 ktxTexture_GetRowPitch(ktxTexture* This, ktx_uint32_t level)
 {}

/**
 * @memberof ktxTexture @private
 * @~English
 * @brief Query if a ktxTexture has an active stream.
 *
 * Tests if a ktxTexture has unread image data. The internal stream is closed
 * once all the images have been read.
 *
 * @param[in]     This     pointer to the ktxTexture object of interest.
 *
 * @return KTX_TRUE if there is an active stream, KTX_FALSE otherwise.
 */
ktx_bool_t
ktxTexture_isActiveStream(ktxTexture* This)
{}

/** @} */