 061991fe60
			
		
	
	
		061991fe60
		
	
	
	
	
		
			
			it appears a one-character typo in the cmake_minimum_required line prevents it from compiling under CMake 4.0. in order to fix that, I had to take this thing out of submodules... it is recommended to do this after you pull; git submodule deinit extern/libsndfile
		
			
				
	
	
		
			908 lines
		
	
	
		
			30 KiB
		
	
	
	
		
			C
		
	
	
	
	
	
			
		
		
	
	
			908 lines
		
	
	
		
			30 KiB
		
	
	
	
		
			C
		
	
	
	
	
	
| /*
 | |
| ** Copyright (C) 2003-2016 Erik de Castro Lopo <erikd@mega-nerd.com>
 | |
| **
 | |
| ** This program is free software; you can redistribute it and/or modify
 | |
| ** it under the terms of the GNU General Public License as published by
 | |
| ** the Free Software Foundation; either version 2 of the License, or
 | |
| ** (at your option) any later version.
 | |
| **
 | |
| ** This program is distributed in the hope that it will be useful,
 | |
| ** but WITHOUT ANY WARRANTY; without even the implied warranty of
 | |
| ** MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
 | |
| ** GNU General Public License for more details.
 | |
| **
 | |
| ** You should have received a copy of the GNU General Public License
 | |
| ** along with this program; if not, write to the Free Software
 | |
| ** Foundation, Inc., 59 Temple Place - Suite 330, Boston, MA 02111-1307, USA.
 | |
| */
 | |
| 
 | |
| #include "sfconfig.h"
 | |
| 
 | |
| #include <stdio.h>
 | |
| #include <stdlib.h>
 | |
| #include <string.h>
 | |
| #include <math.h>
 | |
| #include <inttypes.h>
 | |
| 
 | |
| #if HAVE_UNISTD_H
 | |
| #include <unistd.h>
 | |
| #else
 | |
| #include "sf_unistd.h"
 | |
| #endif
 | |
| 
 | |
| #include	<sndfile.h>
 | |
| 
 | |
| #include	"utils.h"
 | |
| 
 | |
| #define	BUFFER_LEN			(1 << 10)
 | |
| #define LOG_BUFFER_SIZE		1024
 | |
| 
 | |
| #define NULL_PRINTF_CHECK(X) (X ? X : "(null)")
 | |
| 
 | |
| static const char STR_TEST_PREFIX[] = "str" ;
 | |
| 
 | |
| static void	string_start_test (const char *filename, int typemajor) ;
 | |
| static void	string_start_end_test (const char *filename, int typemajor) ;
 | |
| static void	string_multi_set_test (const char *filename, int typemajor) ;
 | |
| static void	string_rdwr_test (const char *filename, int typemajor) ;
 | |
| static void	string_short_rdwr_test (const char *filename, int typemajor) ;
 | |
| static void	string_rdwr_grow_test (const char *filename, int typemajor) ;
 | |
| static void	string_header_update (const char *filename, int typemajor) ;
 | |
| 
 | |
| static void	software_string_test (const char *filename) ;
 | |
| 
 | |
| static int str_count (const char * haystack, const char * needle) ;
 | |
| 
 | |
| int
 | |
| main (int argc, char *argv [])
 | |
