update with new semantics for padding
[flac.git] / include / FLAC / metadata.h
1 /* libFLAC - Free Lossless Audio Codec library
2  * Copyright (C) 2001,2002  Josh Coalson
3  *
4  * This library is free software; you can redistribute it and/or
5  * modify it under the terms of the GNU Library General Public
6  * License as published by the Free Software Foundation; either
7  * version 2 of the License, or (at your option) any later version.
8  *
9  * This library is distributed in the hope that it will be useful,
10  * but WITHOUT ANY WARRANTY; without even the implied warranty of
11  * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the GNU
12  * Library General Public License for more details.
13  *
14  * You should have received a copy of the GNU Library General Public
15  * License along with this library; if not, write to the
16  * Free Software Foundation, Inc., 59 Temple Place - Suite 330,
17  * Boston, MA  02111-1307, USA.
18  */
19
20 #ifndef FLAC__METADATA_H
21 #define FLAC__METADATA_H
22
23 #include "format.h"
24
25 /******************************************************************************
26         (For an example of how all these routines are used, see the source
27         code for the unit tests in src/test_unit/metadata_*.c, or metaflac
28         in src/metaflac/)
29 ******************************************************************************/
30
31 /******************************************************************************
32         This module provides read and write access to FLAC file metadata at
33         three increasing levels of complexity:
34
35         level 0:
36         read-only access to the STREAMINFO block.
37
38         level 1:
39         read-write access to all metadata blocks.  This level is write-
40         efficient in most cases (more on this later), and uses less memory
41         than level 2.
42
43         level 2:
44         read-write access to all metadata blocks.  This level is write-
45         efficient in all cases, but uses more memory since all metadata for
46         the whole file is read into memory and manipulated before writing
47         out again.
48
49         What do we mean by efficient?  When writing metadata back to a FLAC
50         file it is possible to grow or shrink the metadata such that the entire
51         file must be rewritten.  However, if the size remains the same during
52         changes or PADDING blocks are utilized, only the metadata needs to be
53         overwritten, which is much faster.
54
55         Efficient means the whole file is rewritten at most one time, and only
56         when necessary.  Level 1 is not efficient only in the case that you
57         cause more than one metadata block to grow or shrink beyond what can
58         be accomodated by padding.  In this case you should probably use level
59         2, which allows you to edit all the metadata for a file in memory and
60         write it out all at once.
61
62         WATCHOUT: levels 1 and 2 do not support id3v2 tags at the front of the
63         file.  You will get an error that it is not a valid FLAC file.
64 ******************************************************************************/
65
66 /******************************************************************************
67         After the three interfaces, methods for creating and manipulating
68         the various metadata blocks are defined.  Unless you will be using
69         level 1 or 2 to modify existing metadata you will not need these.
70 ******************************************************************************/
71
72 #ifdef __cplusplus
73 extern "C" {
74 #endif
75
76
77 /***********************************************************************
78  * level 0
79  * ---------------------------------------------------------------------
80  * Only one routine to read the STREAMINFO.  Skips any id3v2 tag at the
81  * head of the file.  Useful for file-based player plugins.
82  *
83  * Provide the address of a FLAC__StreamMetaData_StreamInfo object to
84  * fill.
85  */
86
87 FLAC__bool FLAC__metadata_get_streaminfo(const char *filename, FLAC__StreamMetaData_StreamInfo *streaminfo);
88
89
90 /***********************************************************************
91  * level 1
92  * ---------------------------------------------------------------------
93  * The general usage of this interface is:
94  *
95  * Create an iterator using FLAC__metadata_simple_iterator_new()
96  * Attach it to a file using FLAC__metadata_simple_iterator_init() and check
97  *    the exit code.  Call FLAC__metadata_simple_iterator_is_writable() to
98  *    see if the file is writable, or read-only access is allowed.
99  * Use _next() and _prev() to move around the blocks.  This is does not
100  *    read the actual blocks themselves.  _next() is relatively fast.
101  *    _prev() is slower since it needs to search forward from the front
102  *    of the file.
103  * Use _get_block_type() or _get_block() to access the actual data at
104  *    the current iterator position.  The returned object is yours to
105  *    modify and free.
106  * Use _set_block() to write a modified block back.  You must have write
107  *    permission to the original file.  Make sure to read the whole
108  *    comment to _set_block() below.
109  * Use _insert_block_after() to add new blocks.  Use the object creation
110  *    functions from the end of this header file to generate new objects.
111  * Use _delete_block() to remove the block currently referred to by the
112  *    iterator, or replace it with padding.
113  * Destroy the iterator with FLAC__metadata_simple_iterator_delete()
114  *    when finished.
115  *
116  * NOTE: The FLAC file remains open the whole time between _init() and
117  *       _delete(), so make sure you are not altering the file during
118  *       this time.
119  *
120  * NOTE: Do not modify the is_last, length, or type fields of returned
121  *       FLAC__MetaDataType objects.  These are managed automatically.
122  *
123  * NOTE: If any of the modification functions (_set_block, _delete_block,
124  *       _insert_block_after, etc) return false, you should delete the
125  *       iterator as it may no longer be valid.
126  */
127
128 /*
129  * opaque structure definition
130  */
131 struct FLAC__MetaData_SimpleIterator;
132 typedef struct FLAC__MetaData_SimpleIterator FLAC__MetaData_SimpleIterator;
133
134 typedef enum {
135         FLAC__METADATA_SIMPLE_ITERATOR_STATUS_OK = 0,
136         FLAC__METADATA_SIMPLE_ITERATOR_STATUS_ILLEGAL_INPUT,
137         FLAC__METADATA_SIMPLE_ITERATOR_STATUS_ERROR_OPENING_FILE,
138         FLAC__METADATA_SIMPLE_ITERATOR_STATUS_NOT_A_FLAC_FILE,
139         FLAC__METADATA_SIMPLE_ITERATOR_STATUS_NOT_WRITABLE,
140         FLAC__METADATA_SIMPLE_ITERATOR_STATUS_READ_ERROR,
141         FLAC__METADATA_SIMPLE_ITERATOR_STATUS_SEEK_ERROR,
142         FLAC__METADATA_SIMPLE_ITERATOR_STATUS_WRITE_ERROR,
143         FLAC__METADATA_SIMPLE_ITERATOR_STATUS_RENAME_ERROR,
144         FLAC__METADATA_SIMPLE_ITERATOR_STATUS_UNLINK_ERROR,
145         FLAC__METADATA_SIMPLE_ITERATOR_STATUS_MEMORY_ALLOCATION_ERROR,
146         FLAC__METADATA_SIMPLE_ITERATOR_STATUS_INTERNAL_ERROR
147 } FLAC__MetaData_SimpleIteratorStatus;
148 extern const char *FLAC__MetaData_SimpleIteratorStatusString[];
149
150 /*
151  * Constructor/destructor
152  */
153 FLAC__MetaData_SimpleIterator *FLAC__metadata_simple_iterator_new();
154 void FLAC__metadata_simple_iterator_delete(FLAC__MetaData_SimpleIterator *iterator);
155
156 /*
157  * Get the current status of the iterator.  Call this after a function
158  * returns false to get the reason for the error.  Also resets the status
159  * to FLAC__METADATA_SIMPLE_ITERATOR_STATUS_OK
160  */
161 FLAC__MetaData_SimpleIteratorStatus FLAC__metadata_simple_iterator_status(FLAC__MetaData_SimpleIterator *iterator);
162
163 /*
164  * Initialize the iterator to point to the first metadata block in the
165  * given FLAC file.  If 'preserve_file_stats' is true, the owner and
166  * modification time will be preserved even if the FLAC file is written.
167  */
168 FLAC__bool FLAC__metadata_simple_iterator_init(FLAC__MetaData_SimpleIterator *iterator, const char *filename, FLAC__bool preserve_file_stats);
169
170 /*
171  * Returns true if the FLAC file is writable.  If false, calls to
172  * FLAC__metadata_simple_iterator_set_block() and
173  * FLAC__metadata_simple_iterator_insert_block_after() will fail.
174  */
175 FLAC__bool FLAC__metadata_simple_iterator_is_writable(const FLAC__MetaData_SimpleIterator *iterator);
176
177 /*
178  * These move the iterator forwards or backwards, returning false if
179  * already at the end.
180  */
181 FLAC__bool FLAC__metadata_simple_iterator_next(FLAC__MetaData_SimpleIterator *iterator);
182 FLAC__bool FLAC__metadata_simple_iterator_prev(FLAC__MetaData_SimpleIterator *iterator);
183
184 /*
185  * Get the type of the metadata block at the current position.  This
186  * avoids reading the actual block data which can save time for large
187  * blocks.
188  */
189 FLAC__MetaDataType FLAC__metadata_simple_iterator_get_block_type(const FLAC__MetaData_SimpleIterator *iterator);
190
191 /*
192  * Get the metadata block at the current position.  You can modify the
193  * block but must use FLAC__metadata_simple_iterator_set_block() to
194  * write it back to the FLAC file.
195  *
196  * You must call FLAC__metadata_object_delete() on the returned object
197  * when you are finished with it.
198  */
199 FLAC__StreamMetaData *FLAC__metadata_simple_iterator_get_block(FLAC__MetaData_SimpleIterator *iterator);
200
201 /*
202  * Write a block back to the FLAC file.  This function tries to be
203  * as efficient as possible; how the block is actually written is
204  * shown by the following:
205  *
206  * Existing block is a STREAMINFO block and the new block is a
207  * STREAMINFO block: the new block is written in place.  Make sure
208  * you know what you're doing when changing the values of a
209  * STREAMINFO block.
210  *
211  * Existing block is a STREAMINFO block and the new block is a
212  * not a STREAMINFO block: this is an error since the first block
213  * must be a STREAMINFO block.  Returns false without altering the
214  * file.
215  *
216  * Existing block is not a STREAMINFO block and the new block is a
217  * STREAMINFO block: this is an error since there may be only one
218  * STREAMINFO block.  Returns false without altering the file.
219  *
220  * Existing block and new block are the same length: the existing
221  * block will be replaced by the new block, written in place.
222  *
223  * Existing block is longer than new block: if use_padding is true,
224  * the existing block will be overwritten in place with the new
225  * block followed by a PADDING block, if possible, to make the total
226  * size the same as the existing block.  Remember that a padding
227  * block requires at least four bytes so if the difference in size
228  * between the new block and existing block is less than that, the
229  * entire file will have to be rewritten, using the new block's
230  * exact size.  If use_padding is false, the entire file will be
231  * rewritten, replacing the existing block by the new block.
232  *
233  * Existing block is shorter than new block: if use_padding is true,
234  * the function will try and expand the new block into the following
235  * PADDING block, if it exists and doing so won't shrink the PADDING
236  * block to less than 4 bytes.  If there is no following PADDING
237  * block, or it will shrink to less than 4 bytes, or use_padding is
238  * false, the entire file is rewritten, replacing the existing block
239  * with the new block.  Note that in this case any following PADDING
240  * block is preserved as is.
241  *
242  * After writing the block, the iterator will remain in the same
243  * place, i.e. pointing to the new block.
244  */
245 FLAC__bool FLAC__metadata_simple_iterator_set_block(FLAC__MetaData_SimpleIterator *iterator, FLAC__StreamMetaData *block, FLAC__bool use_padding);
246
247 /*
248  * This is similar to FLAC__metadata_simple_iterator_set_block()
249  * except that instead of writing over an existing block, it appends
250  * a block after the existing block.  'use_padding' is again used to
251  * tell the function to try an expand into following padding in an
252  * attempt to avoid rewriting the entire file.
253  *
254  * This function will fail and return false if given a STREAMINFO
255  * block.
256  *
257  * After writing the block, the iterator will be pointing to the
258  * new block.
259  */
260 FLAC__bool FLAC__metadata_simple_iterator_insert_block_after(FLAC__MetaData_SimpleIterator *iterator, FLAC__StreamMetaData *block, FLAC__bool use_padding);
261
262 /*
263  * Deletes the block at the current position.  This will cause the
264  * entire FLAC file to be rewritten, unless 'use_padding' is true,
265  * in which case the block will be replaced by an equal-sized PADDING
266  * block.  The iterator will be left pointing to the block before the
267  * one just deleted.
268  *
269  * You may not delete the STREAMINFO block.
270  */
271 FLAC__bool FLAC__metadata_simple_iterator_delete_block(FLAC__MetaData_SimpleIterator *iterator, FLAC__bool use_padding);
272
273
274 /***********************************************************************
275  * level 2
276  * ---------------------------------------------------------------------
277  * The general usage of this interface is:
278  *
279  * Create a new chain using FLAC__metadata_chain_new().  A chain is a
280  *    linked list of metadata blocks.
281  * Read all metadata into the the chain from a FLAC file using
282  *    FLAC__metadata_chain_read() and check the status.
283  * Optionally, consolidate the padding using
284  *    FLAC__metadata_chain_merge_padding() or
285  *    FLAC__metadata_chain_sort_padding().
286  * Create a new iterator using FLAC__metadata_iterator_new()
287  * Initialize the iterator to point to the first element in the chain
288  *    using FLAC__metadata_iterator_init()
289  * Traverse the chain using FLAC__metadata_iterator_next/prev().
290  * Get a block for reading or modification using
291  *    FLAC__metadata_iterator_get_block().  The pointer to the object
292  *    inside the chain is returned, so the block is yours to modify.
293  *    Changes will be reflected in the FLAC file when you write the
294  *    chain.  You can also add and delete blocks (see functions below).
295  * When done, write out the chain using FLAC__metadata_chain_write().
296  *    Make sure to read the whole comment to the function below.
297  * Delete the chain using FLAC__metadata_chain_delete().
298  *
299  * NOTE: Even though the FLAC file is not open while the chain is being
300  *       manipulated, you must not alter the file externally during
301  *       this time.  The chain assumes the FLAC file will not change
302  *       between the time of FLAC__metadata_chain_read() and
303  *       FLAC__metadata_chain_write().
304  *
305  * NOTE: Do not modify the is_last, length, or type fields of returned
306  *       FLAC__MetaDataType objects.  These are managed automatically.
307  *
308  * NOTE: The metadata objects returned by _get_bloca()k are owned by the
309  *       chain; do not FLAC__metadata_object_delete() them.  In the
310  *       same way, blocks passed to _set_block() become owned by the
311  *       chain and will be deleted when the chain is deleted.
312  */
313
314 /*
315  * opaque structure definitions
316  */
317 struct FLAC__MetaData_Chain;
318 typedef struct FLAC__MetaData_Chain FLAC__MetaData_Chain;
319 struct FLAC__MetaData_Iterator;
320 typedef struct FLAC__MetaData_Iterator FLAC__MetaData_Iterator;
321
322 typedef enum {
323         FLAC__METADATA_CHAIN_STATUS_OK = 0,
324         FLAC__METADATA_CHAIN_STATUS_ILLEGAL_INPUT,
325         FLAC__METADATA_CHAIN_STATUS_ERROR_OPENING_FILE,
326         FLAC__METADATA_CHAIN_STATUS_NOT_A_FLAC_FILE,
327         FLAC__METADATA_CHAIN_STATUS_NOT_WRITABLE,
328         FLAC__METADATA_CHAIN_STATUS_READ_ERROR,
329         FLAC__METADATA_CHAIN_STATUS_SEEK_ERROR,
330         FLAC__METADATA_CHAIN_STATUS_WRITE_ERROR,
331         FLAC__METADATA_CHAIN_STATUS_RENAME_ERROR,
332         FLAC__METADATA_CHAIN_STATUS_UNLINK_ERROR,
333         FLAC__METADATA_CHAIN_STATUS_MEMORY_ALLOCATION_ERROR,
334         FLAC__METADATA_CHAIN_STATUS_INTERNAL_ERROR
335 } FLAC__MetaData_ChainStatus;
336 extern const char *FLAC__MetaData_ChainStatusString[];
337
338 /*********** FLAC__MetaData_Chain ***********/
339
340 /*
341  * Constructor/destructor
342  */
343 FLAC__MetaData_Chain *FLAC__metadata_chain_new();
344 void FLAC__metadata_chain_delete(FLAC__MetaData_Chain *chain);
345
346 /*
347  * Get the current status of the chain.  Call this after a function
348  * returns false to get the reason for the error.  Also resets the status
349  * to FLAC__METADATA_CHAIN_STATUS_OK
350  */
351 FLAC__MetaData_ChainStatus FLAC__metadata_chain_status(FLAC__MetaData_Chain *chain);
352
353 /*
354  * Read all metadata into the chain
355  */
356 FLAC__bool FLAC__metadata_chain_read(FLAC__MetaData_Chain *chain, const char *filename);
357
358 /*
359  * Write all metadata out to the FLAC file.  This function tries to be as
360  * efficient as possible; how the metadata is actually written is shown by
361  * the following:
362  *
363  * If the current chain is the same size as the existing metadata, the new
364  * data is written in place.
365  *
366  * If the current chain is longer than the existing metadata, and
367  * 'use_padding' is true, and the last block is a PADDING block of
368  * sufficient length, the function will truncate the final padding block
369  * so that the overall size of the metadata is the same as the existing
370  * metadata, and then just rewrite the metadata.  Otherwise, if not all of
371  * the above conditions are met, the entire FLAC file must be rewritten.
372  * If you want to use padding this way it is a good idea to call
373  * FLAC__metadata_chain_sort_padding() first so that you have the maximum
374  * amount of padding to work with, unless you need to preserve ordering
375  * of the PADDING blocks for some reason.
376  *
377  * If the current chain is shorter than the existing metadata, and
378  * use_padding is true, and the final block is a PADDING block, the padding
379  * is extended to make the overall size the same as the existing data.  If
380  * use_padding is true and the last block is not a PADDING block, a new
381  * PADDING block is added to the end of the new data to make it the same
382  * size as the existing data (if possible, see the note to
383  * FLAC__metadata_simple_iterator_set_block() about the four byte limit)
384  * and the new data is written in place.  If none of the above apply or
385  * use_padding is false, the entire FLAC file is rewritten.
386  *
387  * If 'preserve_file_stats' is true, the owner and modification time will
388  * be preserved even if the FLAC file is written.
389  */
390 FLAC__bool FLAC__metadata_chain_write(FLAC__MetaData_Chain *chain, FLAC__bool use_padding, FLAC__bool preserve_file_stats);
391
392 /*
393  * This function will merge adjacent PADDING blocks into a single block.
394  *
395  * NOTE: this function does not write to the FLAC file, it only
396  * modifies the chain.
397  *
398  * NOTE: Any iterator on the current chain will become invalid after this
399  * call.  You should delete the iterator and get a new one.
400  */
401 void FLAC__metadata_chain_merge_padding(FLAC__MetaData_Chain *chain);
402
403 /*
404  * This function will move all PADDING blocks to the end on the metadata,
405  * then merge them into a single block.
406  *
407  * NOTE: this function does not write to the FLAC file, it only
408  * modifies the chain.
409  *
410  * NOTE: Any iterator on the current chain will become invalid after this
411  * call.  You should delete the iterator and get a new one.
412  */
413 void FLAC__metadata_chain_sort_padding(FLAC__MetaData_Chain *chain);
414
415
416 /*********** FLAC__MetaData_Iterator ***********/
417
418 /*
419  * Constructor/destructor
420  */
421 FLAC__MetaData_Iterator *FLAC__metadata_iterator_new();
422 void FLAC__metadata_iterator_delete(FLAC__MetaData_Iterator *iterator);
423
424 /*
425  * Initialize the iterator to point to the first metadata block in the
426  * given chain.
427  */
428 void FLAC__metadata_iterator_init(FLAC__MetaData_Iterator *iterator, FLAC__MetaData_Chain *chain);
429
430 /*
431  * These move the iterator forwards or backwards, returning false if
432  * already at the end.
433  */
434 FLAC__bool FLAC__metadata_iterator_next(FLAC__MetaData_Iterator *iterator);
435 FLAC__bool FLAC__metadata_iterator_prev(FLAC__MetaData_Iterator *iterator);
436
437 /*
438  * Get the type of the metadata block at the current position.
439  */
440 FLAC__MetaDataType FLAC__metadata_iterator_get_block_type(const FLAC__MetaData_Iterator *iterator);
441
442 /*
443  * Get the metadata block at the current position.  You can modify
444  * the block in place but must write the chain before the changes
445  * are reflected to the FLAC file.
446  *
447  * Do not call FLAC__metadata_object_delete() on the returned object;
448  * to delete a block use FLAC__metadata_iterator_delete_block().
449  */
450 FLAC__StreamMetaData *FLAC__metadata_iterator_get_block(FLAC__MetaData_Iterator *iterator);
451
452 /*
453  * Set the metadata block at the current position, replacing the existing
454  * block.  The new block passed in becomes owned by the chain and will be
455  * deleted when the chain is deleted.
456  */
457 FLAC__bool FLAC__metadata_iterator_set_block(FLAC__MetaData_Iterator *iterator, FLAC__StreamMetaData *block);
458
459 /*
460  * Removes the current block from the chain.  If replace_with_padding is
461  * true, the block will instead be replaced with a padding block of equal
462  * size.  You can not delete the STREAMINFO block.  The iterator will be
463  * left pointing to the block before the one just 'deleted', even if
464  * 'replace_with_padding' is true.
465  */
466 FLAC__bool FLAC__metadata_iterator_delete_block(FLAC__MetaData_Iterator *iterator, FLAC__bool replace_with_padding);
467
468 /*
469  * Insert a new block before or after the current block.  You cannot
470  * insert a block before the first STREAMINFO block.  You cannot
471  * insert a STREAMINFO block as there can be only one, the one that
472  * already exists at the head when you read in a chain.  The iterator
473  * will be left pointing to the new block.
474  */
475 FLAC__bool FLAC__metadata_iterator_insert_block_before(FLAC__MetaData_Iterator *iterator, FLAC__StreamMetaData *block);
476 FLAC__bool FLAC__metadata_iterator_insert_block_after(FLAC__MetaData_Iterator *iterator, FLAC__StreamMetaData *block);
477
478
479 /******************************************************************************
480         The following are methods for manipulating the defined block types.
481         Since many are variable length we have to be careful about the memory
482         management.  We decree that all pointers to data in the object are
483         owned by the object and memory-managed by the object.
484
485         Use the _new and _delete functions to create all instances.  When
486         using the _set_ functions to set pointers to data, set 'copy' to true
487         to have the function make it's own copy of the data, or to false to
488         give the object ownership of your data.  In the latter case your pointer
489         must be freeable by free() and will be free()d when the object is
490         FLAC__metadata_object_delete()d.  It is legal to pass a null pointer
491         as the data pointer to a _set_ function as long as then length argument
492         is 0 and the copy argument is 'false'.
493
494         The _new and _copy function will return NULL in the case of a memory
495         allocation error, otherwise a new object.  The _set_ functions return
496         false in the case of a memory allocation error.
497
498         We don't have the convenience of C++ here, so note that the library
499         relies on you to keep the types straight.  In other words, if you pass,
500         for example, a FLAC__StreamMetaData* that represents a STREAMINFO block
501         to FLAC__metadata_object_application_set_data(), you will get an
502         assertion failure.
503
504         There is no need to recalculate the length field on metadata blocks
505         you have modified.  They will be calculated automatically before they
506         are written back to a file.
507 ******************************************************************************/
508
509
510 /******************************************************************
511  * Common to all the types derived from FLAC__StreamMetaData:
512  */
513 FLAC__StreamMetaData *FLAC__metadata_object_new(FLAC__MetaDataType type);
514 FLAC__StreamMetaData *FLAC__metadata_object_copy(const FLAC__StreamMetaData *object);
515 void FLAC__metadata_object_delete(FLAC__StreamMetaData *object);
516
517 /******************************************************************
518  * FLAC__StreamMetaData_Application
519  * ----------------------------------------------------------------
520  * Note: 'length' is in bytes.
521  */
522 FLAC__bool FLAC__metadata_object_application_set_data(FLAC__StreamMetaData *object, FLAC__byte *data, unsigned length, FLAC__bool copy);
523
524 /******************************************************************
525  * FLAC__StreamMetaData_SeekPoint
526  * ----------------------------------------------------------------
527  * Note that we do not manipulate individual seek points as the
528  * seek table holds a pointer to an array of seek points.  You can
529  * use the _resize function to alter in.  If the size shrinks,
530  * elements will truncated; if it grows, new elements will be added
531  * to the end.
532  */
533 FLAC__StreamMetaData_SeekPoint *FLAC__metadata_object_seekpoint_array_new(unsigned num_points);
534 FLAC__StreamMetaData_SeekPoint *FLAC__metadata_object_seekpoint_array_copy(const FLAC__StreamMetaData_SeekPoint *object_array, unsigned num_points);
535 void FLAC__metadata_object_seekpoint_array_delete(FLAC__StreamMetaData_SeekPoint *object_array);
536 FLAC__bool FLAC__metadata_object_seekpoint_array_resize(FLAC__StreamMetaData_SeekPoint **object_array, unsigned old_num_points, unsigned new_num_points);
537
538 /******************************************************************
539  * FLAC__StreamMetaData_SeekTable
540  */
541 FLAC__bool FLAC__metadata_object_seektable_set_points(FLAC__StreamMetaData *object, FLAC__StreamMetaData_SeekPoint *points, unsigned num_points, FLAC__bool copy);
542
543 /******************************************************************
544  * FLAC__StreamMetaData_VorbisComment_Entry
545  * ----------------------------------------------------------------
546  * This is similar to FLAC__StreamMetaData_SeekPoint.
547  */
548 FLAC__StreamMetaData_VorbisComment_Entry *FLAC__metadata_object_vorbiscomment_entry_array_new(unsigned num_comments);
549 FLAC__StreamMetaData_VorbisComment_Entry *FLAC__metadata_object_vorbiscomment_entry_array_copy(const FLAC__StreamMetaData_VorbisComment_Entry *object_array, unsigned num_comments);
550 void FLAC__metadata_object_vorbiscomment_entry_array_delete(FLAC__StreamMetaData_VorbisComment_Entry *object_array, unsigned num_comments);
551 FLAC__bool FLAC__metadata_object_vorbiscomment_entry_array_resize(FLAC__StreamMetaData_VorbisComment_Entry **object_array, unsigned old_num_comments, unsigned new_num_comments);
552
553 /******************************************************************
554  * FLAC__StreamMetaData_VorbisComment
555  */
556 FLAC__bool FLAC__metadata_object_vorbiscomment_set_vendor_string(FLAC__StreamMetaData *object, FLAC__byte *entry, unsigned length, FLAC__bool copy);
557 FLAC__bool FLAC__metadata_object_vorbiscomment_set_comments(FLAC__StreamMetaData *object, FLAC__StreamMetaData_VorbisComment_Entry *comments, unsigned num_comments, FLAC__bool copy);
558
559 #ifdef __cplusplus
560 }
561 #endif
562
563 #endif