1 // Copyright 2011 Google Inc. All Rights Reserved. 2 // 3 // Use of this source code is governed by a BSD-style license 4 // that can be found in the COPYING file in the root of the source 5 // tree. An additional intellectual property rights grant can be found 6 // in the file PATENTS. All contributing project authors may 7 // be found in the AUTHORS file in the root of the source tree. 8 // ----------------------------------------------------------------------------- 9 // 10 // Internal header for mux library. 11 // 12 // Author: Urvang (urvang (at) google.com) 13 14 #ifndef WEBP_MUX_MUXI_H_ 15 #define WEBP_MUX_MUXI_H_ 16 17 #include <stdlib.h> 18 #include "../dec/vp8i_dec.h" 19 #include "../dec/vp8li_dec.h" 20 #include "../webp/mux.h" 21 22 #ifdef __cplusplus 23 extern "C" { 24 #endif 25 26 //------------------------------------------------------------------------------ 27 // Defines and constants. 28 29 #define MUX_MAJ_VERSION 0 30 #define MUX_MIN_VERSION 4 31 #define MUX_REV_VERSION 0 32 33 // Chunk object. 34 typedef struct WebPChunk WebPChunk; 35 struct WebPChunk { 36 uint32_t tag_; 37 int owner_; // True if *data_ memory is owned internally. 38 // VP8X, ANIM, and other internally created chunks 39 // like ANMF are always owned. 40 WebPData data_; 41 WebPChunk* next_; 42 }; 43 44 // MuxImage object. Store a full WebP image (including ANMF chunk, ALPH 45 // chunk and VP8/VP8L chunk), 46 typedef struct WebPMuxImage WebPMuxImage; 47 struct WebPMuxImage { 48 WebPChunk* header_; // Corresponds to WEBP_CHUNK_ANMF. 49 WebPChunk* alpha_; // Corresponds to WEBP_CHUNK_ALPHA. 50 WebPChunk* img_; // Corresponds to WEBP_CHUNK_IMAGE. 51 WebPChunk* unknown_; // Corresponds to WEBP_CHUNK_UNKNOWN. 52 int width_; 53 int height_; 54 int has_alpha_; // Through ALPH chunk or as part of VP8L. 55 int is_partial_; // True if only some of the chunks are filled. 56 WebPMuxImage* next_; 57 }; 58 59 // Main mux object. Stores data chunks. 60 struct WebPMux { 61 WebPMuxImage* images_; 62 WebPChunk* iccp_; 63 WebPChunk* exif_; 64 WebPChunk* xmp_; 65 WebPChunk* anim_; 66 WebPChunk* vp8x_; 67 68 WebPChunk* unknown_; 69 int canvas_width_; 70 int canvas_height_; 71 }; 72 73 // CHUNK_INDEX enum: used for indexing within 'kChunks' (defined below) only. 74 // Note: the reason for having two enums ('WebPChunkId' and 'CHUNK_INDEX') is to 75 // allow two different chunks to have the same id (e.g. WebPChunkId 76 // 'WEBP_CHUNK_IMAGE' can correspond to CHUNK_INDEX 'IDX_VP8' or 'IDX_VP8L'). 77 typedef enum { 78 IDX_VP8X = 0, 79 IDX_ICCP, 80 IDX_ANIM, 81 IDX_ANMF, 82 IDX_ALPHA, 83 IDX_VP8, 84 IDX_VP8L, 85 IDX_EXIF, 86 IDX_XMP, 87 IDX_UNKNOWN, 88 89 IDX_NIL, 90 IDX_LAST_CHUNK 91 } CHUNK_INDEX; 92 93 #define NIL_TAG 0x00000000u // To signal void chunk. 94 95 typedef struct { 96 uint32_t tag; 97 WebPChunkId id; 98 uint32_t size; 99 } ChunkInfo; 100 101 extern const ChunkInfo kChunks[IDX_LAST_CHUNK]; 102 103 //------------------------------------------------------------------------------ 104 // Chunk object management. 105 106 // Initialize. 107 void ChunkInit(WebPChunk* const chunk); 108 109 // Get chunk index from chunk tag. Returns IDX_UNKNOWN if not found. 110 CHUNK_INDEX ChunkGetIndexFromTag(uint32_t tag); 111 112 // Get chunk id from chunk tag. Returns WEBP_CHUNK_UNKNOWN if not found. 113 WebPChunkId ChunkGetIdFromTag(uint32_t tag); 114 115 // Convert a fourcc string to a tag. 116 uint32_t ChunkGetTagFromFourCC(const char fourcc[4]); 117 118 // Get chunk index from fourcc. Returns IDX_UNKNOWN if given fourcc is unknown. 119 CHUNK_INDEX ChunkGetIndexFromFourCC(const char fourcc[4]); 120 121 // Search for nth chunk with given 'tag' in the chunk list. 122 // nth = 0 means "last of the list". 123 WebPChunk* ChunkSearchList(WebPChunk* first, uint32_t nth, uint32_t tag); 124 125 // Fill the chunk with the given data. 126 WebPMuxError ChunkAssignData(WebPChunk* chunk, const WebPData* const data, 127 int copy_data, uint32_t tag); 128 129 // Sets 'chunk' at nth position in the 'chunk_list'. 130 // nth = 0 has the special meaning "last of the list". 131 // On success ownership is transferred from 'chunk' to the 'chunk_list'. 132 WebPMuxError ChunkSetNth(WebPChunk* chunk, WebPChunk** chunk_list, 133 uint32_t nth); 134 135 // Releases chunk and returns chunk->next_. 136 WebPChunk* ChunkRelease(WebPChunk* const chunk); 137 138 // Deletes given chunk & returns chunk->next_. 139 WebPChunk* ChunkDelete(WebPChunk* const chunk); 140 141 // Deletes all chunks in the given chunk list. 142 void ChunkListDelete(WebPChunk** const chunk_list); 143 144 // Returns size of the chunk including chunk header and padding byte (if any). 145 static WEBP_INLINE size_t SizeWithPadding(size_t chunk_size) { 146 return CHUNK_HEADER_SIZE + ((chunk_size + 1) & ~1U); 147 } 148 149 // Size of a chunk including header and padding. 150 static WEBP_INLINE size_t ChunkDiskSize(const WebPChunk* chunk) { 151 const size_t data_size = chunk->data_.size; 152 assert(data_size < MAX_CHUNK_PAYLOAD); 153 return SizeWithPadding(data_size); 154 } 155 156 // Total size of a list of chunks. 157 size_t ChunkListDiskSize(const WebPChunk* chunk_list); 158 159 // Write out the given list of chunks into 'dst'. 160 uint8_t* ChunkListEmit(const WebPChunk* chunk_list, uint8_t* dst); 161 162 //------------------------------------------------------------------------------ 163 // MuxImage object management. 164 165 // Initialize. 166 void MuxImageInit(WebPMuxImage* const wpi); 167 168 // Releases image 'wpi' and returns wpi->next. 169 WebPMuxImage* MuxImageRelease(WebPMuxImage* const wpi); 170 171 // Delete image 'wpi' and return the next image in the list or NULL. 172 // 'wpi' can be NULL. 173 WebPMuxImage* MuxImageDelete(WebPMuxImage* const wpi); 174 175 // Count number of images matching the given tag id in the 'wpi_list'. 176 // If id == WEBP_CHUNK_NIL, all images will be matched. 177 int MuxImageCount(const WebPMuxImage* wpi_list, WebPChunkId id); 178 179 // Update width/height/has_alpha info from chunks within wpi. 180 // Also remove ALPH chunk if not needed. 181 int MuxImageFinalize(WebPMuxImage* const wpi); 182 183 // Check if given ID corresponds to an image related chunk. 184 static WEBP_INLINE int IsWPI(WebPChunkId id) { 185 switch (id) { 186 case WEBP_CHUNK_ANMF: 187 case WEBP_CHUNK_ALPHA: 188 case WEBP_CHUNK_IMAGE: return 1; 189 default: return 0; 190 } 191 } 192 193 // Pushes 'wpi' at the end of 'wpi_list'. 194 WebPMuxError MuxImagePush(const WebPMuxImage* wpi, WebPMuxImage** wpi_list); 195 196 // Delete nth image in the image list. 197 WebPMuxError MuxImageDeleteNth(WebPMuxImage** wpi_list, uint32_t nth); 198 199 // Get nth image in the image list. 200 WebPMuxError MuxImageGetNth(const WebPMuxImage** wpi_list, uint32_t nth, 201 WebPMuxImage** wpi); 202 203 // Total size of the given image. 204 size_t MuxImageDiskSize(const WebPMuxImage* const wpi); 205 206 // Write out the given image into 'dst'. 207 uint8_t* MuxImageEmit(const WebPMuxImage* const wpi, uint8_t* dst); 208 209 //------------------------------------------------------------------------------ 210 // Helper methods for mux. 211 212 // Checks if the given image list contains at least one image with alpha. 213 int MuxHasAlpha(const WebPMuxImage* images); 214 215 // Write out RIFF header into 'data', given total data size 'size'. 216 uint8_t* MuxEmitRiffHeader(uint8_t* const data, size_t size); 217 218 // Returns the list where chunk with given ID is to be inserted in mux. 219 WebPChunk** MuxGetChunkListFromId(const WebPMux* mux, WebPChunkId id); 220 221 // Validates the given mux object. 222 WebPMuxError MuxValidate(const WebPMux* const mux); 223 224 //------------------------------------------------------------------------------ 225 226 #ifdef __cplusplus 227 } // extern "C" 228 #endif 229 230 #endif /* WEBP_MUX_MUXI_H_ */ 231