| {	int		do_all = 0 ;
 | |
| 	int		test_count = 0 ;
 | |
| 
 | |
| 	if (argc != 2)
 | |
| 	{	printf ("Usage : %s <test>\n", argv [0]) ;
 | |
| 		printf ("    Where <test> is one of the following:\n") ;
 | |
| 		printf ("           wav  - test adding strings to WAV files\n") ;
 | |
| 		printf ("           aiff - test adding strings to AIFF files\n") ;
 | |
| 		printf ("           flac - test adding strings to FLAC files\n") ;
 | |
| 		printf ("           ogg  - test adding strings to OGG files\n") ;
 | |
| 		printf ("           opus - test adding strings to OPUS files\n") ;
 | |
| 		printf ("           all  - perform all tests\n") ;
 | |
| 		exit (1) ;
 | |
| 		} ;
 | |
| 
 | |
| 	do_all = ! strcmp (argv [1], "all") ;
 | |
| 
 | |
| 	if (do_all || ! strcmp (argv [1], "wav"))
 | |
| 	{	string_start_end_test ("strings.wav", SF_FORMAT_WAV) ;
 | |
| 		string_multi_set_test ("multi.wav", SF_FORMAT_WAV) ;
 | |
| 		string_rdwr_test ("rdwr.wav", SF_FORMAT_WAV) ;
 | |
| 		string_short_rdwr_test ("short_rdwr.wav", SF_FORMAT_WAV) ;
 | |
| 		string_rdwr_grow_test ("rdwr_grow.wav", SF_FORMAT_WAV) ;
 | |
| 		string_header_update ("header_update.wav", SF_FORMAT_WAV) ;
 | |
| 
 | |
| 		string_start_end_test ("strings.wavex", SF_FORMAT_WAVEX) ;
 | |
| 		string_multi_set_test ("multi.wavex", SF_FORMAT_WAVEX) ;
 | |
| 		string_rdwr_test ("rdwr.wavex", SF_FORMAT_WAVEX) ;
 | |
| 		string_short_rdwr_test ("short_rdwr.wavex", SF_FORMAT_WAVEX) ;
 | |
| 
 | |
| 		string_start_end_test ("strings.rifx", SF_ENDIAN_BIG | SF_FORMAT_WAV) ;
 | |
| 		string_multi_set_test ("multi.rifx", SF_ENDIAN_BIG | SF_FORMAT_WAV) ;
 | |
| 		string_rdwr_test ("rdwr.rifx", SF_ENDIAN_BIG | SF_FORMAT_WAV) ;
 | |
| 		string_short_rdwr_test ("short_rdwr.rifx", SF_ENDIAN_BIG | SF_FORMAT_WAV) ;
 | |
| 
 | |
| 		software_string_test ("software_string.wav") ;
 | |
| 		test_count++ ;
 | |
| 		} ;
 | |
| 
 | |
| 	if (do_all || ! strcmp (argv [1], "aiff"))
 | |
| 	{	string_start_test ("strings.aiff", SF_FORMAT_AIFF) ;
 | |
| 		string_start_end_test ("strings.aiff", SF_FORMAT_AIFF) ;
 | |
| 		/*
 | |
| 		TODO : Fix src/aiff.c so these tests pass.
 | |
| 		string_multi_set_test ("multi.aiff", SF_FORMAT_AIFF) ;
 | |
| 		string_rdwr_test ("rdwr.aiff", SF_FORMAT_AIFF) ;
 | |
| 		string_short_rdwr_test ("short_rdwr.aiff", SF_FORMAT_AIFF) ;
 | |
| 		string_rdwr_grow_test ("rdwr_grow.aiff", SF_FORMAT_AIFF) ;
 | |
| 		string_header_update ("header_update.aiff", SF_FORMAT_AIFF) ;
 | |
| 		*/
 | |
| 
 | |
| 		test_count++ ;
 | |
| 		} ;
 | |
| 
 | |
| 	if (do_all || ! strcmp (argv [1], "flac"))
 | |
| 	{	if (HAVE_EXTERNAL_XIPH_LIBS)
 | |
| 			string_start_test ("strings.flac", SF_FORMAT_FLAC) ;
 | |
| 		else
 | |
| 			puts ("    No FLAC tests because FLAC support was not compiled in.") ;
 | |
| 		test_count++ ;
 | |
| 		} ;
 | |
| 
 | |
| 	if (do_all || ! strcmp (argv [1], "mpeg"))
 | |
| 	{	if (HAVE_MPEG)
 | |
| 			string_start_test ("mpeg.mp3", SF_FORMAT_MPEG | SF_FORMAT_MPEG_LAYER_III) ;
 | |
| 		else
 | |
| 			puts ("    No MP3 tests because MPEG support was not compiled in.") ;
 | |
| 		test_count++ ;
 | |
| 		} ;
 | |
| 
 | |
| 	if (do_all || ! strcmp (argv [1], "ogg"))
 | |
| 	{	if (HAVE_EXTERNAL_XIPH_LIBS)
 | |
| 			string_start_test ("vorbis.oga", SF_FORMAT_OGG | SF_FORMAT_VORBIS) ;
 | |
| 		else
 | |
| 			puts ("    No Ogg/Vorbis tests because Ogg/Vorbis support was not compiled in.") ;
 | |
| 		test_count++ ;
 | |
| 		} ;
 | |
| 
 | |
| 	if (do_all || ! strcmp (argv [1], "opus"))
 | |
| 	{	if (HAVE_EXTERNAL_XIPH_LIBS)
 | |
| 			string_start_test ("opus.opus", SF_FORMAT_OGG | SF_FORMAT_OPUS) ;
 | |
| 		else
 | |
| 			puts ("    No Ogg/Opus tests because Ogg/Opus support was not compiled in.") ;
 | |
| 		test_count++ ;
 | |
| 		} ;
 | |
| 
 | |
| 	if (do_all || ! strcmp (argv [1], "caf"))
 | |
| 	{	string_start_test ("strings.caf", SF_FORMAT_CAF) ;
 | |
| 		string_start_end_test ("strings.caf", SF_FORMAT_CAF) ;
 | |
| 		string_multi_set_test ("multi.caf", SF_FORMAT_CAF) ;
 | |
| 		/*
 | |
| 		TODO : Fix src/caf.c so these tests pass.
 | |
| 		string_rdwr_test ("rdwr.caf", SF_FORMAT_CAF) ;
 | |
| 		string_short_rdwr_test ("short_rdwr.caf", SF_FORMAT_CAF) ;
 | |
| 		string_header_update ("header_update.caf", SF_FORMAT_CAF) ;
 | |
| 		*/
 | |
| 		test_count++ ;
 | |
| 		} ;
 | |
| 
 | |
| 	if (do_all || ! strcmp (argv [1], "rf64"))
 | |
| 	{	string_start_test ("strings.rf64", SF_FORMAT_RF64) ;
 | |
| 		string_start_end_test ("strings.rf64", SF_FORMAT_RF64) ;
 | |
| 		string_multi_set_test ("multi.rf64", SF_FORMAT_RF64) ;
 | |
| 		/*
 | |
| 		TODO : Fix src/rf64.c so these tests pass.
 | |
| 		string_rdwr_test ("rdwr.rf64", SF_FORMAT_RF64) ;
 | |
| 		string_short_rdwr_test ("short_rdwr.rf64", SF_FORMAT_RF64) ;
 | |
| 		string_header_update ("header_update.rf64", SF_FORMAT_RF64) ;
 | |
| 		*/
 | |
| 		test_count++ ;
 | |
| 		} ;
 | |
| 
 | |
| 	if (do_all || ! strcmp (argv [1], "w64"))
 | |
| 	{	puts ("\n\n     **** String test not working yet for W64 format. ****\n") ;
 | |
| 		/*
 | |
| 		string_start_test ("strings.w64", SF_FORMAT_W64) ;
 | |
| 		string_start_end_test ("strings.w64", SF_FORMAT_W64) ;
 | |
| 		string_multi_set_test ("multi.w64", SF_FORMAT_W64) ;
 | |
| 		string_rdwr_test ("rdwr.w64", SF_FORMAT_W64) ;
 | |
| 		string_short_rdwr_test ("short_rdwr.w64", SF_FORMAT_W64) ;
 | |
| 		string_header_update ("header_update.w64", SF_FORMAT_W64) ;
 | |
| 		*/
 | |
| 		test_count++ ;
 | |
| 		} ;
 | |
| 
 | |
| 	if (test_count == 0)
 | |
| 	{	printf ("Mono : ************************************\n") ;
 | |
| 		printf ("Mono : *  No '%s' test defined.\n", argv [1]) ;
 | |
| 		printf ("Mono : ************************************\n") ;
 | |
| 		return 1 ;
 | |
| 		} ;
 | |
| 
 | |
| 	return 0 ;
 | |
| } /* main */
 | |
| 
 | |
| 
 | |
| /*============================================================================================
 | |
| **	Here are the test functions.
 | |
| */
 | |
| 
 | |
| static const char
 | |
| 	software	[]	= "software (libsndfile-X.Y.Z)",
 | |
| 	artist		[]	= "The Artist",
 | |
| 	copyright	[]	= "Copyright (c) 2001 Artist",
 | |
| 	comment		[]	= "Comment goes here!!!",
 | |
| 	date		[]	= "2001/01/27",
 | |
| 	album		[]	= "The Album",
 | |
| 	license		[]	= "The license",
 | |
| 	title		[]	= "This is the title",
 | |
| 	long_title	[]	= "This is a very long and very boring title for this file",
 | |
| 	long_artist	[]	= "The artist who kept on changing its name",
 | |
| 	genre		[]	= "The genre",
 | |
| 	trackno		[]	= "Track three",
 | |
| 	id3v1_genre	[]	= "Rock",
 | |
| 	year		[]	= "2001" ;
 | |
| 
 | |
| 
 | |
| static	short	data_out [BUFFER_LEN] ;
 | |
| 
 | |
| static void
 | |
| string_start_end_test (const char *filename, int typemajor)
 | |
