xref: /php-src/ext/standard/libavifinfo/avifinfo.h (revision 38460c2c)
1 // Copyright (c) 2021, Alliance for Open Media. All rights reserved
2 //
3 // This source code is subject to the terms of the BSD 2 Clause License and
4 // the Alliance for Open Media Patent License 1.0. If the BSD 2 Clause License
5 // was not distributed with this source code in the LICENSE file, you can
6 // obtain it at www.aomedia.org/license/software. If the Alliance for Open
7 // Media Patent License 1.0 was not distributed with this source code in the
8 // PATENTS file, you can obtain it at www.aomedia.org/license/patent.
9 
10 #ifndef AVIFINFO_H_
11 #define AVIFINFO_H_
12 
13 #include <stddef.h>
14 #include <stdint.h>
15 
16 #ifdef __cplusplus
17 extern "C" {
18 #endif
19 
20 //------------------------------------------------------------------------------
21 
22 typedef enum {
23   kAvifInfoOk,             // The file was correctly parsed and the requested
24                            // information was extracted. It is not guaranteed
25                            // that the input bitstream is a valid complete
26                            // AVIF file.
27   kAvifInfoNotEnoughData,  // The input bitstream was correctly parsed until
28                            // now but bytes are missing. The request should be
29                            // repeated with more input bytes.
30   kAvifInfoTooComplex,     // The input bitstream was correctly parsed until
31                            // now but it is too complex. The parsing was
32                            // stopped to avoid any timeout or crash.
33   kAvifInfoInvalidFile,    // The input bitstream is not a valid AVIF file,
34                            // truncated or not.
35 } AvifInfoStatus;
36 
37 typedef struct {
38   uint32_t width, height;  // In number of pixels. Ignores mirror and rotation.
39   uint32_t bit_depth;      // Likely 8, 10 or 12 bits per channel per pixel.
40   uint32_t num_channels;   // Likely 1, 2, 3 or 4 channels:
41                            //   (1 monochrome or 3 colors) + (0 or 1 alpha)
42 } AvifInfoFeatures;
43 
44 //------------------------------------------------------------------------------
45 // Fixed-size input API
46 // Use this API if a raw byte array of fixed size is available as input.
47 
48 // Parses the 'data' and returns kAvifInfoOk if it is identified as an AVIF.
49 // The file type can be identified in the first 12 bytes of most AVIF files.
50 AvifInfoStatus AvifInfoIdentify(const uint8_t* data, size_t data_size);
51 
52 // Parses the identified AVIF 'data' and extracts its 'features'.
53 // 'data' can be partial but must point to the beginning of the AVIF file.
54 // The 'features' can be parsed in the first 450 bytes of most AVIF files.
55 // 'features' are set to 0 unless kAvifInfoOk is returned.
56 AvifInfoStatus AvifInfoGetFeatures(const uint8_t* data, size_t data_size,
57                                    AvifInfoFeatures* features);
58 
59 //------------------------------------------------------------------------------
60 // Streamed input API
61 // Use this API if the input bytes must be fetched and/or if the AVIF payload
62 // size is unknown. Implement the two function signatures below and pass them to
63 // AvifInfoRead*() with a 'stream', which can be anything (file, struct etc.).
64 
65 // Reads 'num_bytes' from the 'stream'.
66 // The position in the 'stream' must be advanced by 'num_bytes'.
67 // Returns a pointer to the 'num_bytes' or null if it cannot be fulfilled.
68 // The returned data must remain valid until the next read.
69 typedef const uint8_t* (*read_stream_t)(void* stream, size_t num_bytes);
70 // Advances the position in the 'stream' by 'num_bytes'.
71 typedef void (*skip_stream_t)(void* stream, size_t num_bytes);
72 
73 // Maximum number of bytes requested per read. There is no limit per skip.
74 #define AVIFINFO_MAX_NUM_READ_BYTES 64
75 
76 // Same as AvifInfo*() but takes a 'stream' as input. AvifInfo*Stream() does
77 // not access the 'stream' directly but passes it as is to 'read' and 'skip'.
78 // 'read' cannot be null. If 'skip' is null, 'read' is called instead.
79 AvifInfoStatus AvifInfoIdentifyStream(void* stream, read_stream_t read,
80                                       skip_stream_t skip);
81 // Can be called right after AvifInfoIdentifyStream() with the same 'stream'.
82 AvifInfoStatus AvifInfoGetFeaturesStream(void* stream, read_stream_t read,
83                                          skip_stream_t skip,
84                                          AvifInfoFeatures* features);
85 
86 //------------------------------------------------------------------------------
87 
88 #ifdef __cplusplus
89 }  // extern "C"
90 #endif
91 
92 #endif  // AVIFINFO_H_
93