| {	const char	*cptr ;
 | |
| 	SNDFILE		*file ;
 | |
| 	SF_INFO		sfinfo ;
 | |
| 	int			errors = 0 ;
 | |
| 
 | |
| 	get_unique_test_name (&filename, STR_TEST_PREFIX) ;
 | |
| 	print_test_name ("string_start_end_test", filename) ;
 | |
| 
 | |
| 	memset (&sfinfo, 0, sizeof (sfinfo)) ;
 | |
| 	sfinfo.samplerate	= 44100 ;
 | |
| 	sfinfo.channels		= 1 ;
 | |
| 	sfinfo.frames		= 0 ;
 | |
| 	sfinfo.format		= typemajor | SF_FORMAT_PCM_16 ;
 | |
| 
 | |
| 	file = test_open_file_or_die (filename, SFM_WRITE, &sfinfo, SF_TRUE, __LINE__) ;
 | |
| 
 | |
| 	/* Write stuff at start of file. */
 | |
| 	sf_set_string (file, SF_STR_TITLE, filename) ;
 | |
| 	sf_set_string (file, SF_STR_SOFTWARE, software) ;
 | |
| 	sf_set_string (file, SF_STR_ARTIST, artist) ;
 | |
| 	sf_set_string (file, SF_STR_GENRE, genre) ;
 | |
| 	sf_set_string (file, SF_STR_TRACKNUMBER, trackno) ;
 | |
| 
 | |
| 	/* Write data to file. */
 | |
| 	test_write_short_or_die (file, 0, data_out, BUFFER_LEN, __LINE__) ;
 | |
| 	test_seek_or_die (file, 0, SEEK_SET, 0, sfinfo.channels, __LINE__) ;
 | |
| 
 | |
| 	/* Write more stuff at end of file. */
 | |
| 	sf_set_string (file, SF_STR_COPYRIGHT, copyright) ;
 | |
| 	sf_set_string (file, SF_STR_COMMENT, comment) ;
 | |
| 	sf_set_string (file, SF_STR_DATE, date) ;
 | |
| 	sf_set_string (file, SF_STR_ALBUM, album) ;
 | |
| 	sf_set_string (file, SF_STR_LICENSE, license) ;
 | |
| 
 | |
| 	sf_close (file) ;
 | |
| 
 | |
| 	file = test_open_file_or_die (filename, SFM_READ, &sfinfo, SF_TRUE, __LINE__) ;
 | |
| 
 | |
| 	check_log_buffer_or_die (file, __LINE__) ;
 | |
| 
 | |
| 	if (sfinfo.frames != BUFFER_LEN)
 | |
| 	{	printf ("***** Bad frame count %d (should be %d)\n\n", (int) sfinfo.frames, BUFFER_LEN) ;
 | |
| 		errors ++ ;
 | |
| 		} ;
 | |
| 
 | |
| 	cptr = sf_get_string (file, SF_STR_TITLE) ;
 | |
| 	if (cptr == NULL || strcmp (filename, cptr) != 0)
 | |
| 	{	if (errors++ == 0)
 | |
| 			puts ("\n") ;
 | |
| 		printf ("    Bad filename  : %s\n", NULL_PRINTF_CHECK(cptr)) ;
 | |
| 		} ;
 | |
| 
 | |
| 	cptr = sf_get_string (file, SF_STR_COPYRIGHT) ;
 | |
| 	if (cptr == NULL || strcmp (copyright, cptr) != 0)
 | |
| 	{	if (errors++ == 0)
 | |
| 			puts ("\n") ;
 | |
| 		printf ("    Bad copyright : %s\n", NULL_PRINTF_CHECK(cptr)) ;
 | |
| 		} ;
 | |
| 
 | |
| 	cptr = sf_get_string (file, SF_STR_SOFTWARE) ;
 | |
| 	if (cptr == NULL || strstr (cptr, software) != cptr)
 | |
| 	{	if (errors++ == 0)
 | |
| 			puts ("\n") ;
 | |
| 		printf ("    Bad software  : %s\n", NULL_PRINTF_CHECK(cptr)) ;
 | |
| 		} ;
 | |
| 
 | |
| 	if (str_count (cptr, "libsndfile") != 1)
 | |
| 	{	if (errors++ == 0)
 | |
| 			puts ("\n") ;
 | |
| 		printf ("    Bad software  : %s\n", cptr) ;
 | |
| 		} ;
 | |
| 
 | |
| 	cptr = sf_get_string (file, SF_STR_ARTIST) ;
 | |
| 	if (cptr == NULL || strcmp (artist, cptr) != 0)
 | |
| 	{	if (errors++ == 0)
 | |
| 			puts ("\n") ;
 | |
| 		printf ("    Bad artist    : %s\n", NULL_PRINTF_CHECK(cptr)) ;
 | |
| 		} ;
 | |
| 
 | |
| 	cptr = sf_get_string (file, SF_STR_COMMENT) ;
 | |
| 	if (cptr == NULL || strcmp (comment, cptr) != 0)
 | |
| 	{	if (errors++ == 0)
 | |
| 			puts ("\n") ;
 | |
| 		printf ("    Bad comment   : %s\n", NULL_PRINTF_CHECK(cptr)) ;
 | |
| 		} ;
 | |
| 
 | |
| 	if (typemajor != SF_FORMAT_AIFF)
 | |
| 	{	cptr = sf_get_string (file, SF_STR_DATE) ;
 | |
| 		if (cptr == NULL || strcmp (date, cptr) != 0)
 | |
| 		{	if (errors++ == 0)
 | |
| 				puts ("\n") ;
 | |
| 			printf ("    Bad date      : %s\n", NULL_PRINTF_CHECK(cptr)) ;
 | |
| 			} ;
 | |
| 
 | |
| 		cptr = sf_get_string (file, SF_STR_GENRE) ;
 | |
| 		if (cptr == NULL || strcmp (genre, cptr) != 0)
 | |
| 		{	if (errors++ == 0)
 | |
| 				puts ("\n") ;
 | |
| 			printf ("    Bad genre     : %s\n", NULL_PRINTF_CHECK(cptr)) ;
 | |
| 			} ;
 | |
| 		} ;
 | |
| 
 | |
| 	switch (typemajor)
 | |
| 	{	case SF_FORMAT_AIFF :
 | |
| 		case SF_FORMAT_WAV :
 | |
| 		case SF_FORMAT_WAVEX :
 | |
| 		case SF_ENDIAN_BIG | SF_FORMAT_WAV :
 | |
| 		case SF_FORMAT_RF64 :
 | |
| 			/* These formats do not support the following. */
 | |
| 			break ;
 | |
| 
 | |
| 		default :
 | |
| 			cptr = sf_get_string (file, SF_STR_ALBUM) ;
 | |
| 			if (cptr == NULL || strcmp (album, cptr) != 0)
 | |
| 			{	if (errors++ == 0)
 | |
| 					puts ("\n") ;
 | |
| 				printf ("    Bad album     : %s\n", NULL_PRINTF_CHECK(cptr)) ;
 | |
| 				} ;
 | |
| 
 | |
| 			cptr = sf_get_string (file, SF_STR_LICENSE) ;
 | |
| 			if (cptr == NULL || strcmp (license, cptr) != 0)
 | |
| 			{	if (errors++ == 0)
 | |
| 					puts ("\n") ;
 | |
| 				printf ("    Bad license   : %s\n", NULL_PRINTF_CHECK(cptr)) ;
 | |
| 				} ;
 | |
| 
 | |
| 			cptr = sf_get_string (file, SF_STR_TRACKNUMBER) ;
 | |
| 			if (cptr == NULL || strcmp (trackno, cptr) != 0)
 | |
| 			{	if (errors++ == 0)
 | |
| 					puts ("\n") ;
 | |
| 				printf ("    Bad track no. : %s\n", NULL_PRINTF_CHECK(cptr)) ;
 | |
| 				} ;
 | |
| 			break ;
 | |
| 		} ;
 | |
| 
 | |
| 	if (errors > 0)
 | |
| 	{	printf ("\n*** Error count : %d ***\n\n", errors) ;
 | |
| 		dump_log_buffer (file) ;
 | |
| 		exit (1) ;
 | |
| 		} ;
 | |
| 
 | |
| 	sf_close (file) ;
 | |
| 	unlink (filename) ;
 | |
| 
 | |
| 	puts ("ok") ;
 | |
| } /* string_start_end_test */
 | |
| 
 | |
| static void
 | |
| string_start_test (const char *filename, int formattype)
 | |
| {	const char	*cptr ;
 | |
| 	SNDFILE		*file ;
 | |
| 	SF_INFO		sfinfo ;
 | |
| 	int			errors = 0 ;
 | |
| 	int			typemajor = SF_FORMAT_TYPEMASK & formattype ;
 | |
| 
 | |
| 	get_unique_test_name (&filename, STR_TEST_PREFIX) ;
 | |
| 	print_test_name ("string_start_test", filename) ;
 | |
| 
 | |
| 	memset (&sfinfo, 0, sizeof (sfinfo)) ;
 | |
| 	sfinfo.samplerate	= 44100 ;
 | |
| 	sfinfo.channels		= 1 ;
 | |
| 	sfinfo.frames		= 0 ;
 | |
| 
 | |
| 	switch (formattype)
 | |
| 	{	case SF_FORMAT_OGG | SF_FORMAT_OPUS :
 | |
| 			/* Opus only supports some discrete sample rates. */
 | |
| 			sfinfo.samplerate = 48000 ;
 | |
| 			break ;
 | |
| 
 | |
| 		case SF_FORMAT_OGG | SF_FORMAT_VORBIS :
 | |
| 		case SF_FORMAT_MPEG | SF_FORMAT_MPEG_LAYER_III :
 | |
| 			break ;
 | |
| 
 | |
| 		default :
 | |
| 			formattype |= SF_FORMAT_PCM_16 ;
 | |
| 			break ;
 | |
| 		} ;
 | |
| 	sfinfo.format = formattype ;
 | |
| 
 | |
| 	file = test_open_file_or_die (filename, SFM_WRITE, &sfinfo, SF_TRUE, __LINE__) ;
 | |
| 
 | |
| 	/* Write stuff at start of file. */
 | |
| 	sf_set_string (file, SF_STR_TITLE, filename) ;
 | |
| 	sf_set_string (file, SF_STR_SOFTWARE, software) ;
 | |
| 	sf_set_string (file, SF_STR_ARTIST, artist) ;
 | |
| 	sf_set_string (file, SF_STR_COPYRIGHT, copyright) ;
 | |
| 	sf_set_string (file, SF_STR_COMMENT, comment) ;
 | |
| 	sf_set_string (file, SF_STR_ALBUM, album) ;
 | |
| 	sf_set_string (file, SF_STR_LICENSE, license) ;
 | |
| 	if (typemajor == SF_FORMAT_MPEG)
 | |
| 	{	sf_set_string (file, SF_STR_GENRE, id3v1_genre) ;
 | |
| 		sf_set_string (file, SF_STR_DATE, year) ;
 | |
| 		}
 | |
| 	else
 | |
| 	{	sf_set_string (file, SF_STR_DATE, date) ;
 | |
| 		} ;
 | |
| 
 | |
| 	/* Write data to file. */
 | |
| 	test_write_short_or_die (file, 0, data_out, BUFFER_LEN, __LINE__) ;
 | |
| 
 | |
| 	sf_close (file) ;
 | |
| 
 | |
| 	file = test_open_file_or_die (filename, SFM_READ, &sfinfo, SF_TRUE, __LINE__) ;
 | |
| 
 | |
| 	check_log_buffer_or_die (file, __LINE__) ;
 | |
| 
 | |
| 	if (sfinfo.frames != BUFFER_LEN)
 | |
| 	{	printf ("***** Bad frame count %d (should be %d)\n\n", (int) sfinfo.frames, BUFFER_LEN) ;
 | |
| 		errors ++ ;
 | |
| 		} ;
 | |
| 
 | |
| 	cptr = sf_get_string (file, SF_STR_TITLE) ;
 | |
| 	if (cptr == NULL || strcmp (filename, cptr) != 0)
 | |
| 	{	if (errors++ == 0)
 | |
| 			puts ("\n") ;
 | |
| 		printf ("    Bad filename  : %s\n", NULL_PRINTF_CHECK(cptr)) ;
 | |
| 		} ;
 | |
| 
 | |
| 	if (typemajor != SF_FORMAT_MPEG)
 | |
| 	{	cptr = sf_get_string (file, SF_STR_COPYRIGHT) ;
 | |
| 		if (cptr == NULL || strcmp (copyright, cptr) != 0)
 | |
| 		{	if (errors++ == 0)
 | |
| 				puts ("\n") ;
 | |
| 			printf ("    Bad copyright : %s\n", NULL_PRINTF_CHECK(cptr)) ;
 | |
| 			} ;
 | |
| 
 | |
| 		cptr = sf_get_string (file, SF_STR_SOFTWARE) ;
 | |
| 		if (cptr == NULL || strstr (cptr, software) != cptr)
 | |
| 		{	if (errors++ == 0)
 | |
| 				puts ("\n") ;
 | |
| 			printf ("    Bad software  : %s\n", NULL_PRINTF_CHECK(cptr)) ;
 | |
| 			} ;
 | |
| 
 | |
| 		if (cptr && str_count (cptr, "libsndfile") != 1)
 | |
| 		{	if (errors++ == 0)
 | |
| 				puts ("\n") ;
 | |
| 			printf ("    Bad software  : %s\n", cptr) ;
 | |
| 			} ;
 | |
| 		} ;
 | |
| 
 | |
| 	if (typemajor == SF_FORMAT_MPEG)
 | |
| 	{	cptr = sf_get_string (file, SF_STR_GENRE) ;
 | |
| 		if (cptr == NULL || strcmp (id3v1_genre, cptr) != 0)
 | |
| 		{	if (errors++ == 0)
 | |
| 				puts ("\n") ;
 | |
| 			printf ("    Bad genre     : %s\n", NULL_PRINTF_CHECK(cptr)) ;
 | |
| 			} ;
 | |
| 		} ;
 | |
| 
 | |
| 	cptr = sf_get_string (file, SF_STR_ARTIST) ;
 | |
| 	if (cptr == NULL || strcmp (artist, cptr) != 0)
 | |
| 	{	if (errors++ == 0)
 | |
| 			puts ("\n") ;
 | |
| 		printf ("    Bad artist    : %s\n", NULL_PRINTF_CHECK(cptr)) ;
 | |
| 		} ;
 | |
| 
 | |
| 	cptr = sf_get_string (file, SF_STR_COMMENT) ;
 | |
| 	if (cptr == NULL || strcmp (comment, cptr) != 0)
 | |
| 	{	if (errors++ == 0)
 | |
| 			puts ("\n") ;
 | |
| 		printf ("    Bad comment   : %s\n", NULL_PRINTF_CHECK(cptr)) ;
 | |
| 		} ;
 | |
| 
 | |
| 	switch (typemajor)
 | |
| 	{	case SF_FORMAT_AIFF :
 | |
| 			/* not supported */
 | |
| 			break ;
 | |
| 
 | |
| 		case SF_FORMAT_MPEG :
 | |
| 			/* id3 only supports years */
 | |
| 			cptr = sf_get_string (file, SF_STR_DATE) ;
 | |
| 			if (cptr == NULL || strcmp (year, cptr) != 0)
 | |
| 			{	if (errors++ == 0)
 | |
| 					puts ("\n") ;
 | |
| 				printf ("    Bad date      : %s\n", NULL_PRINTF_CHECK(cptr)) ;
 | |
| 				} ;
 | |
| 			break ;
 | |
| 
 | |
| 		default :
 | |
| 			cptr = sf_get_string (file, SF_STR_DATE) ;
 | |
| 			if (cptr == NULL || strcmp (date, cptr) != 0)
 | |
| 			{	if (errors++ == 0)
 | |
| 					puts ("\n") ;
 | |
| 				printf ("    Bad date      : %s\n", NULL_PRINTF_CHECK(cptr)) ;
 | |
| 				} ;
 | |
| 			break ;
 | |
| 		} ;
 | |
| 
 | |
| 	if (typemajor != SF_FORMAT_WAV && typemajor != SF_FORMAT_AIFF)
 | |
| 	{	cptr = sf_get_string (file, SF_STR_ALBUM) ;
 | |
| 		if (cptr == NULL || strcmp (album, cptr) != 0)
 | |
| 		{	if (errors++ == 0)
 | |
| 				puts ("\n") ;
 | |
| 			printf ("    Bad album     : %s\n", NULL_PRINTF_CHECK(cptr)) ;
 | |
| 			} ;
 | |
| 		} ;
 | |
| 
 | |
| 	switch (typemajor)
 | |
| 	{	case SF_FORMAT_WAV :
 | |
| 		case SF_FORMAT_AIFF :
 | |
| 		case SF_FORMAT_RF64 :
 | |
| 		case SF_FORMAT_MPEG :
 | |
| 			/* not supported */
 | |
| 			break ;
 | |
| 
 | |
| 		default:
 | |
| 			cptr = sf_get_string (file, SF_STR_LICENSE) ;
 | |
| 			if (cptr == NULL || strcmp (license, cptr) != 0)
 | |
| 			{	if (errors++ == 0)
 | |
| 					puts ("\n") ;
 | |
| 				printf ("    Bad license   : %s\n", NULL_PRINTF_CHECK(cptr)) ;
 | |
| 				} ;
 | |
| 		} ;
 | |
| 
 | |
| 	if (errors > 0)
 | |
| 	{	printf ("\n*** Error count : %d ***\n\n", errors) ;
 | |
| 		dump_log_buffer (file) ;
 | |
| 		exit (1) ;
 | |
| 		} ;
 | |
| 
 | |
| 	sf_close (file) ;
 | |
| 	unlink (filename) ;
 | |
| 
 | |
| 	puts ("ok") ;
 | |
| } /* string_start_test */
 | |
| 
 | |
| static void
 | |
| string_multi_set_test (const char *filename, int typemajor)
 | |
| {	static const char
 | |
| 		new_software	[]	= "new software (libsndfile-X.Y.Z)",
 | |
| 		new_copyright	[]	= "Copyright (c) 2001 New Artist",
 | |
| 		new_artist		[]	= "The New Artist",
 | |
| 		new_title		[]	= "This is the new title" ;
 | |
| 
 | |
| 	static char buffer [2048] ;
 | |
| 	SNDFILE		*file ;
 | |
| 	SF_INFO		sfinfo ;
 | |
| 	int			count ;
 | |
| 
 | |
| 	get_unique_test_name (&filename, STR_TEST_PREFIX) ;
 | |
| 	print_test_name (__func__, filename) ;
 | |
| 
 | |
| 	memset (&sfinfo, 0, sizeof (sfinfo)) ;
 | |
| 	sfinfo.format		= typemajor | SF_FORMAT_PCM_16 ;
 | |
| 	sfinfo.samplerate	= 44100 ;
 | |
| 	sfinfo.channels		= 1 ;
 | |
| 	sfinfo.frames		= 0 ;
 | |
| 
 | |
| 	file = test_open_file_or_die (filename, SFM_WRITE, &sfinfo, SF_TRUE, __LINE__) ;
 | |
| 
 | |
| 	/* Write stuff at start of file. */
 | |
| 	sf_set_string (file, SF_STR_TITLE, title) ;
 | |
| 	sf_set_string (file, SF_STR_SOFTWARE, software) ;
 | |
| 	sf_set_string (file, SF_STR_ARTIST, artist) ;
 | |
| 
 | |
| 	/* Write data to file. */
 | |
| 	test_write_short_or_die (file, 0, data_out, BUFFER_LEN, __LINE__) ;
 | |
| 
 | |
| 	/* Write it all again. */
 | |
| 
 | |
| 	sf_set_string (file, SF_STR_TITLE, new_title) ;
 | |
| 	sf_set_string (file, SF_STR_SOFTWARE, new_software) ;
 | |
| 	sf_set_string (file, SF_STR_ARTIST, new_artist) ;
 | |
| 
 | |
| 	sf_set_string (file, SF_STR_COPYRIGHT, copyright) ;
 | |
| 	sf_set_string (file, SF_STR_COMMENT, comment) ;
 | |
| 	sf_set_string (file, SF_STR_DATE, date) ;
 | |
| 	sf_set_string (file, SF_STR_ALBUM, album) ;
 | |
| 	sf_set_string (file, SF_STR_LICENSE, license) ;
 | |
| 	sf_set_string (file, SF_STR_COPYRIGHT, new_copyright) ;
 | |
| 	sf_set_string (file, SF_STR_COMMENT, comment) ;
 | |
| 	sf_set_string (file, SF_STR_DATE, date) ;
 | |
| 	sf_set_string (file, SF_STR_ALBUM, album) ;
 | |
| 	sf_set_string (file, SF_STR_LICENSE, license) ;
 | |
| 
 | |
| 	sf_close (file) ;
 | |
| 
 | |
| 	file = test_open_file_or_die (filename, SFM_READ, &sfinfo, SF_TRUE, __LINE__) ;
 | |
| 	sf_command	(file, SFC_GET_LOG_INFO, buffer, sizeof (buffer)) ;
 | |
| 	sf_close (file) ;
 | |
| 
 | |
| 	count = str_count (buffer, new_title) ;
 | |
| 	exit_if_true (count < 1, "\n\nLine %d : Could not find new_title in :\n%s\n", __LINE__, buffer) ;
 | |
| 	exit_if_true (count > 1, "\n\nLine %d : new_title appears %d times in :\n\n%s\n", __LINE__, count, buffer) ;
 | |
| 
 | |
| 	count = str_count (buffer, software) ;
 | |
| 	exit_if_true (count < 1, "\n\nLine %d : Could not find new_software in :\n%s\n", __LINE__, buffer) ;
 | |
| 	exit_if_true (count > 1, "\n\nLine %d : new_software appears %d times in :\n\n%s\n", __LINE__, count, buffer) ;
 | |
| 
 | |
| 	count = str_count (buffer, new_artist) ;
 | |
| 	exit_if_true (count < 1, "\n\nLine %d : Could not find new_artist in :\n%s\n", __LINE__, buffer) ;
 | |
| 	exit_if_true (count > 1, "\n\nLine %d : new_artist appears %d times in :\n\n%s\n", __LINE__, count, buffer) ;
 | |
| 
 | |
| 	count = str_count (buffer, new_copyright) ;
 | |
| 	exit_if_true (count < 1, "\n\nLine %d : Could not find new_copyright in :\n%s\n", __LINE__, buffer) ;
 | |
| 	exit_if_true (count > 1, "\n\nLine %d : new_copyright appears %d times in :\n\n%s\n", __LINE__, count, buffer) ;
 | |
| 
 | |
| 	unlink (filename) ;
 | |
| 
 | |
| 	puts ("ok") ;
 | |
| } /* string_multi_set_test */
 | |
| 
 | |
| static void
 | |
| string_rdwr_test (const char *filename, int typemajor)
 | |
| {	SNDFILE *file ;
 | |
| 	SF_INFO sfinfo ;
 | |
| 	sf_count_t frames ;
 | |
| 	const char * str ;
 | |
| 
 | |
| 	get_unique_test_name (&filename, STR_TEST_PREFIX) ;
 | |
| 	print_test_name (__func__, filename) ;
 | |
| 	create_short_sndfile (filename, typemajor | SF_FORMAT_PCM_16, 2) ;
 | |
| 
 | |
| 	memset (&sfinfo, 0, sizeof (sfinfo)) ;
 | |
| 	file = test_open_file_or_die (filename, SFM_RDWR, &sfinfo, SF_FALSE, __LINE__) ;
 | |
| 	frames = sfinfo.frames ;
 | |
| 	sf_set_string (file, SF_STR_TITLE, title) ;
 | |
| 	sf_close (file) ;
 | |
| 
 | |
| 	file = test_open_file_or_die (filename, SFM_READ, &sfinfo, SF_FALSE, __LINE__) ;
 | |
| 	exit_if_true (frames != sfinfo.frames, "\n\nLine %d : Frame count %" PRId64 " should be %" PRId64 ".\n", __LINE__, sfinfo.frames, frames) ;
 | |
| 	str = sf_get_string (file, SF_STR_TITLE) ;
 | |
| 	exit_if_true (str == NULL, "\n\nLine %d : SF_STR_TITLE string is NULL.\n", __LINE__) ;
 | |
| 	exit_if_true (strcmp (str, title) != 0, "\n\nLine %d : SF_STR_TITLE doesn't match what was written.\n", __LINE__) ;
 | |
| 	sf_close (file) ;
 | |
| 
 | |
| 	file = test_open_file_or_die (filename, SFM_RDWR, &sfinfo, SF_FALSE, __LINE__) ;
 | |
| 	frames = sfinfo.frames ;
 | |
| 	sf_set_string (file, SF_STR_TITLE, title) ;
 | |
| 	sf_close (file) ;
 | |
| 
 | |
| 	file = test_open_file_or_die (filename, SFM_RDWR, &sfinfo, SF_FALSE, __LINE__) ;
 | |
| 	str = sf_get_string (file, SF_STR_TITLE) ;
 | |
| 	exit_if_true (str == NULL, "\n\nLine %d : SF_STR_TITLE string is NULL.\n", __LINE__) ;
 | |
| 	sf_set_string (file, SF_STR_ARTIST, artist) ;
 | |
| 	sf_close (file) ;
 | |
| 
 | |
| 	file = test_open_file_or_die (filename, SFM_READ, &sfinfo, SF_FALSE, __LINE__) ;
 | |
| 
 | |
| 	str = sf_get_string (file, SF_STR_ARTIST) ;
 | |
| 	exit_if_true (str == NULL, "\n\nLine %d : SF_STR_ARTIST string is NULL.\n", __LINE__) ;
 | |
| 	exit_if_true (strcmp (str, artist) != 0, "\n\nLine %d : SF_STR_ARTIST doesn't match what was written.\n", __LINE__) ;
 | |
| 
 | |
| 	str = sf_get_string (file, SF_STR_TITLE) ;
 | |
| 	exit_if_true (str == NULL, "\n\nLine %d : SF_STR_TITLE string is NULL.\n", __LINE__) ;
 | |
| 	exit_if_true (strcmp (str, title) != 0, "\n\nLine %d : SF_STR_TITLE doesn't match what was written.\n", __LINE__) ;
 | |
| 
 | |
| 	exit_if_true (frames != sfinfo.frames, "\n\nLine %d : Frame count %" PRId64 " should be %" PRId64 ".\n", __LINE__, sfinfo.frames, frames) ;
 | |
| 
 | |
| 	sf_close (file) ;
 | |
| 	unlink (filename) ;
 | |
| 
 | |
| 	puts ("ok") ;
 | |
| } /* string_rdwr_test */
 | |
| 
 | |
| static void
 | |
| string_short_rdwr_test (const char *filename, int typemajor)
 | |
| {	SNDFILE *file ;
 | |
| 	SF_INFO sfinfo ;
 | |
| 	sf_count_t frames = BUFFER_LEN ;
 | |
| 	const char * str ;
 | |
| 
 | |
| 	get_unique_test_name (&filename, STR_TEST_PREFIX) ;
 | |
| 	print_test_name (__func__, filename) ;
 | |
| 
 | |
| 	memset (&sfinfo, 0, sizeof (sfinfo)) ;
 | |
| 	sfinfo.format		= typemajor | SF_FORMAT_PCM_16 ;
 | |
| 	sfinfo.samplerate	= 44100 ;
 | |
| 	sfinfo.channels		= 1 ;
 | |
| 	sfinfo.frames		= 0 ;
 | |
| 
 | |
| 	file = test_open_file_or_die (filename, SFM_WRITE, &sfinfo, SF_FALSE, __LINE__) ;
 | |
| 
 | |
| 	/* Write data to file. */
 | |
| 	test_write_short_or_die (file, 0, data_out, BUFFER_LEN, __LINE__) ;
 | |
| 
 | |
| 	sf_set_string (file, SF_STR_TITLE, long_title) ;
 | |
| 	sf_set_string (file, SF_STR_ARTIST, long_artist) ;
 | |
| 	sf_close (file) ;
 | |
| 
 | |
| 	/* Open the file RDWR. */
 | |
| 	file = test_open_file_or_die (filename, SFM_RDWR, &sfinfo, SF_FALSE, __LINE__) ;
 | |
| 	exit_if_true (frames != sfinfo.frames, "\n\nLine %d : Frame count %" PRId64 " should be %" PRId64 ".\n", __LINE__, sfinfo.frames, frames) ;
 | |
| 	str = sf_get_string (file, SF_STR_TITLE) ;
 | |
| 	exit_if_true (str == NULL, "\n\nLine %d : SF_STR_TITLE string is NULL.\n", __LINE__) ;
 | |
| 	exit_if_true (strcmp (str, long_title) != 0, "\n\nLine %d : SF_STR_TITLE doesn't match what was written.\n", __LINE__) ;
 | |
| 	str = sf_get_string (file, SF_STR_ARTIST) ;
 | |
| 	exit_if_true (str == NULL, "\n\nLine %d : SF_STR_TITLE string is NULL.\n", __LINE__) ;
 | |
| 	exit_if_true (strcmp (str, long_artist) != 0, "\n\nLine %d : SF_STR_ARTIST doesn't match what was written.\n", __LINE__) ;
 | |
| 
 | |
| 	/* Change title and artist. */
 | |
| 	sf_set_string (file, SF_STR_TITLE, title) ;
 | |
| 	sf_set_string (file, SF_STR_ARTIST, artist) ;
 | |
| 
 | |
| 	sf_close (file) ;
 | |
| 
 | |
| 	file = test_open_file_or_die (filename, SFM_READ, &sfinfo, SF_FALSE, __LINE__) ;
 | |
| 
 | |
| 	check_log_buffer_or_die (file, __LINE__) ;
 | |
| 
 | |
| 	str = sf_get_string (file, SF_STR_TITLE) ;
 | |
| 	exit_if_true (str == NULL, "\n\nLine %d : SF_STR_TITLE string is NULL.\n", __LINE__) ;
 | |
| 	exit_if_true (strcmp (str, title) != 0, "\n\nLine %d : SF_STR_TITLE doesn't match what was written.\n", __LINE__) ;
 | |
| 
 | |
| 	str = sf_get_string (file, SF_STR_ARTIST) ;
 | |
| 	exit_if_true (str == NULL, "\n\nLine %d : SF_STR_ARTIST string is NULL.\n", __LINE__) ;
 | |
| 	exit_if_true (strcmp (str, artist) != 0, "\n\nLine %d : SF_STR_ARTIST doesn't match what was written.\n", __LINE__) ;
 | |
| 
 | |
| 	sf_close (file) ;
 | |
| 	unlink (filename) ;
 | |
| 
 | |
| 	puts ("ok") ;
 | |
| } /* string_short_rdwr_test */
 | |
| 
 | |
| static int
 | |
| str_count (const char * haystack, const char * needle)
 | |
| {	int count = 0 ;
 | |
| 
 | |
| 	while ((haystack = strstr (haystack, needle)) != NULL)
 | |
| 	{	count ++ ;
 | |
| 		haystack ++ ;
 | |
| 		} ;
 | |
| 
 | |
| 	return count ;
 | |
| } /* str_count */
 | |
| 
 | |
| #define MIN(a, b)	((a) < (b) ? (a) : (b))
 | |
| 
 | |
| static void
 | |
| software_string_test (const char *filename)
 | |
| {	size_t k ;
 | |
| 
 | |
| 	get_unique_test_name (&filename, STR_TEST_PREFIX) ;
 | |
| 	print_test_name (__func__, filename) ;
 | |
| 
 | |
| 	for (k = 0 ; k < 50 ; k++)
 | |
| 	{	const char *result ;
 | |
| 		char sfname [64] = "" ;
 | |
| 		SNDFILE *file ;
 | |
| 		SF_INFO info ;
 | |
| 
 | |
| 		sf_info_setup (&info, SF_FORMAT_WAV | SF_FORMAT_PCM_16, 44100, 1) ;
 | |
| 		file = test_open_file_or_die (filename, SFM_WRITE, &info, SF_TRUE, __LINE__) ;
 | |
| 
 | |
| 		snprintf (sfname, MIN (k, sizeof (sfname)), "%s", "abcdefghijklmnopqrestvwxyz0123456789abcdefghijklmnopqrestvwxyz") ;
 | |
| 
 | |
| 		exit_if_true (sf_set_string (file, SF_STR_SOFTWARE, sfname),
 | |
| 			"\n\nLine %d : sf_set_string (f, SF_STR_SOFTWARE, '%s') failed : %s\n", __LINE__, sfname, sf_strerror (file)) ;
 | |
| 
 | |
| 		sf_close (file) ;
 | |
| 
 | |
| 		file = test_open_file_or_die (filename, SFM_READ, &info, SF_TRUE, __LINE__) ;
 | |
| 		result = sf_get_string (file, SF_STR_SOFTWARE) ;
 | |
| 
 | |
| 		exit_if_true (result == NULL, "\n\nLine %d : sf_get_string (file, SF_STR_SOFTWARE) returned NULL.\n\n", __LINE__) ;
 | |
| 
 | |
| 		exit_if_true (strstr (result, sfname) != result,
 | |
| 			"\n\nLine %d : Can't fine string '%s' in '%s'\n\n", __LINE__, sfname, result) ;
 | |
| 		sf_close (file) ;
 | |
| 		} ;
 | |
| 
 | |
| 	unlink (filename) ;
 | |
| 	puts ("ok") ;
 | |
| } /* software_string_test */
 | |
| 
 | |
| 
 | |
| static void
 | |
| string_rdwr_grow_test (const char *filename, int typemajor)
 | |
| {	SNDFILE *file ;
 | |
| 	SF_INFO sfinfo ;
 | |
| 	sf_count_t frames ;
 | |
| 	const char * str ;
 | |
| 
 | |
| 	get_unique_test_name (&filename, STR_TEST_PREFIX) ;
 | |
| 	print_test_name (__func__, filename) ;
 | |
| 
 | |
| 	/* Create a file that contains some strings. Then open the file in RDWR mode and
 | |
| 		 grow the file by writing more audio data to it. Check that the audio data has
 | |
| 		 been added to the file, and that the strings are still there. */
 | |
| 
 | |
| 	/* Create a short file that contains a string. */
 | |
| 	memset (&sfinfo, 0, sizeof (sfinfo)) ;
 | |
| 	sfinfo.samplerate	= 44100 ;
 | |
| 	sfinfo.channels		= 2 ;
 | |
| 	sfinfo.frames		= 0 ;
 | |
| 	sfinfo.format		= typemajor | SF_FORMAT_PCM_16 ;
 | |
| 
 | |
| 	file = test_open_file_or_die (filename, SFM_WRITE, &sfinfo, SF_TRUE, __LINE__) ;
 | |
| 	/* Write data to file. */
 | |
| 	test_write_short_or_die (file, 0, data_out, BUFFER_LEN, __LINE__) ;
 | |
| 
 | |
| 	/* Write some strings at end of file. */
 | |
| 	sf_set_string (file, SF_STR_TITLE , title) ;
 | |
| 	sf_set_string (file, SF_STR_COMMENT, comment) ;
 | |
| 	sf_close (file) ;
 | |
| 
 | |
| 
 | |
| 	/* Now open file again in SFM_RDWR mode and write more audio data to it. */
 | |
| 	file = test_open_file_or_die (filename, SFM_RDWR, &sfinfo, SF_TRUE, __LINE__) ;
 | |
| 	/* Write more data to file.  */
 | |
| 	test_write_short_or_die (file, 0, data_out, BUFFER_LEN, __LINE__) ;
 | |
| 	sf_close (file) ;
 | |
| 
 | |
| 
 | |
| 	/* Now open file again. It should now contain two BUFFER_LEN's worth of frames and the strings. */
 | |
| 	frames = 2 * BUFFER_LEN / sfinfo.channels ;
 | |
| 	file = test_open_file_or_die (filename, SFM_READ, &sfinfo, SF_TRUE, __LINE__) ;
 | |
| 	exit_if_true (frames != sfinfo.frames, "\n\nLine %d : Frame count %" PRId64 " should be %" PRId64 ".\n", __LINE__, sfinfo.frames, frames) ;
 | |
| 
 | |
| 	/* Check the strings */
 | |
| 	str = sf_get_string (file, SF_STR_TITLE) ;
 | |
| 	exit_if_true (str == NULL, "\n\nLine %d : SF_STR_TITLE string is NULL.\n", __LINE__) ;
 | |
| 	exit_if_true (strcmp (str, title) != 0, "\n\nLine %d : SF_STR_TITLE doesn't match what was written.\n", __LINE__) ;
 | |
| 
 | |
| 	str = sf_get_string (file, SF_STR_COMMENT) ;
 | |
| 	exit_if_true (str == NULL, "\n\nLine %d : SF_STR_COMMENT string is NULL.\n", __LINE__) ;
 | |
| 	exit_if_true (strcmp (str, comment) != 0, "\n\nLine %d : SF_STR_COMMENT doesn't match what was written.\n", __LINE__) ;
 | |
| 
 | |
| 	sf_close (file) ;
 | |
| 	unlink (filename) ;
 | |
| 
 | |
| 	puts ("ok") ;
 | |
| } /* string_rdwr_grow_test */
 | |
| 
 | |
| static void
 | |
| string_header_update (const char *filename, int typemajor)
 | |
| {	SNDFILE *file , *file1 ;
 | |
| 	SF_INFO sfinfo , sfinfo1 ;
 | |
| 	sf_count_t frames ;
 | |
| 	const char * str ;
 | |
| 	const int GROW_BUFFER_AMOUNT = 4 ; /* this should be less than half the size of the string header */
 | |
| 
 | |
| 	get_unique_test_name (&filename, STR_TEST_PREFIX) ;
 | |
| 	print_test_name (__func__, filename) ;
 | |
| 
 | |
| 	/* Create a short file. */
 | |
| 	memset (&sfinfo, 0, sizeof (sfinfo)) ;
 | |
| 	sfinfo.samplerate	= 44100 ;
 | |
| 	sfinfo.channels		= 2 ;
 | |
| 	sfinfo.frames		= 0 ;
 | |
| 	sfinfo.format		= typemajor | SF_FORMAT_PCM_16 ;
 | |
| 
 | |
| 	file = test_open_file_or_die (filename, SFM_WRITE, &sfinfo, SF_TRUE, __LINE__) ;
 | |
| 	test_write_short_or_die (file, 0, data_out, BUFFER_LEN, __LINE__) ;
 | |
| 	sf_set_string (file, SF_STR_TITLE, long_title) ;
 | |
| 	sf_close (file) ;
 | |
| 
 | |
| 
 | |
| 	/* Check that SFC_UPDATE_HEADER_NOW correctly calculates datalength. */
 | |
| 	file = test_open_file_or_die (filename, SFM_RDWR, &sfinfo, SF_TRUE, __LINE__) ;
 | |
| 	/* Write a very small amount of new audio data that doesn't completely overwrite the existing header. */
 | |
| 	test_write_short_or_die (file, 0, data_out, GROW_BUFFER_AMOUNT, __LINE__) ;
 | |
| 
 | |
| 	/* Update the header without closing the file. */
 | |
| 	sf_command (file, SFC_UPDATE_HEADER_NOW, NULL, 0) ;
 | |
| 
 | |
| 	/* The file should now contain BUFFER_LEN + GROW_BUFFER_AMOUNT frames.
 | |
| 		Open a second handle to the file and check the reported length. */
 | |
| 	memset (&sfinfo1, 0, sizeof (sfinfo1)) ;
 | |
| 	file1 = test_open_file_or_die (filename, SFM_READ, &sfinfo1, SF_TRUE, __LINE__) ;
 | |
| 
 | |
| 	frames = (BUFFER_LEN + GROW_BUFFER_AMOUNT) / sfinfo.channels ;
 | |
| 	exit_if_true (frames != sfinfo1.frames, "\n\nLine %d : Frame count %" PRId64 " should be %" PRId64 ".\n", __LINE__, sfinfo1.frames, frames) ;
 | |
| 
 | |
| 	/* The strings are probably not readable by the second soundfile handle because write_tailer has not yet been called.
 | |
| 		It's a design decision whether SFC_UPDATE_HEADER_NOW should write the tailer. I think it's fine that it doesn't.  */
 | |
| 
 | |
| 	sf_close (file1) ;
 | |
| 	sf_close (file) ;
 | |
| 
 | |
| 
 | |
| 	/* Check that sf_close correctly calculates datalength. */
 | |
| 	file = test_open_file_or_die (filename, SFM_RDWR, &sfinfo, SF_TRUE, __LINE__) ;
 | |
| 	/* Write a very small amount of new audio data that doesn't completely overwrite the existing header. */
 | |
| 	test_write_short_or_die (file, 0, data_out, GROW_BUFFER_AMOUNT, __LINE__) ;
 | |
| 	sf_close (file) ;
 | |
| 
 | |
| 
 | |
| 	/* Open file again and verify data and string. */
 | |
| 	file = test_open_file_or_die (filename, SFM_READ, &sfinfo, SF_TRUE, __LINE__) ;
 | |
| 	frames = (BUFFER_LEN + 2*GROW_BUFFER_AMOUNT) / sfinfo.channels ;
 | |
| 	exit_if_true (frames != sfinfo.frames, "\n\nLine %d : Frame count %" PRId64 " should be %" PRId64 ".\n", __LINE__, sfinfo.frames, frames) ;
 | |
| 	str = sf_get_string (file, SF_STR_TITLE) ;
 | |
| 	exit_if_true (str == NULL, "\n\nLine %d : SF_STR_TITLE string is NULL.\n", __LINE__) ;
 | |
| 	exit_if_true (strcmp (str, long_title) != 0, "\n\nLine %d : SF_STR_TITLE doesn't match what was written.\n", __LINE__) ;
 | |
| 	sf_close (file) ;
 | |
| 	unlink (filename) ;
 | |
| 	puts ("ok") ;
 | |
| } /* string_header_update */
 |