aplay.c (85605B)
1 /* 2 * aplay.c - plays and records 3 * 4 * CREATIVE LABS CHANNEL-files 5 * Microsoft WAVE-files 6 * SPARC AUDIO .AU-files 7 * Raw Data 8 * 9 * Copyright (c) by Jaroslav Kysela <perex@perex.cz> 10 * Based on vplay program by Michael Beck 11 * 12 * 13 * This program is free software; you can redistribute it and/or modify 14 * it under the terms of the GNU General Public License as published by 15 * the Free Software Foundation; either version 2 of the License, or 16 * (at your option) any later version. 17 * 18 * This program is distributed in the hope that it will be useful, 19 * but WITHOUT ANY WARRANTY; without even the implied warranty of 20 * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the 21 * GNU General Public License for more details. 22 * 23 * You should have received a copy of the GNU General Public License 24 * along with this program; if not, write to the Free Software 25 * Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA 26 * 27 */ 28 29 #define _GNU_SOURCE 30 #include <stdio.h> 31 #include <malloc.h> 32 #include <unistd.h> 33 #include <stdlib.h> 34 #include <string.h> 35 #include <getopt.h> 36 #include <fcntl.h> 37 #include <ctype.h> 38 #include <errno.h> 39 #include <limits.h> 40 #include <time.h> 41 #include <locale.h> 42 #include <alsa/asoundlib.h> 43 #include <assert.h> 44 #include <termios.h> 45 #include <signal.h> 46 #include <sys/poll.h> 47 #include <sys/uio.h> 48 #include <sys/time.h> 49 #include <sys/stat.h> 50 #include <sys/types.h> 51 #include <endian.h> 52 #include "aconfig.h" 53 #include "gettext.h" 54 #include "formats.h" 55 #include "version.h" 56 57 #ifdef SND_CHMAP_API_VERSION 58 #define CONFIG_SUPPORT_CHMAP 1 59 #endif 60 61 #ifndef LLONG_MAX 62 #define LLONG_MAX 9223372036854775807LL 63 #endif 64 65 #ifndef le16toh 66 #include <asm/byteorder.h> 67 #define le16toh(x) __le16_to_cpu(x) 68 #define be16toh(x) __be16_to_cpu(x) 69 #define le32toh(x) __le32_to_cpu(x) 70 #define be32toh(x) __be32_to_cpu(x) 71 #endif 72 73 #define DEFAULT_FORMAT SND_PCM_FORMAT_U8 74 #define DEFAULT_SPEED 8000 75 76 #define FORMAT_DEFAULT -1 77 #define FORMAT_RAW 0 78 #define FORMAT_VOC 1 79 #define FORMAT_WAVE 2 80 #define FORMAT_AU 3 81 82 /* global data */ 83 84 static snd_pcm_sframes_t (*readi_func)(snd_pcm_t *handle, void *buffer, snd_pcm_uframes_t size); 85 static snd_pcm_sframes_t (*writei_func)(snd_pcm_t *handle, const void *buffer, snd_pcm_uframes_t size); 86 static snd_pcm_sframes_t (*readn_func)(snd_pcm_t *handle, void **bufs, snd_pcm_uframes_t size); 87 static snd_pcm_sframes_t (*writen_func)(snd_pcm_t *handle, void **bufs, snd_pcm_uframes_t size); 88 89 enum { 90 VUMETER_NONE, 91 VUMETER_MONO, 92 VUMETER_STEREO 93 }; 94 95 static char *command; 96 static snd_pcm_t *handle; 97 static struct { 98 snd_pcm_format_t format; 99 unsigned int channels; 100 unsigned int rate; 101 } hwparams, rhwparams; 102 static int timelimit = 0; 103 static int quiet_mode = 0; 104 static int file_type = FORMAT_DEFAULT; 105 static int open_mode = 0; 106 static snd_pcm_stream_t stream = SND_PCM_STREAM_PLAYBACK; 107 static int mmap_flag = 0; 108 static int interleaved = 1; 109 static int nonblock = 0; 110 static volatile sig_atomic_t in_aborting = 0; 111 static u_char *audiobuf = NULL; 112 static snd_pcm_uframes_t chunk_size = 0; 113 static unsigned period_time = 0; 114 static unsigned buffer_time = 0; 115 static snd_pcm_uframes_t period_frames = 0; 116 static snd_pcm_uframes_t buffer_frames = 0; 117 static int avail_min = -1; 118 static int start_delay = 0; 119 static int stop_delay = 0; 120 static int monotonic = 0; 121 static int interactive = 0; 122 static int can_pause = 0; 123 static int fatal_errors = 0; 124 static int verbose = 0; 125 static int vumeter = VUMETER_NONE; 126 static int buffer_pos = 0; 127 static size_t significant_bits_per_sample, bits_per_sample, bits_per_frame; 128 static size_t chunk_bytes; 129 static int test_position = 0; 130 static int test_coef = 8; 131 static int test_nowait = 0; 132 static snd_output_t *log; 133 static long long max_file_size = 0; 134 static int max_file_time = 0; 135 static int use_strftime = 0; 136 volatile static int recycle_capture_file = 0; 137 static long term_c_lflag = -1; 138 static int dump_hw_params = 0; 139 140 static int fd = -1; 141 static off64_t pbrec_count = LLONG_MAX, fdcount; 142 static int vocmajor, vocminor; 143 144 static char *pidfile_name = NULL; 145 FILE *pidf = NULL; 146 static int pidfile_written = 0; 147 148 #ifdef CONFIG_SUPPORT_CHMAP 149 static snd_pcm_chmap_t *channel_map = NULL; /* chmap to override */ 150 static unsigned int *hw_map = NULL; /* chmap to follow */ 151 #endif 152 153 /* needed prototypes */ 154 155 static void done_stdin(void); 156 157 static void playback(char *filename); 158 static void capture(char *filename); 159 static void playbackv(char **filenames, unsigned int count); 160 static void capturev(char **filenames, unsigned int count); 161 162 static void begin_voc(int fd, size_t count); 163 static void end_voc(int fd); 164 static void begin_wave(int fd, size_t count); 165 static void end_wave(int fd); 166 static void begin_au(int fd, size_t count); 167 static void end_au(int fd); 168 169 static void suspend(void); 170 171 static const struct fmt_capture { 172 void (*start) (int fd, size_t count); 173 void (*end) (int fd); 174 char *what; 175 long long max_filesize; 176 } fmt_rec_table[] = { 177 { NULL, NULL, N_("raw data"), LLONG_MAX }, 178 { begin_voc, end_voc, N_("VOC"), 16000000LL }, 179 /* FIXME: can WAV handle exactly 2GB or less than it? */ 180 { begin_wave, end_wave, N_("WAVE"), 2147483648LL }, 181 { begin_au, end_au, N_("Sparc Audio"), LLONG_MAX } 182 }; 183 184 #if __GNUC__ > 2 || (__GNUC__ == 2 && __GNUC_MINOR__ >= 95) 185 #define error(...) do {\ 186 fprintf(stderr, "%s: %s:%d: ", command, __FUNCTION__, __LINE__); \ 187 fprintf(stderr, __VA_ARGS__); \ 188 putc('\n', stderr); \ 189 } while (0) 190 #else 191 #define error(args...) do {\ 192 fprintf(stderr, "%s: %s:%d: ", command, __FUNCTION__, __LINE__); \ 193 fprintf(stderr, ##args); \ 194 putc('\n', stderr); \ 195 } while (0) 196 #endif 197 198 static void usage(char *command) 199 { 200 snd_pcm_format_t k; 201 printf( 202 _("Usage: %s [OPTION]... [FILE]...\n" 203 "\n" 204 "-h, --help help\n" 205 " --version print current version\n" 206 "-l, --list-devices list all soundcards and digital audio devices\n" 207 "-L, --list-pcms list device names\n" 208 "-D, --device=NAME select PCM by name\n" 209 "-q, --quiet quiet mode\n" 210 "-t, --file-type TYPE file type (voc, wav, raw or au)\n" 211 "-c, --channels=# channels\n" 212 "-f, --format=FORMAT sample format (case insensitive)\n" 213 "-r, --rate=# sample rate\n" 214 "-d, --duration=# interrupt after # seconds\n" 215 "-M, --mmap mmap stream\n" 216 "-N, --nonblock nonblocking mode\n" 217 "-F, --period-time=# distance between interrupts is # microseconds\n" 218 "-B, --buffer-time=# buffer duration is # microseconds\n" 219 " --period-size=# distance between interrupts is # frames\n" 220 " --buffer-size=# buffer duration is # frames\n" 221 "-A, --avail-min=# min available space for wakeup is # microseconds\n" 222 "-R, --start-delay=# delay for automatic PCM start is # microseconds \n" 223 " (relative to buffer size if <= 0)\n" 224 "-T, --stop-delay=# delay for automatic PCM stop is # microseconds from xrun\n" 225 "-v, --verbose show PCM structure and setup (accumulative)\n" 226 "-V, --vumeter=TYPE enable VU meter (TYPE: mono or stereo)\n" 227 "-I, --separate-channels one file for each channel\n" 228 "-i, --interactive allow interactive operation from stdin\n" 229 "-m, --chmap=ch1,ch2,.. Give the channel map to override or follow\n" 230 " --disable-resample disable automatic rate resample\n" 231 " --disable-channels disable automatic channel conversions\n" 232 " --disable-format disable automatic format conversions\n" 233 " --disable-softvol disable software volume control (softvol)\n" 234 " --test-position test ring buffer position\n" 235 " --test-coef=# test coefficient for ring buffer position (default 8)\n" 236 " expression for validation is: coef * (buffer_size / 2)\n" 237 " --test-nowait do not wait for ring buffer - eats whole CPU\n" 238 " --max-file-time=# start another output file when the old file has recorded\n" 239 " for this many seconds\n" 240 " --process-id-file write the process ID here\n" 241 " --use-strftime apply the strftime facility to the output file name\n" 242 " --dump-hw-params dump hw_params of the device\n" 243 " --fatal-errors treat all errors as fatal\n" 244 ) 245 , command); 246 printf(_("Recognized sample formats are:")); 247 for (k = 0; k <= SND_PCM_FORMAT_LAST; ++k) { 248 const char *s = snd_pcm_format_name(k); 249 if (s) 250 printf(" %s", s); 251 } 252 printf(_("\nSome of these may not be available on selected hardware\n")); 253 printf(_("The available format shortcuts are:\n")); 254 printf(_("-f cd (16 bit little endian, 44100, stereo)\n")); 255 printf(_("-f cdr (16 bit big endian, 44100, stereo)\n")); 256 printf(_("-f dat (16 bit little endian, 48000, stereo)\n")); 257 } 258 259 static void device_list(void) 260 { 261 snd_ctl_t *handle; 262 int card, err, dev, idx; 263 snd_ctl_card_info_t *info; 264 snd_pcm_info_t *pcminfo; 265 snd_ctl_card_info_alloca(&info); 266 snd_pcm_info_alloca(&pcminfo); 267 268 card = -1; 269 if (snd_card_next(&card) < 0 || card < 0) { 270 error(_("no soundcards found...")); 271 return; 272 } 273 printf(_("**** List of %s Hardware Devices ****\n"), 274 snd_pcm_stream_name(stream)); 275 while (card >= 0) { 276 char name[32]; 277 sprintf(name, "hw:%d", card); 278 if ((err = snd_ctl_open(&handle, name, 0)) < 0) { 279 error("control open (%i): %s", card, snd_strerror(err)); 280 goto next_card; 281 } 282 if ((err = snd_ctl_card_info(handle, info)) < 0) { 283 error("control hardware info (%i): %s", card, snd_strerror(err)); 284 snd_ctl_close(handle); 285 goto next_card; 286 } 287 dev = -1; 288 while (1) { 289 unsigned int count; 290 if (snd_ctl_pcm_next_device(handle, &dev)<0) 291 error("snd_ctl_pcm_next_device"); 292 if (dev < 0) 293 break; 294 snd_pcm_info_set_device(pcminfo, dev); 295 snd_pcm_info_set_subdevice(pcminfo, 0); 296 snd_pcm_info_set_stream(pcminfo, stream); 297 if ((err = snd_ctl_pcm_info(handle, pcminfo)) < 0) { 298 if (err != -ENOENT) 299 error("control digital audio info (%i): %s", card, snd_strerror(err)); 300 continue; 301 } 302 printf(_("card %i: %s [%s], device %i: %s [%s]\n"), 303 card, snd_ctl_card_info_get_id(info), snd_ctl_card_info_get_name(info), 304 dev, 305 snd_pcm_info_get_id(pcminfo), 306 snd_pcm_info_get_name(pcminfo)); 307 count = snd_pcm_info_get_subdevices_count(pcminfo); 308 printf( _(" Subdevices: %i/%i\n"), 309 snd_pcm_info_get_subdevices_avail(pcminfo), count); 310 for (idx = 0; idx < (int)count; idx++) { 311 snd_pcm_info_set_subdevice(pcminfo, idx); 312 if ((err = snd_ctl_pcm_info(handle, pcminfo)) < 0) { 313 error("control digital audio playback info (%i): %s", card, snd_strerror(err)); 314 } else { 315 printf(_(" Subdevice #%i: %s\n"), 316 idx, snd_pcm_info_get_subdevice_name(pcminfo)); 317 } 318 } 319 } 320 snd_ctl_close(handle); 321 next_card: 322 if (snd_card_next(&card) < 0) { 323 error("snd_card_next"); 324 break; 325 } 326 } 327 } 328 329 static void pcm_list(void) 330 { 331 void **hints, **n; 332 char *name, *descr, *descr1, *io; 333 const char *filter; 334 335 if (snd_device_name_hint(-1, "pcm", &hints) < 0) 336 return; 337 n = hints; 338 filter = stream == SND_PCM_STREAM_CAPTURE ? "Input" : "Output"; 339 while (*n != NULL) { 340 name = snd_device_name_get_hint(*n, "NAME"); 341 descr = snd_device_name_get_hint(*n, "DESC"); 342 io = snd_device_name_get_hint(*n, "IOID"); 343 if (io != NULL && strcmp(io, filter) != 0) 344 goto __end; 345 printf("%s\n", name); 346 if ((descr1 = descr) != NULL) { 347 printf(" "); 348 while (*descr1) { 349 if (*descr1 == '\n') 350 printf("\n "); 351 else 352 putchar(*descr1); 353 descr1++; 354 } 355 putchar('\n'); 356 } 357 __end: 358 if (name != NULL) 359 free(name); 360 if (descr != NULL) 361 free(descr); 362 if (io != NULL) 363 free(io); 364 n++; 365 } 366 snd_device_name_free_hint(hints); 367 } 368 369 static void version(void) 370 { 371 printf("%s: version " SND_UTIL_VERSION_STR " by Jaroslav Kysela <perex@perex.cz>\n", command); 372 } 373 374 /* 375 * Subroutine to clean up before exit. 376 */ 377 static void prg_exit(int code) 378 { 379 done_stdin(); 380 if (handle) 381 snd_pcm_close(handle); 382 if (pidfile_written) 383 remove (pidfile_name); 384 exit(code); 385 } 386 387 static void signal_handler(int sig) 388 { 389 if (in_aborting) 390 return; 391 392 in_aborting = 1; 393 if (verbose==2) 394 putchar('\n'); 395 if (!quiet_mode) 396 fprintf(stderr, _("Aborted by signal %s...\n"), strsignal(sig)); 397 if (handle) 398 snd_pcm_abort(handle); 399 if (sig == SIGABRT) { 400 /* do not call snd_pcm_close() and abort immediately */ 401 handle = NULL; 402 prg_exit(EXIT_FAILURE); 403 } 404 signal(sig, SIG_DFL); 405 } 406 407 /* call on SIGUSR1 signal. */ 408 static void signal_handler_recycle (int sig) 409 { 410 /* flag the capture loop to start a new output file */ 411 recycle_capture_file = 1; 412 } 413 414 enum { 415 OPT_VERSION = 1, 416 OPT_PERIOD_SIZE, 417 OPT_BUFFER_SIZE, 418 OPT_DISABLE_RESAMPLE, 419 OPT_DISABLE_CHANNELS, 420 OPT_DISABLE_FORMAT, 421 OPT_DISABLE_SOFTVOL, 422 OPT_TEST_POSITION, 423 OPT_TEST_COEF, 424 OPT_TEST_NOWAIT, 425 OPT_MAX_FILE_TIME, 426 OPT_PROCESS_ID_FILE, 427 OPT_USE_STRFTIME, 428 OPT_DUMP_HWPARAMS, 429 OPT_FATAL_ERRORS, 430 }; 431 432 static long parse_long(const char *str, int *err) 433 { 434 long val; 435 char *endptr; 436 437 errno = 0; 438 val = strtol(str, &endptr, 0); 439 440 if (errno != 0 || *endptr != '\0') 441 *err = -1; 442 else 443 *err = 0; 444 445 return val; 446 } 447 448 int main(int argc, char *argv[]) 449 { 450 int option_index; 451 static const char short_options[] = "hnlLD:qt:c:f:r:d:MNF:A:R:T:B:vV:IPCi" 452 #ifdef CONFIG_SUPPORT_CHMAP 453 "m:" 454 #endif 455 ; 456 static const struct option long_options[] = { 457 {"help", 0, 0, 'h'}, 458 {"version", 0, 0, OPT_VERSION}, 459 {"list-devnames", 0, 0, 'n'}, 460 {"list-devices", 0, 0, 'l'}, 461 {"list-pcms", 0, 0, 'L'}, 462 {"device", 1, 0, 'D'}, 463 {"quiet", 0, 0, 'q'}, 464 {"file-type", 1, 0, 't'}, 465 {"channels", 1, 0, 'c'}, 466 {"format", 1, 0, 'f'}, 467 {"rate", 1, 0, 'r'}, 468 {"duration", 1, 0 ,'d'}, 469 {"mmap", 0, 0, 'M'}, 470 {"nonblock", 0, 0, 'N'}, 471 {"period-time", 1, 0, 'F'}, 472 {"period-size", 1, 0, OPT_PERIOD_SIZE}, 473 {"avail-min", 1, 0, 'A'}, 474 {"start-delay", 1, 0, 'R'}, 475 {"stop-delay", 1, 0, 'T'}, 476 {"buffer-time", 1, 0, 'B'}, 477 {"buffer-size", 1, 0, OPT_BUFFER_SIZE}, 478 {"verbose", 0, 0, 'v'}, 479 {"vumeter", 1, 0, 'V'}, 480 {"separate-channels", 0, 0, 'I'}, 481 {"playback", 0, 0, 'P'}, 482 {"capture", 0, 0, 'C'}, 483 {"disable-resample", 0, 0, OPT_DISABLE_RESAMPLE}, 484 {"disable-channels", 0, 0, OPT_DISABLE_CHANNELS}, 485 {"disable-format", 0, 0, OPT_DISABLE_FORMAT}, 486 {"disable-softvol", 0, 0, OPT_DISABLE_SOFTVOL}, 487 {"test-position", 0, 0, OPT_TEST_POSITION}, 488 {"test-coef", 1, 0, OPT_TEST_COEF}, 489 {"test-nowait", 0, 0, OPT_TEST_NOWAIT}, 490 {"max-file-time", 1, 0, OPT_MAX_FILE_TIME}, 491 {"process-id-file", 1, 0, OPT_PROCESS_ID_FILE}, 492 {"use-strftime", 0, 0, OPT_USE_STRFTIME}, 493 {"interactive", 0, 0, 'i'}, 494 {"dump-hw-params", 0, 0, OPT_DUMP_HWPARAMS}, 495 {"fatal-errors", 0, 0, OPT_FATAL_ERRORS}, 496 #ifdef CONFIG_SUPPORT_CHMAP 497 {"chmap", 1, 0, 'm'}, 498 #endif 499 {0, 0, 0, 0} 500 }; 501 char *pcm_name = "default"; 502 int tmp, err, c; 503 int do_device_list = 0, do_pcm_list = 0; 504 snd_pcm_info_t *info; 505 FILE *direction; 506 507 #ifdef ENABLE_NLS 508 setlocale(LC_ALL, ""); 509 textdomain(PACKAGE); 510 #endif 511 512 snd_pcm_info_alloca(&info); 513 514 err = snd_output_stdio_attach(&log, stderr, 0); 515 assert(err >= 0); 516 517 command = argv[0]; 518 file_type = FORMAT_DEFAULT; 519 if (strstr(argv[0], "arecord")) { 520 stream = SND_PCM_STREAM_CAPTURE; 521 file_type = FORMAT_WAVE; 522 command = "arecord"; 523 start_delay = 1; 524 direction = stdout; 525 } else if (strstr(argv[0], "aplay")) { 526 stream = SND_PCM_STREAM_PLAYBACK; 527 command = "aplay"; 528 direction = stdin; 529 } else { 530 error(_("command should be named either arecord or aplay")); 531 return 1; 532 } 533 534 if (isatty(fileno(direction)) && (argc == 1)) { 535 usage(command); 536 return 1; 537 } 538 539 chunk_size = -1; 540 rhwparams.format = DEFAULT_FORMAT; 541 rhwparams.rate = DEFAULT_SPEED; 542 rhwparams.channels = 1; 543 544 while ((c = getopt_long(argc, argv, short_options, long_options, &option_index)) != -1) { 545 switch (c) { 546 case 'h': 547 usage(command); 548 return 0; 549 case OPT_VERSION: 550 version(); 551 return 0; 552 case 'l': 553 do_device_list = 1; 554 break; 555 case 'L': 556 do_pcm_list = 1; 557 break; 558 case 'D': 559 pcm_name = optarg; 560 break; 561 case 'q': 562 quiet_mode = 1; 563 break; 564 case 't': 565 if (strcasecmp(optarg, "raw") == 0) 566 file_type = FORMAT_RAW; 567 else if (strcasecmp(optarg, "voc") == 0) 568 file_type = FORMAT_VOC; 569 else if (strcasecmp(optarg, "wav") == 0) 570 file_type = FORMAT_WAVE; 571 else if (strcasecmp(optarg, "au") == 0 || strcasecmp(optarg, "sparc") == 0) 572 file_type = FORMAT_AU; 573 else { 574 error(_("unrecognized file format %s"), optarg); 575 return 1; 576 } 577 break; 578 case 'c': 579 rhwparams.channels = parse_long(optarg, &err); 580 if (err < 0) { 581 error(_("invalid channels argument '%s'"), optarg); 582 return 1; 583 } 584 if (rhwparams.channels < 1 || rhwparams.channels > 256) { 585 error(_("value %i for channels is invalid"), rhwparams.channels); 586 return 1; 587 } 588 break; 589 case 'f': 590 if (strcasecmp(optarg, "cd") == 0 || strcasecmp(optarg, "cdr") == 0) { 591 if (strcasecmp(optarg, "cdr") == 0) 592 rhwparams.format = SND_PCM_FORMAT_S16_BE; 593 else 594 rhwparams.format = file_type == FORMAT_AU ? SND_PCM_FORMAT_S16_BE : SND_PCM_FORMAT_S16_LE; 595 rhwparams.rate = 44100; 596 rhwparams.channels = 2; 597 } else if (strcasecmp(optarg, "dat") == 0) { 598 rhwparams.format = file_type == FORMAT_AU ? SND_PCM_FORMAT_S16_BE : SND_PCM_FORMAT_S16_LE; 599 rhwparams.rate = 48000; 600 rhwparams.channels = 2; 601 } else { 602 rhwparams.format = snd_pcm_format_value(optarg); 603 if (rhwparams.format == SND_PCM_FORMAT_UNKNOWN) { 604 error(_("wrong extended format '%s'"), optarg); 605 prg_exit(EXIT_FAILURE); 606 } 607 } 608 break; 609 case 'r': 610 tmp = parse_long(optarg, &err); 611 if (err < 0) { 612 error(_("invalid rate argument '%s'"), optarg); 613 return 1; 614 } 615 if (tmp < 300) 616 tmp *= 1000; 617 rhwparams.rate = tmp; 618 if (tmp < 2000 || tmp > 192000) { 619 error(_("bad speed value %i"), tmp); 620 return 1; 621 } 622 break; 623 case 'd': 624 timelimit = parse_long(optarg, &err); 625 if (err < 0) { 626 error(_("invalid duration argument '%s'"), optarg); 627 return 1; 628 } 629 break; 630 case 'N': 631 nonblock = 1; 632 open_mode |= SND_PCM_NONBLOCK; 633 break; 634 case 'F': 635 period_time = parse_long(optarg, &err); 636 if (err < 0) { 637 error(_("invalid period time argument '%s'"), optarg); 638 return 1; 639 } 640 break; 641 case 'B': 642 buffer_time = parse_long(optarg, &err); 643 if (err < 0) { 644 error(_("invalid buffer time argument '%s'"), optarg); 645 return 1; 646 } 647 break; 648 case OPT_PERIOD_SIZE: 649 period_frames = parse_long(optarg, &err); 650 if (err < 0) { 651 error(_("invalid period size argument '%s'"), optarg); 652 return 1; 653 } 654 break; 655 case OPT_BUFFER_SIZE: 656 buffer_frames = parse_long(optarg, &err); 657 if (err < 0) { 658 error(_("invalid buffer size argument '%s'"), optarg); 659 return 1; 660 } 661 break; 662 case 'A': 663 avail_min = parse_long(optarg, &err); 664 if (err < 0) { 665 error(_("invalid min available space argument '%s'"), optarg); 666 return 1; 667 } 668 break; 669 case 'R': 670 start_delay = parse_long(optarg, &err); 671 if (err < 0) { 672 error(_("invalid start delay argument '%s'"), optarg); 673 return 1; 674 } 675 break; 676 case 'T': 677 stop_delay = parse_long(optarg, &err); 678 if (err < 0) { 679 error(_("invalid stop delay argument '%s'"), optarg); 680 return 1; 681 } 682 break; 683 case 'v': 684 verbose++; 685 if (verbose > 1 && !vumeter) 686 vumeter = VUMETER_MONO; 687 break; 688 case 'V': 689 if (*optarg == 's') 690 vumeter = VUMETER_STEREO; 691 else if (*optarg == 'm') 692 vumeter = VUMETER_MONO; 693 else 694 vumeter = VUMETER_NONE; 695 break; 696 case 'M': 697 mmap_flag = 1; 698 break; 699 case 'I': 700 interleaved = 0; 701 break; 702 case 'P': 703 stream = SND_PCM_STREAM_PLAYBACK; 704 command = "aplay"; 705 break; 706 case 'C': 707 stream = SND_PCM_STREAM_CAPTURE; 708 command = "arecord"; 709 start_delay = 1; 710 if (file_type == FORMAT_DEFAULT) 711 file_type = FORMAT_WAVE; 712 break; 713 case 'i': 714 interactive = 1; 715 break; 716 case OPT_DISABLE_RESAMPLE: 717 open_mode |= SND_PCM_NO_AUTO_RESAMPLE; 718 break; 719 case OPT_DISABLE_CHANNELS: 720 open_mode |= SND_PCM_NO_AUTO_CHANNELS; 721 break; 722 case OPT_DISABLE_FORMAT: 723 open_mode |= SND_PCM_NO_AUTO_FORMAT; 724 break; 725 case OPT_DISABLE_SOFTVOL: 726 open_mode |= SND_PCM_NO_SOFTVOL; 727 break; 728 case OPT_TEST_POSITION: 729 test_position = 1; 730 break; 731 case OPT_TEST_COEF: 732 test_coef = parse_long(optarg, &err); 733 if (err < 0) { 734 error(_("invalid test coef argument '%s'"), optarg); 735 return 1; 736 } 737 if (test_coef < 1) 738 test_coef = 1; 739 break; 740 case OPT_TEST_NOWAIT: 741 test_nowait = 1; 742 break; 743 case OPT_MAX_FILE_TIME: 744 max_file_time = parse_long(optarg, &err); 745 if (err < 0) { 746 error(_("invalid max file time argument '%s'"), optarg); 747 return 1; 748 } 749 break; 750 case OPT_PROCESS_ID_FILE: 751 pidfile_name = optarg; 752 break; 753 case OPT_USE_STRFTIME: 754 use_strftime = 1; 755 break; 756 case OPT_DUMP_HWPARAMS: 757 dump_hw_params = 1; 758 break; 759 case OPT_FATAL_ERRORS: 760 fatal_errors = 1; 761 break; 762 #ifdef CONFIG_SUPPORT_CHMAP 763 case 'm': 764 channel_map = snd_pcm_chmap_parse_string(optarg); 765 if (!channel_map) { 766 fprintf(stderr, _("Unable to parse channel map string: %s\n"), optarg); 767 return 1; 768 } 769 break; 770 #endif 771 default: 772 fprintf(stderr, _("Try `%s --help' for more information.\n"), command); 773 return 1; 774 } 775 } 776 777 if (do_device_list) { 778 if (do_pcm_list) pcm_list(); 779 device_list(); 780 goto __end; 781 } else if (do_pcm_list) { 782 pcm_list(); 783 goto __end; 784 } 785 786 err = snd_pcm_open(&handle, pcm_name, stream, open_mode); 787 if (err < 0) { 788 error(_("audio open error: %s"), snd_strerror(err)); 789 return 1; 790 } 791 792 if ((err = snd_pcm_info(handle, info)) < 0) { 793 error(_("info error: %s"), snd_strerror(err)); 794 return 1; 795 } 796 797 if (nonblock) { 798 err = snd_pcm_nonblock(handle, 1); 799 if (err < 0) { 800 error(_("nonblock setting error: %s"), snd_strerror(err)); 801 return 1; 802 } 803 } 804 805 chunk_size = 1024; 806 hwparams = rhwparams; 807 808 audiobuf = (u_char *)malloc(1024); 809 if (audiobuf == NULL) { 810 error(_("not enough memory")); 811 return 1; 812 } 813 814 if (mmap_flag) { 815 writei_func = snd_pcm_mmap_writei; 816 readi_func = snd_pcm_mmap_readi; 817 writen_func = snd_pcm_mmap_writen; 818 readn_func = snd_pcm_mmap_readn; 819 } else { 820 writei_func = snd_pcm_writei; 821 readi_func = snd_pcm_readi; 822 writen_func = snd_pcm_writen; 823 readn_func = snd_pcm_readn; 824 } 825 826 if (pidfile_name) { 827 errno = 0; 828 pidf = fopen (pidfile_name, "w"); 829 if (pidf) { 830 (void)fprintf (pidf, "%d\n", getpid()); 831 fclose(pidf); 832 pidfile_written = 1; 833 } else { 834 error(_("Cannot create process ID file %s: %s"), 835 pidfile_name, strerror (errno)); 836 return 1; 837 } 838 } 839 840 signal(SIGINT, signal_handler); 841 signal(SIGTERM, signal_handler); 842 signal(SIGABRT, signal_handler); 843 signal(SIGUSR1, signal_handler_recycle); 844 if (interleaved) { 845 if (optind > argc - 1) { 846 if (stream == SND_PCM_STREAM_PLAYBACK) 847 playback(NULL); 848 else 849 capture(NULL); 850 } else { 851 while (optind <= argc - 1) { 852 if (stream == SND_PCM_STREAM_PLAYBACK) 853 playback(argv[optind++]); 854 else 855 capture(argv[optind++]); 856 } 857 } 858 } else { 859 if (stream == SND_PCM_STREAM_PLAYBACK) 860 playbackv(&argv[optind], argc - optind); 861 else 862 capturev(&argv[optind], argc - optind); 863 } 864 if (verbose==2) 865 putchar('\n'); 866 snd_pcm_close(handle); 867 handle = NULL; 868 free(audiobuf); 869 __end: 870 snd_output_close(log); 871 snd_config_update_free_global(); 872 prg_exit(EXIT_SUCCESS); 873 /* avoid warning */ 874 return EXIT_SUCCESS; 875 } 876 877 /* 878 * Safe read (for pipes) 879 */ 880 881 static ssize_t safe_read(int fd, void *buf, size_t count) 882 { 883 ssize_t result = 0, res; 884 885 while (count > 0 && !in_aborting) { 886 if ((res = read(fd, buf, count)) == 0) 887 break; 888 if (res < 0) 889 return result > 0 ? result : res; 890 count -= res; 891 result += res; 892 buf = (char *)buf + res; 893 } 894 return result; 895 } 896 897 /* 898 * Test, if it is a .VOC file and return >=0 if ok (this is the length of rest) 899 * < 0 if not 900 */ 901 static int test_vocfile(void *buffer) 902 { 903 VocHeader *vp = buffer; 904 905 if (!memcmp(vp->magic, VOC_MAGIC_STRING, 20)) { 906 vocminor = LE_SHORT(vp->version) & 0xFF; 907 vocmajor = LE_SHORT(vp->version) / 256; 908 if (LE_SHORT(vp->version) != (0x1233 - LE_SHORT(vp->coded_ver))) 909 return -2; /* coded version mismatch */ 910 return LE_SHORT(vp->headerlen) - sizeof(VocHeader); /* 0 mostly */ 911 } 912 return -1; /* magic string fail */ 913 } 914 915 /* 916 * helper for test_wavefile 917 */ 918 919 static size_t test_wavefile_read(int fd, u_char *buffer, size_t *size, size_t reqsize, int line) 920 { 921 if (*size >= reqsize) 922 return *size; 923 if ((size_t)safe_read(fd, buffer + *size, reqsize - *size) != reqsize - *size) { 924 error(_("read error (called from line %i)"), line); 925 prg_exit(EXIT_FAILURE); 926 } 927 return *size = reqsize; 928 } 929 930 #define check_wavefile_space(buffer, len, blimit) \ 931 if (len > blimit) { \ 932 blimit = len; \ 933 if ((buffer = realloc(buffer, blimit)) == NULL) { \ 934 error(_("not enough memory")); \ 935 prg_exit(EXIT_FAILURE); \ 936 } \ 937 } 938 939 /* 940 * test, if it's a .WAV file, > 0 if ok (and set the speed, stereo etc.) 941 * == 0 if not 942 * Value returned is bytes to be discarded. 943 */ 944 static ssize_t test_wavefile(int fd, u_char *_buffer, size_t size) 945 { 946 WaveHeader *h = (WaveHeader *)_buffer; 947 u_char *buffer = NULL; 948 size_t blimit = 0; 949 WaveFmtBody *f; 950 WaveChunkHeader *c; 951 u_int type, len; 952 unsigned short format, channels; 953 int big_endian, native_format; 954 955 if (size < sizeof(WaveHeader)) 956 return -1; 957 if (h->magic == WAV_RIFF) 958 big_endian = 0; 959 else if (h->magic == WAV_RIFX) 960 big_endian = 1; 961 else 962 return -1; 963 if (h->type != WAV_WAVE) 964 return -1; 965 966 if (size > sizeof(WaveHeader)) { 967 check_wavefile_space(buffer, size - sizeof(WaveHeader), blimit); 968 memcpy(buffer, _buffer + sizeof(WaveHeader), size - sizeof(WaveHeader)); 969 } 970 size -= sizeof(WaveHeader); 971 while (1) { 972 check_wavefile_space(buffer, sizeof(WaveChunkHeader), blimit); 973 test_wavefile_read(fd, buffer, &size, sizeof(WaveChunkHeader), __LINE__); 974 c = (WaveChunkHeader*)buffer; 975 type = c->type; 976 len = TO_CPU_INT(c->length, big_endian); 977 len += len % 2; 978 if (size > sizeof(WaveChunkHeader)) 979 memmove(buffer, buffer + sizeof(WaveChunkHeader), size - sizeof(WaveChunkHeader)); 980 size -= sizeof(WaveChunkHeader); 981 if (type == WAV_FMT) 982 break; 983 check_wavefile_space(buffer, len, blimit); 984 test_wavefile_read(fd, buffer, &size, len, __LINE__); 985 if (size > len) 986 memmove(buffer, buffer + len, size - len); 987 size -= len; 988 } 989 990 if (len < sizeof(WaveFmtBody)) { 991 error(_("unknown length of 'fmt ' chunk (read %u, should be %u at least)"), 992 len, (u_int)sizeof(WaveFmtBody)); 993 prg_exit(EXIT_FAILURE); 994 } 995 check_wavefile_space(buffer, len, blimit); 996 test_wavefile_read(fd, buffer, &size, len, __LINE__); 997 f = (WaveFmtBody*) buffer; 998 format = TO_CPU_SHORT(f->format, big_endian); 999 if (format == WAV_FMT_EXTENSIBLE) { 1000 WaveFmtExtensibleBody *fe = (WaveFmtExtensibleBody*)buffer; 1001 if (len < sizeof(WaveFmtExtensibleBody)) { 1002 error(_("unknown length of extensible 'fmt ' chunk (read %u, should be %u at least)"), 1003 len, (u_int)sizeof(WaveFmtExtensibleBody)); 1004 prg_exit(EXIT_FAILURE); 1005 } 1006 if (memcmp(fe->guid_tag, WAV_GUID_TAG, 14) != 0) { 1007 error(_("wrong format tag in extensible 'fmt ' chunk")); 1008 prg_exit(EXIT_FAILURE); 1009 } 1010 format = TO_CPU_SHORT(fe->guid_format, big_endian); 1011 } 1012 if (format != WAV_FMT_PCM && 1013 format != WAV_FMT_IEEE_FLOAT) { 1014 error(_("can't play WAVE-file format 0x%04x which is not PCM or FLOAT encoded"), format); 1015 prg_exit(EXIT_FAILURE); 1016 } 1017 channels = TO_CPU_SHORT(f->channels, big_endian); 1018 if (channels < 1) { 1019 error(_("can't play WAVE-files with %d tracks"), channels); 1020 prg_exit(EXIT_FAILURE); 1021 } 1022 hwparams.channels = channels; 1023 switch (TO_CPU_SHORT(f->bit_p_spl, big_endian)) { 1024 case 8: 1025 if (hwparams.format != DEFAULT_FORMAT && 1026 hwparams.format != SND_PCM_FORMAT_U8) 1027 fprintf(stderr, _("Warning: format is changed to U8\n")); 1028 hwparams.format = SND_PCM_FORMAT_U8; 1029 break; 1030 case 16: 1031 if (big_endian) 1032 native_format = SND_PCM_FORMAT_S16_BE; 1033 else 1034 native_format = SND_PCM_FORMAT_S16_LE; 1035 if (hwparams.format != DEFAULT_FORMAT && 1036 hwparams.format != native_format) 1037 fprintf(stderr, _("Warning: format is changed to %s\n"), 1038 snd_pcm_format_name(native_format)); 1039 hwparams.format = native_format; 1040 break; 1041 case 24: 1042 switch (TO_CPU_SHORT(f->byte_p_spl, big_endian) / hwparams.channels) { 1043 case 3: 1044 if (big_endian) 1045 native_format = SND_PCM_FORMAT_S24_3BE; 1046 else 1047 native_format = SND_PCM_FORMAT_S24_3LE; 1048 if (hwparams.format != DEFAULT_FORMAT && 1049 hwparams.format != native_format) 1050 fprintf(stderr, _("Warning: format is changed to %s\n"), 1051 snd_pcm_format_name(native_format)); 1052 hwparams.format = native_format; 1053 break; 1054 case 4: 1055 if (big_endian) 1056 native_format = SND_PCM_FORMAT_S24_BE; 1057 else 1058 native_format = SND_PCM_FORMAT_S24_LE; 1059 if (hwparams.format != DEFAULT_FORMAT && 1060 hwparams.format != native_format) 1061 fprintf(stderr, _("Warning: format is changed to %s\n"), 1062 snd_pcm_format_name(native_format)); 1063 hwparams.format = native_format; 1064 break; 1065 default: 1066 error(_(" can't play WAVE-files with sample %d bits in %d bytes wide (%d channels)"), 1067 TO_CPU_SHORT(f->bit_p_spl, big_endian), 1068 TO_CPU_SHORT(f->byte_p_spl, big_endian), 1069 hwparams.channels); 1070 prg_exit(EXIT_FAILURE); 1071 } 1072 break; 1073 case 32: 1074 if (format == WAV_FMT_PCM) { 1075 if (big_endian) 1076 native_format = SND_PCM_FORMAT_S32_BE; 1077 else 1078 native_format = SND_PCM_FORMAT_S32_LE; 1079 hwparams.format = native_format; 1080 } else if (format == WAV_FMT_IEEE_FLOAT) { 1081 if (big_endian) 1082 native_format = SND_PCM_FORMAT_FLOAT_BE; 1083 else 1084 native_format = SND_PCM_FORMAT_FLOAT_LE; 1085 hwparams.format = native_format; 1086 } 1087 break; 1088 default: 1089 error(_(" can't play WAVE-files with sample %d bits wide"), 1090 TO_CPU_SHORT(f->bit_p_spl, big_endian)); 1091 prg_exit(EXIT_FAILURE); 1092 } 1093 hwparams.rate = TO_CPU_INT(f->sample_fq, big_endian); 1094 1095 if (size > len) 1096 memmove(buffer, buffer + len, size - len); 1097 size -= len; 1098 1099 while (1) { 1100 u_int type, len; 1101 1102 check_wavefile_space(buffer, sizeof(WaveChunkHeader), blimit); 1103 test_wavefile_read(fd, buffer, &size, sizeof(WaveChunkHeader), __LINE__); 1104 c = (WaveChunkHeader*)buffer; 1105 type = c->type; 1106 len = TO_CPU_INT(c->length, big_endian); 1107 if (size > sizeof(WaveChunkHeader)) 1108 memmove(buffer, buffer + sizeof(WaveChunkHeader), size - sizeof(WaveChunkHeader)); 1109 size -= sizeof(WaveChunkHeader); 1110 if (type == WAV_DATA) { 1111 if (len < pbrec_count && len < 0x7ffffffe) 1112 pbrec_count = len; 1113 if (size > 0) 1114 memcpy(_buffer, buffer, size); 1115 free(buffer); 1116 return size; 1117 } 1118 len += len % 2; 1119 check_wavefile_space(buffer, len, blimit); 1120 test_wavefile_read(fd, buffer, &size, len, __LINE__); 1121 if (size > len) 1122 memmove(buffer, buffer + len, size - len); 1123 size -= len; 1124 } 1125 1126 /* shouldn't be reached */ 1127 return -1; 1128 } 1129 1130 /* 1131 1132 */ 1133 1134 static int test_au(int fd, void *buffer) 1135 { 1136 AuHeader *ap = buffer; 1137 1138 if (ap->magic != AU_MAGIC) 1139 return -1; 1140 if (BE_INT(ap->hdr_size) > 128 || BE_INT(ap->hdr_size) < 24) 1141 return -1; 1142 pbrec_count = BE_INT(ap->data_size); 1143 switch (BE_INT(ap->encoding)) { 1144 case AU_FMT_ULAW: 1145 if (hwparams.format != DEFAULT_FORMAT && 1146 hwparams.format != SND_PCM_FORMAT_MU_LAW) 1147 fprintf(stderr, _("Warning: format is changed to MU_LAW\n")); 1148 hwparams.format = SND_PCM_FORMAT_MU_LAW; 1149 break; 1150 case AU_FMT_LIN8: 1151 if (hwparams.format != DEFAULT_FORMAT && 1152 hwparams.format != SND_PCM_FORMAT_U8) 1153 fprintf(stderr, _("Warning: format is changed to U8\n")); 1154 hwparams.format = SND_PCM_FORMAT_U8; 1155 break; 1156 case AU_FMT_LIN16: 1157 if (hwparams.format != DEFAULT_FORMAT && 1158 hwparams.format != SND_PCM_FORMAT_S16_BE) 1159 fprintf(stderr, _("Warning: format is changed to S16_BE\n")); 1160 hwparams.format = SND_PCM_FORMAT_S16_BE; 1161 break; 1162 default: 1163 return -1; 1164 } 1165 hwparams.rate = BE_INT(ap->sample_rate); 1166 if (hwparams.rate < 2000 || hwparams.rate > 256000) 1167 return -1; 1168 hwparams.channels = BE_INT(ap->channels); 1169 if (hwparams.channels < 1 || hwparams.channels > 256) 1170 return -1; 1171 if ((size_t)safe_read(fd, buffer + sizeof(AuHeader), BE_INT(ap->hdr_size) - sizeof(AuHeader)) != BE_INT(ap->hdr_size) - sizeof(AuHeader)) { 1172 error(_("read error")); 1173 prg_exit(EXIT_FAILURE); 1174 } 1175 return 0; 1176 } 1177 1178 static void show_available_sample_formats(snd_pcm_hw_params_t* params) 1179 { 1180 snd_pcm_format_t format; 1181 1182 fprintf(stderr, "Available formats:\n"); 1183 for (format = 0; format <= SND_PCM_FORMAT_LAST; format++) { 1184 if (snd_pcm_hw_params_test_format(handle, params, format) == 0) 1185 fprintf(stderr, "- %s\n", snd_pcm_format_name(format)); 1186 } 1187 } 1188 1189 #ifdef CONFIG_SUPPORT_CHMAP 1190 static int setup_chmap(void) 1191 { 1192 snd_pcm_chmap_t *chmap = channel_map; 1193 char mapped[hwparams.channels]; 1194 snd_pcm_chmap_t *hw_chmap; 1195 unsigned int ch, i; 1196 int err; 1197 1198 if (!chmap) 1199 return 0; 1200 1201 if (chmap->channels != hwparams.channels) { 1202 error(_("Channel numbers don't match between hw_params and channel map")); 1203 return -1; 1204 } 1205 err = snd_pcm_set_chmap(handle, chmap); 1206 if (!err) 1207 return 0; 1208 1209 hw_chmap = snd_pcm_get_chmap(handle); 1210 if (!hw_chmap) { 1211 fprintf(stderr, _("Warning: unable to get channel map\n")); 1212 return 0; 1213 } 1214 1215 if (hw_chmap->channels == chmap->channels && 1216 !memcmp(hw_chmap, chmap, 4 * (chmap->channels + 1))) { 1217 /* maps are identical, so no need to convert */ 1218 free(hw_chmap); 1219 return 0; 1220 } 1221 1222 hw_map = calloc(hwparams.channels, sizeof(int)); 1223 if (!hw_map) { 1224 error(_("not enough memory")); 1225 return -1; 1226 } 1227 1228 memset(mapped, 0, sizeof(mapped)); 1229 for (ch = 0; ch < hw_chmap->channels; ch++) { 1230 if (chmap->pos[ch] == hw_chmap->pos[ch]) { 1231 mapped[ch] = 1; 1232 hw_map[ch] = ch; 1233 continue; 1234 } 1235 for (i = 0; i < hw_chmap->channels; i++) { 1236 if (!mapped[i] && chmap->pos[ch] == hw_chmap->pos[i]) { 1237 mapped[i] = 1; 1238 hw_map[ch] = i; 1239 break; 1240 } 1241 } 1242 if (i >= hw_chmap->channels) { 1243 char buf[256]; 1244 error(_("Channel %d doesn't match with hw_parmas"), ch); 1245 snd_pcm_chmap_print(hw_chmap, sizeof(buf), buf); 1246 fprintf(stderr, "hardware chmap = %s\n", buf); 1247 return -1; 1248 } 1249 } 1250 free(hw_chmap); 1251 return 0; 1252 } 1253 #else 1254 #define setup_chmap() 0 1255 #endif 1256 1257 static void set_params(void) 1258 { 1259 snd_pcm_hw_params_t *params; 1260 snd_pcm_sw_params_t *swparams; 1261 snd_pcm_uframes_t buffer_size; 1262 int err; 1263 size_t n; 1264 unsigned int rate; 1265 snd_pcm_uframes_t start_threshold, stop_threshold; 1266 snd_pcm_hw_params_alloca(¶ms); 1267 snd_pcm_sw_params_alloca(&swparams); 1268 err = snd_pcm_hw_params_any(handle, params); 1269 if (err < 0) { 1270 error(_("Broken configuration for this PCM: no configurations available")); 1271 prg_exit(EXIT_FAILURE); 1272 } 1273 if (dump_hw_params) { 1274 fprintf(stderr, _("HW Params of device \"%s\":\n"), 1275 snd_pcm_name(handle)); 1276 fprintf(stderr, "--------------------\n"); 1277 snd_pcm_hw_params_dump(params, log); 1278 fprintf(stderr, "--------------------\n"); 1279 } 1280 if (mmap_flag) { 1281 snd_pcm_access_mask_t *mask = alloca(snd_pcm_access_mask_sizeof()); 1282 snd_pcm_access_mask_none(mask); 1283 snd_pcm_access_mask_set(mask, SND_PCM_ACCESS_MMAP_INTERLEAVED); 1284 snd_pcm_access_mask_set(mask, SND_PCM_ACCESS_MMAP_NONINTERLEAVED); 1285 snd_pcm_access_mask_set(mask, SND_PCM_ACCESS_MMAP_COMPLEX); 1286 err = snd_pcm_hw_params_set_access_mask(handle, params, mask); 1287 } else if (interleaved) 1288 err = snd_pcm_hw_params_set_access(handle, params, 1289 SND_PCM_ACCESS_RW_INTERLEAVED); 1290 else 1291 err = snd_pcm_hw_params_set_access(handle, params, 1292 SND_PCM_ACCESS_RW_NONINTERLEAVED); 1293 if (err < 0) { 1294 error(_("Access type not available")); 1295 prg_exit(EXIT_FAILURE); 1296 } 1297 err = snd_pcm_hw_params_set_format(handle, params, hwparams.format); 1298 if (err < 0) { 1299 error(_("Sample format non available")); 1300 show_available_sample_formats(params); 1301 prg_exit(EXIT_FAILURE); 1302 } 1303 err = snd_pcm_hw_params_set_channels(handle, params, hwparams.channels); 1304 if (err < 0) { 1305 error(_("Channels count non available")); 1306 prg_exit(EXIT_FAILURE); 1307 } 1308 1309 #if 0 1310 err = snd_pcm_hw_params_set_periods_min(handle, params, 2); 1311 assert(err >= 0); 1312 #endif 1313 rate = hwparams.rate; 1314 err = snd_pcm_hw_params_set_rate_near(handle, params, &hwparams.rate, 0); 1315 assert(err >= 0); 1316 if ((float)rate * 1.05 < hwparams.rate || (float)rate * 0.95 > hwparams.rate) { 1317 if (!quiet_mode) { 1318 char plugex[64]; 1319 const char *pcmname = snd_pcm_name(handle); 1320 fprintf(stderr, _("Warning: rate is not accurate (requested = %iHz, got = %iHz)\n"), rate, hwparams.rate); 1321 if (! pcmname || strchr(snd_pcm_name(handle), ':')) 1322 *plugex = 0; 1323 else 1324 snprintf(plugex, sizeof(plugex), "(-Dplug:%s)", 1325 snd_pcm_name(handle)); 1326 fprintf(stderr, _(" please, try the plug plugin %s\n"), 1327 plugex); 1328 } 1329 } 1330 rate = hwparams.rate; 1331 if (buffer_time == 0 && buffer_frames == 0) { 1332 err = snd_pcm_hw_params_get_buffer_time_max(params, 1333 &buffer_time, 0); 1334 assert(err >= 0); 1335 if (buffer_time > 500000) 1336 buffer_time = 500000; 1337 } 1338 if (period_time == 0 && period_frames == 0) { 1339 if (buffer_time > 0) 1340 period_time = buffer_time / 4; 1341 else 1342 period_frames = buffer_frames / 4; 1343 } 1344 if (period_time > 0) 1345 err = snd_pcm_hw_params_set_period_time_near(handle, params, 1346 &period_time, 0); 1347 else 1348 err = snd_pcm_hw_params_set_period_size_near(handle, params, 1349 &period_frames, 0); 1350 assert(err >= 0); 1351 if (buffer_time > 0) { 1352 err = snd_pcm_hw_params_set_buffer_time_near(handle, params, 1353 &buffer_time, 0); 1354 } else { 1355 err = snd_pcm_hw_params_set_buffer_size_near(handle, params, 1356 &buffer_frames); 1357 } 1358 assert(err >= 0); 1359 monotonic = snd_pcm_hw_params_is_monotonic(params); 1360 can_pause = snd_pcm_hw_params_can_pause(params); 1361 err = snd_pcm_hw_params(handle, params); 1362 if (err < 0) { 1363 error(_("Unable to install hw params:")); 1364 snd_pcm_hw_params_dump(params, log); 1365 prg_exit(EXIT_FAILURE); 1366 } 1367 snd_pcm_hw_params_get_period_size(params, &chunk_size, 0); 1368 snd_pcm_hw_params_get_buffer_size(params, &buffer_size); 1369 if (chunk_size == buffer_size) { 1370 error(_("Can't use period equal to buffer size (%lu == %lu)"), 1371 chunk_size, buffer_size); 1372 prg_exit(EXIT_FAILURE); 1373 } 1374 snd_pcm_sw_params_current(handle, swparams); 1375 if (avail_min < 0) 1376 n = chunk_size; 1377 else 1378 n = (double) rate * avail_min / 1000000; 1379 err = snd_pcm_sw_params_set_avail_min(handle, swparams, n); 1380 1381 /* round up to closest transfer boundary */ 1382 n = buffer_size; 1383 if (start_delay <= 0) { 1384 start_threshold = n + (double) rate * start_delay / 1000000; 1385 } else 1386 start_threshold = (double) rate * start_delay / 1000000; 1387 if (start_threshold < 1) 1388 start_threshold = 1; 1389 if (start_threshold > n) 1390 start_threshold = n; 1391 err = snd_pcm_sw_params_set_start_threshold(handle, swparams, start_threshold); 1392 assert(err >= 0); 1393 if (stop_delay <= 0) 1394 stop_threshold = buffer_size + (double) rate * stop_delay / 1000000; 1395 else 1396 stop_threshold = (double) rate * stop_delay / 1000000; 1397 err = snd_pcm_sw_params_set_stop_threshold(handle, swparams, stop_threshold); 1398 assert(err >= 0); 1399 1400 if (snd_pcm_sw_params(handle, swparams) < 0) { 1401 error(_("unable to install sw params:")); 1402 snd_pcm_sw_params_dump(swparams, log); 1403 prg_exit(EXIT_FAILURE); 1404 } 1405 1406 if (setup_chmap()) 1407 prg_exit(EXIT_FAILURE); 1408 1409 if (verbose) 1410 snd_pcm_dump(handle, log); 1411 1412 bits_per_sample = snd_pcm_format_physical_width(hwparams.format); 1413 significant_bits_per_sample = snd_pcm_format_width(hwparams.format); 1414 bits_per_frame = bits_per_sample * hwparams.channels; 1415 chunk_bytes = chunk_size * bits_per_frame / 8; 1416 audiobuf = realloc(audiobuf, chunk_bytes); 1417 if (audiobuf == NULL) { 1418 error(_("not enough memory")); 1419 prg_exit(EXIT_FAILURE); 1420 } 1421 // fprintf(stderr, "real chunk_size = %i, frags = %i, total = %i\n", chunk_size, setup.buf.block.frags, setup.buf.block.frags * chunk_size); 1422 1423 /* stereo VU-meter isn't always available... */ 1424 if (vumeter == VUMETER_STEREO) { 1425 if (hwparams.channels != 2 || !interleaved || verbose > 2) 1426 vumeter = VUMETER_MONO; 1427 } 1428 1429 /* show mmap buffer arragment */ 1430 if (mmap_flag && verbose) { 1431 const snd_pcm_channel_area_t *areas; 1432 snd_pcm_uframes_t offset, size = chunk_size; 1433 int i; 1434 err = snd_pcm_mmap_begin(handle, &areas, &offset, &size); 1435 if (err < 0) { 1436 error(_("snd_pcm_mmap_begin problem: %s"), snd_strerror(err)); 1437 prg_exit(EXIT_FAILURE); 1438 } 1439 for (i = 0; i < hwparams.channels; i++) 1440 fprintf(stderr, "mmap_area[%i] = %p,%u,%u (%u)\n", i, areas[i].addr, areas[i].first, areas[i].step, snd_pcm_format_physical_width(hwparams.format)); 1441 /* not required, but for sure */ 1442 snd_pcm_mmap_commit(handle, offset, 0); 1443 } 1444 1445 buffer_frames = buffer_size; /* for position test */ 1446 } 1447 1448 static void init_stdin(void) 1449 { 1450 struct termios term; 1451 long flags; 1452 1453 if (!interactive) 1454 return; 1455 if (!isatty(fileno(stdin))) { 1456 interactive = 0; 1457 return; 1458 } 1459 tcgetattr(fileno(stdin), &term); 1460 term_c_lflag = term.c_lflag; 1461 if (fd == fileno(stdin)) 1462 return; 1463 flags = fcntl(fileno(stdin), F_GETFL); 1464 if (flags < 0 || fcntl(fileno(stdin), F_SETFL, flags|O_NONBLOCK) < 0) 1465 fprintf(stderr, _("stdin O_NONBLOCK flag setup failed\n")); 1466 term.c_lflag &= ~ICANON; 1467 tcsetattr(fileno(stdin), TCSANOW, &term); 1468 } 1469 1470 static void done_stdin(void) 1471 { 1472 struct termios term; 1473 1474 if (!interactive) 1475 return; 1476 if (fd == fileno(stdin) || term_c_lflag == -1) 1477 return; 1478 tcgetattr(fileno(stdin), &term); 1479 term.c_lflag = term_c_lflag; 1480 tcsetattr(fileno(stdin), TCSANOW, &term); 1481 } 1482 1483 static void do_pause(void) 1484 { 1485 int err; 1486 unsigned char b; 1487 1488 if (!can_pause) { 1489 fprintf(stderr, _("\rPAUSE command ignored (no hw support)\n")); 1490 return; 1491 } 1492 if (snd_pcm_state(handle) == SND_PCM_STATE_SUSPENDED) 1493 suspend(); 1494 1495 err = snd_pcm_pause(handle, 1); 1496 if (err < 0) { 1497 error(_("pause push error: %s"), snd_strerror(err)); 1498 return; 1499 } 1500 while (1) { 1501 while (read(fileno(stdin), &b, 1) != 1); 1502 if (b == ' ' || b == '\r') { 1503 while (read(fileno(stdin), &b, 1) == 1); 1504 if (snd_pcm_state(handle) == SND_PCM_STATE_SUSPENDED) 1505 suspend(); 1506 err = snd_pcm_pause(handle, 0); 1507 if (err < 0) 1508 error(_("pause release error: %s"), snd_strerror(err)); 1509 return; 1510 } 1511 } 1512 } 1513 1514 static void check_stdin(void) 1515 { 1516 unsigned char b; 1517 1518 if (!interactive) 1519 return; 1520 if (fd != fileno(stdin)) { 1521 while (read(fileno(stdin), &b, 1) == 1) { 1522 if (b == ' ' || b == '\r') { 1523 while (read(fileno(stdin), &b, 1) == 1); 1524 fprintf(stderr, _("\r=== PAUSE === ")); 1525 fflush(stderr); 1526 do_pause(); 1527 fprintf(stderr, " \r"); 1528 fflush(stderr); 1529 } 1530 } 1531 } 1532 } 1533 1534 #ifndef timersub 1535 #define timersub(a, b, result) \ 1536 do { \ 1537 (result)->tv_sec = (a)->tv_sec - (b)->tv_sec; \ 1538 (result)->tv_usec = (a)->tv_usec - (b)->tv_usec; \ 1539 if ((result)->tv_usec < 0) { \ 1540 --(result)->tv_sec; \ 1541 (result)->tv_usec += 1000000; \ 1542 } \ 1543 } while (0) 1544 #endif 1545 1546 #ifndef timermsub 1547 #define timermsub(a, b, result) \ 1548 do { \ 1549 (result)->tv_sec = (a)->tv_sec - (b)->tv_sec; \ 1550 (result)->tv_nsec = (a)->tv_nsec - (b)->tv_nsec; \ 1551 if ((result)->tv_nsec < 0) { \ 1552 --(result)->tv_sec; \ 1553 (result)->tv_nsec += 1000000000L; \ 1554 } \ 1555 } while (0) 1556 #endif 1557 1558 /* I/O error handler */ 1559 static void xrun(void) 1560 { 1561 snd_pcm_status_t *status; 1562 int res; 1563 1564 snd_pcm_status_alloca(&status); 1565 if ((res = snd_pcm_status(handle, status))<0) { 1566 error(_("status error: %s"), snd_strerror(res)); 1567 prg_exit(EXIT_FAILURE); 1568 } 1569 if (snd_pcm_status_get_state(status) == SND_PCM_STATE_XRUN) { 1570 if (fatal_errors) { 1571 error(_("fatal %s: %s"), 1572 stream == SND_PCM_STREAM_PLAYBACK ? _("underrun") : _("overrun"), 1573 snd_strerror(res)); 1574 prg_exit(EXIT_FAILURE); 1575 } 1576 if (monotonic) { 1577 #ifdef HAVE_CLOCK_GETTIME 1578 struct timespec now, diff, tstamp; 1579 clock_gettime(CLOCK_MONOTONIC, &now); 1580 snd_pcm_status_get_trigger_htstamp(status, &tstamp); 1581 timermsub(&now, &tstamp, &diff); 1582 fprintf(stderr, _("%s!!! (at least %.3f ms long)\n"), 1583 stream == SND_PCM_STREAM_PLAYBACK ? _("underrun") : _("overrun"), 1584 diff.tv_sec * 1000 + diff.tv_nsec / 1000000.0); 1585 #else 1586 fprintf(stderr, "%s !!!\n", _("underrun")); 1587 #endif 1588 } else { 1589 struct timeval now, diff, tstamp; 1590 gettimeofday(&now, 0); 1591 snd_pcm_status_get_trigger_tstamp(status, &tstamp); 1592 timersub(&now, &tstamp, &diff); 1593 fprintf(stderr, _("%s!!! (at least %.3f ms long)\n"), 1594 stream == SND_PCM_STREAM_PLAYBACK ? _("underrun") : _("overrun"), 1595 diff.tv_sec * 1000 + diff.tv_usec / 1000.0); 1596 } 1597 if (verbose) { 1598 fprintf(stderr, _("Status:\n")); 1599 snd_pcm_status_dump(status, log); 1600 } 1601 if ((res = snd_pcm_prepare(handle))<0) { 1602 error(_("xrun: prepare error: %s"), snd_strerror(res)); 1603 prg_exit(EXIT_FAILURE); 1604 } 1605 return; /* ok, data should be accepted again */ 1606 } if (snd_pcm_status_get_state(status) == SND_PCM_STATE_DRAINING) { 1607 if (verbose) { 1608 fprintf(stderr, _("Status(DRAINING):\n")); 1609 snd_pcm_status_dump(status, log); 1610 } 1611 if (stream == SND_PCM_STREAM_CAPTURE) { 1612 fprintf(stderr, _("capture stream format change? attempting recover...\n")); 1613 if ((res = snd_pcm_prepare(handle))<0) { 1614 error(_("xrun(DRAINING): prepare error: %s"), snd_strerror(res)); 1615 prg_exit(EXIT_FAILURE); 1616 } 1617 return; 1618 } 1619 } 1620 if (verbose) { 1621 fprintf(stderr, _("Status(R/W):\n")); 1622 snd_pcm_status_dump(status, log); 1623 } 1624 error(_("read/write error, state = %s"), snd_pcm_state_name(snd_pcm_status_get_state(status))); 1625 prg_exit(EXIT_FAILURE); 1626 } 1627 1628 /* I/O suspend handler */ 1629 static void suspend(void) 1630 { 1631 int res; 1632 1633 if (!quiet_mode) 1634 fprintf(stderr, _("Suspended. Trying resume. ")); fflush(stderr); 1635 while ((res = snd_pcm_resume(handle)) == -EAGAIN) 1636 sleep(1); /* wait until suspend flag is released */ 1637 if (res < 0) { 1638 if (!quiet_mode) 1639 fprintf(stderr, _("Failed. Restarting stream. ")); fflush(stderr); 1640 if ((res = snd_pcm_prepare(handle)) < 0) { 1641 error(_("suspend: prepare error: %s"), snd_strerror(res)); 1642 prg_exit(EXIT_FAILURE); 1643 } 1644 } 1645 if (!quiet_mode) 1646 fprintf(stderr, _("Done.\n")); 1647 } 1648 1649 static void print_vu_meter_mono(int perc, int maxperc) 1650 { 1651 const int bar_length = 82; 1652 char line[140]; 1653 int val; 1654 1655 for (val = 0; val <= perc * bar_length / 100 && val < bar_length; val++) 1656 line[val] = '#'; 1657 for (; val <= maxperc * bar_length / 100 && val < bar_length; val++) 1658 line[val] = ' '; 1659 line[val] = '+'; 1660 for (++val; val <= bar_length; val++) 1661 line[val] = ' '; 1662 if (maxperc > 99) 1663 sprintf(line + val, "| MAX"); 1664 else 1665 sprintf(line + val, "| %02i%%", maxperc); 1666 //fputs(line, stderr); 1667 if (perc > 100) 1668 fprintf(stderr, _(" !clip ")); 1669 FILE *vumeter; 1670 vumeter = fopen("/dev/shm/vumeter","w"); 1671 if (vumeter != NULL){ 1672 fputs(line, vumeter); 1673 fclose(vumeter); 1674 } 1675 } 1676 1677 static void print_vu_meter_stereo(int *perc, int *maxperc) 1678 { 1679 const int bar_length = 35; 1680 char line[80]; 1681 int c; 1682 1683 memset(line, ' ', sizeof(line) - 1); 1684 line[bar_length + 3] = '|'; 1685 1686 for (c = 0; c < 2; c++) { 1687 int p = perc[c] * bar_length / 100; 1688 char tmp[4]; 1689 if (p > bar_length) 1690 p = bar_length; 1691 if (c) 1692 memset(line + bar_length + 6 + 1, '#', p); 1693 else 1694 memset(line + bar_length - p - 1, '#', p); 1695 p = maxperc[c] * bar_length / 100; 1696 if (p > bar_length) 1697 p = bar_length; 1698 if (c) 1699 line[bar_length + 6 + 1 + p] = '+'; 1700 else 1701 line[bar_length - p - 1] = '+'; 1702 if (maxperc[c] > 99) 1703 sprintf(tmp, "MAX"); 1704 else 1705 sprintf(tmp, "%02d%%", maxperc[c]); 1706 if (c) 1707 memcpy(line + bar_length + 3 + 1, tmp, 3); 1708 else 1709 memcpy(line + bar_length, tmp, 3); 1710 } 1711 line[bar_length * 2 + 6 + 2] = 0; 1712 fputs(line, stderr); 1713 } 1714 1715 static void print_vu_meter(signed int *perc, signed int *maxperc) 1716 { 1717 if (vumeter == VUMETER_STEREO) 1718 print_vu_meter_stereo(perc, maxperc); 1719 else 1720 print_vu_meter_mono(*perc, *maxperc); 1721 } 1722 1723 /* peak handler */ 1724 static void compute_max_peak(u_char *data, size_t count) 1725 { 1726 signed int val, max, perc[2], max_peak[2]; 1727 static int run = 0; 1728 size_t ocount = count; 1729 int format_little_endian = snd_pcm_format_little_endian(hwparams.format); 1730 int ichans, c; 1731 1732 if (vumeter == VUMETER_STEREO) 1733 ichans = 2; 1734 else 1735 ichans = 1; 1736 1737 memset(max_peak, 0, sizeof(max_peak)); 1738 switch (bits_per_sample) { 1739 case 8: { 1740 signed char *valp = (signed char *)data; 1741 signed char mask = snd_pcm_format_silence(hwparams.format); 1742 c = 0; 1743 while (count-- > 0) { 1744 val = *valp++ ^ mask; 1745 val = abs(val); 1746 if (max_peak[c] < val) 1747 max_peak[c] = val; 1748 if (vumeter == VUMETER_STEREO) 1749 c = !c; 1750 } 1751 break; 1752 } 1753 case 16: { 1754 signed short *valp = (signed short *)data; 1755 signed short mask = snd_pcm_format_silence_16(hwparams.format); 1756 signed short sval; 1757 1758 count /= 2; 1759 c = 0; 1760 while (count-- > 0) { 1761 if (format_little_endian) 1762 sval = le16toh(*valp); 1763 else 1764 sval = be16toh(*valp); 1765 sval = abs(sval) ^ mask; 1766 if (max_peak[c] < sval) 1767 max_peak[c] = sval; 1768 valp++; 1769 if (vumeter == VUMETER_STEREO) 1770 c = !c; 1771 } 1772 break; 1773 } 1774 case 24: { 1775 unsigned char *valp = data; 1776 signed int mask = snd_pcm_format_silence_32(hwparams.format); 1777 1778 count /= 3; 1779 c = 0; 1780 while (count-- > 0) { 1781 if (format_little_endian) { 1782 val = valp[0] | (valp[1]<<8) | (valp[2]<<16); 1783 } else { 1784 val = (valp[0]<<16) | (valp[1]<<8) | valp[2]; 1785 } 1786 /* Correct signed bit in 32-bit value */ 1787 if (val & (1<<(bits_per_sample-1))) { 1788 val |= 0xff<<24; /* Negate upper bits too */ 1789 } 1790 val = abs(val) ^ mask; 1791 if (max_peak[c] < val) 1792 max_peak[c] = val; 1793 valp += 3; 1794 if (vumeter == VUMETER_STEREO) 1795 c = !c; 1796 } 1797 break; 1798 } 1799 case 32: { 1800 signed int *valp = (signed int *)data; 1801 signed int mask = snd_pcm_format_silence_32(hwparams.format); 1802 1803 count /= 4; 1804 c = 0; 1805 while (count-- > 0) { 1806 if (format_little_endian) 1807 val = le32toh(*valp); 1808 else 1809 val = be32toh(*valp); 1810 val = abs(val) ^ mask; 1811 if (max_peak[c] < val) 1812 max_peak[c] = val; 1813 valp++; 1814 if (vumeter == VUMETER_STEREO) 1815 c = !c; 1816 } 1817 break; 1818 } 1819 default: 1820 if (run == 0) { 1821 fprintf(stderr, _("Unsupported bit size %d.\n"), (int)bits_per_sample); 1822 run = 1; 1823 } 1824 return; 1825 } 1826 max = 1 << (significant_bits_per_sample-1); 1827 if (max <= 0) 1828 max = 0x7fffffff; 1829 1830 for (c = 0; c < ichans; c++) { 1831 if (bits_per_sample > 16) 1832 perc[c] = max_peak[c] / (max / 100); 1833 else 1834 perc[c] = max_peak[c] * 100 / max; 1835 } 1836 1837 if (interleaved && verbose <= 2) { 1838 static int maxperc[2]; 1839 static time_t t=0; 1840 const time_t tt=time(NULL); 1841 if(tt>t) { 1842 t=tt; 1843 maxperc[0] = 0; 1844 maxperc[1] = 0; 1845 } 1846 for (c = 0; c < ichans; c++) 1847 if (perc[c] > maxperc[c]) 1848 maxperc[c] = perc[c]; 1849 1850 putc('\r', stderr); 1851 print_vu_meter(perc, maxperc); 1852 fflush(stderr); 1853 } 1854 else if(verbose==3) { 1855 fprintf(stderr, _("Max peak (%li samples): 0x%08x "), (long)ocount, max_peak[0]); 1856 for (val = 0; val < 20; val++) 1857 if (val <= perc[0] / 5) 1858 putc('#', stderr); 1859 else 1860 putc(' ', stderr); 1861 fprintf(stderr, " %i%%\n", perc[0]); 1862 fflush(stderr); 1863 } 1864 } 1865 1866 static void do_test_position(void) 1867 { 1868 static long counter = 0; 1869 static time_t tmr = -1; 1870 time_t now; 1871 static float availsum, delaysum, samples; 1872 static snd_pcm_sframes_t maxavail, maxdelay; 1873 static snd_pcm_sframes_t minavail, mindelay; 1874 static snd_pcm_sframes_t badavail = 0, baddelay = 0; 1875 snd_pcm_sframes_t outofrange; 1876 snd_pcm_sframes_t avail, delay; 1877 int err; 1878 1879 err = snd_pcm_avail_delay(handle, &avail, &delay); 1880 if (err < 0) 1881 return; 1882 outofrange = (test_coef * (snd_pcm_sframes_t)buffer_frames) / 2; 1883 if (avail > outofrange || avail < -outofrange || 1884 delay > outofrange || delay < -outofrange) { 1885 badavail = avail; baddelay = delay; 1886 availsum = delaysum = samples = 0; 1887 maxavail = maxdelay = 0; 1888 minavail = mindelay = buffer_frames * 16; 1889 fprintf(stderr, _("Suspicious buffer position (%li total): " 1890 "avail = %li, delay = %li, buffer = %li\n"), 1891 ++counter, (long)avail, (long)delay, (long)buffer_frames); 1892 } else if (verbose) { 1893 time(&now); 1894 if (tmr == (time_t) -1) { 1895 tmr = now; 1896 availsum = delaysum = samples = 0; 1897 maxavail = maxdelay = 0; 1898 minavail = mindelay = buffer_frames * 16; 1899 } 1900 if (avail > maxavail) 1901 maxavail = avail; 1902 if (delay > maxdelay) 1903 maxdelay = delay; 1904 if (avail < minavail) 1905 minavail = avail; 1906 if (delay < mindelay) 1907 mindelay = delay; 1908 availsum += avail; 1909 delaysum += delay; 1910 samples++; 1911 if (avail != 0 && now != tmr) { 1912 fprintf(stderr, "BUFPOS: avg%li/%li " 1913 "min%li/%li max%li/%li (%li) (%li:%li/%li)\n", 1914 (long)(availsum / samples), 1915 (long)(delaysum / samples), 1916 (long)minavail, (long)mindelay, 1917 (long)maxavail, (long)maxdelay, 1918 (long)buffer_frames, 1919 counter, badavail, baddelay); 1920 tmr = now; 1921 } 1922 } 1923 } 1924 1925 /* 1926 */ 1927 #ifdef CONFIG_SUPPORT_CHMAP 1928 static u_char *remap_data(u_char *data, size_t count) 1929 { 1930 static u_char *tmp, *src, *dst; 1931 static size_t tmp_size; 1932 size_t sample_bytes = bits_per_sample / 8; 1933 size_t step = bits_per_frame / 8; 1934 size_t chunk_bytes; 1935 unsigned int ch, i; 1936 1937 if (!hw_map) 1938 return data; 1939 1940 chunk_bytes = count * bits_per_frame / 8; 1941 if (tmp_size < chunk_bytes) { 1942 free(tmp); 1943 tmp = malloc(chunk_bytes); 1944 if (!tmp) { 1945 error(_("not enough memory")); 1946 exit(1); 1947 } 1948 tmp_size = count; 1949 } 1950 1951 src = data; 1952 dst = tmp; 1953 for (i = 0; i < count; i++) { 1954 for (ch = 0; ch < hwparams.channels; ch++) { 1955 memcpy(dst, src + sample_bytes * hw_map[ch], 1956 sample_bytes); 1957 dst += sample_bytes; 1958 } 1959 src += step; 1960 } 1961 return tmp; 1962 } 1963 1964 static u_char **remap_datav(u_char **data, size_t count) 1965 { 1966 static u_char **tmp; 1967 unsigned int ch; 1968 1969 if (!hw_map) 1970 return data; 1971 1972 if (!tmp) { 1973 tmp = malloc(sizeof(*tmp) * hwparams.channels); 1974 if (!tmp) { 1975 error(_("not enough memory")); 1976 exit(1); 1977 } 1978 for (ch = 0; ch < hwparams.channels; ch++) 1979 tmp[ch] = data[hw_map[ch]]; 1980 } 1981 return tmp; 1982 } 1983 #else 1984 #define remap_data(data, count) (data) 1985 #define remap_datav(data, count) (data) 1986 #endif 1987 1988 /* 1989 * write function 1990 */ 1991 1992 static ssize_t pcm_write(u_char *data, size_t count) 1993 { 1994 ssize_t r; 1995 ssize_t result = 0; 1996 1997 if (count < chunk_size) { 1998 snd_pcm_format_set_silence(hwparams.format, data + count * bits_per_frame / 8, (chunk_size - count) * hwparams.channels); 1999 count = chunk_size; 2000 } 2001 data = remap_data(data, count); 2002 while (count > 0 && !in_aborting) { 2003 if (test_position) 2004 do_test_position(); 2005 check_stdin(); 2006 r = writei_func(handle, data, count); 2007 if (test_position) 2008 do_test_position(); 2009 if (r == -EAGAIN || (r >= 0 && (size_t)r < count)) { 2010 if (!test_nowait) 2011 snd_pcm_wait(handle, 100); 2012 } else if (r == -EPIPE) { 2013 xrun(); 2014 } else if (r == -ESTRPIPE) { 2015 suspend(); 2016 } else if (r < 0) { 2017 error(_("write error: %s"), snd_strerror(r)); 2018 prg_exit(EXIT_FAILURE); 2019 } 2020 if (r > 0) { 2021 if (vumeter) 2022 compute_max_peak(data, r * hwparams.channels); 2023 result += r; 2024 count -= r; 2025 data += r * bits_per_frame / 8; 2026 } 2027 } 2028 return result; 2029 } 2030 2031 static ssize_t pcm_writev(u_char **data, unsigned int channels, size_t count) 2032 { 2033 ssize_t r; 2034 size_t result = 0; 2035 2036 if (count != chunk_size) { 2037 unsigned int channel; 2038 size_t offset = count; 2039 size_t remaining = chunk_size - count; 2040 for (channel = 0; channel < channels; channel++) 2041 snd_pcm_format_set_silence(hwparams.format, data[channel] + offset * bits_per_sample / 8, remaining); 2042 count = chunk_size; 2043 } 2044 data = remap_datav(data, count); 2045 while (count > 0 && !in_aborting) { 2046 unsigned int channel; 2047 void *bufs[channels]; 2048 size_t offset = result; 2049 for (channel = 0; channel < channels; channel++) 2050 bufs[channel] = data[channel] + offset * bits_per_sample / 8; 2051 if (test_position) 2052 do_test_position(); 2053 check_stdin(); 2054 r = writen_func(handle, bufs, count); 2055 if (test_position) 2056 do_test_position(); 2057 if (r == -EAGAIN || (r >= 0 && (size_t)r < count)) { 2058 if (!test_nowait) 2059 snd_pcm_wait(handle, 100); 2060 } else if (r == -EPIPE) { 2061 xrun(); 2062 } else if (r == -ESTRPIPE) { 2063 suspend(); 2064 } else if (r < 0) { 2065 error(_("writev error: %s"), snd_strerror(r)); 2066 prg_exit(EXIT_FAILURE); 2067 } 2068 if (r > 0) { 2069 if (vumeter) { 2070 for (channel = 0; channel < channels; channel++) 2071 compute_max_peak(data[channel], r); 2072 } 2073 result += r; 2074 count -= r; 2075 } 2076 } 2077 return result; 2078 } 2079 2080 /* 2081 * read function 2082 */ 2083 2084 static ssize_t pcm_read(u_char *data, size_t rcount) 2085 { 2086 ssize_t r; 2087 size_t result = 0; 2088 size_t count = rcount; 2089 2090 if (count != chunk_size) { 2091 count = chunk_size; 2092 } 2093 2094 while (count > 0 && !in_aborting) { 2095 if (test_position) 2096 do_test_position(); 2097 check_stdin(); 2098 r = readi_func(handle, data, count); 2099 if (test_position) 2100 do_test_position(); 2101 if (r == -EAGAIN || (r >= 0 && (size_t)r < count)) { 2102 if (!test_nowait) 2103 snd_pcm_wait(handle, 100); 2104 } else if (r == -EPIPE) { 2105 xrun(); 2106 } else if (r == -ESTRPIPE) { 2107 suspend(); 2108 } else if (r < 0) { 2109 error(_("read error: %s"), snd_strerror(r)); 2110 prg_exit(EXIT_FAILURE); 2111 } 2112 if (r > 0) { 2113 if (vumeter) 2114 compute_max_peak(data, r * hwparams.channels); 2115 result += r; 2116 count -= r; 2117 data += r * bits_per_frame / 8; 2118 } 2119 } 2120 return rcount; 2121 } 2122 2123 static ssize_t pcm_readv(u_char **data, unsigned int channels, size_t rcount) 2124 { 2125 ssize_t r; 2126 size_t result = 0; 2127 size_t count = rcount; 2128 2129 if (count != chunk_size) { 2130 count = chunk_size; 2131 } 2132 2133 while (count > 0 && !in_aborting) { 2134 unsigned int channel; 2135 void *bufs[channels]; 2136 size_t offset = result; 2137 for (channel = 0; channel < channels; channel++) 2138 bufs[channel] = data[channel] + offset * bits_per_sample / 8; 2139 if (test_position) 2140 do_test_position(); 2141 check_stdin(); 2142 r = readn_func(handle, bufs, count); 2143 if (test_position) 2144 do_test_position(); 2145 if (r == -EAGAIN || (r >= 0 && (size_t)r < count)) { 2146 if (!test_nowait) 2147 snd_pcm_wait(handle, 100); 2148 } else if (r == -EPIPE) { 2149 xrun(); 2150 } else if (r == -ESTRPIPE) { 2151 suspend(); 2152 } else if (r < 0) { 2153 error(_("readv error: %s"), snd_strerror(r)); 2154 prg_exit(EXIT_FAILURE); 2155 } 2156 if (r > 0) { 2157 if (vumeter) { 2158 for (channel = 0; channel < channels; channel++) 2159 compute_max_peak(data[channel], r); 2160 } 2161 result += r; 2162 count -= r; 2163 } 2164 } 2165 return rcount; 2166 } 2167 2168 /* 2169 * ok, let's play a .voc file 2170 */ 2171 2172 static ssize_t voc_pcm_write(u_char *data, size_t count) 2173 { 2174 ssize_t result = count, r; 2175 size_t size; 2176 2177 while (count > 0) { 2178 size = count; 2179 if (size > chunk_bytes - buffer_pos) 2180 size = chunk_bytes - buffer_pos; 2181 memcpy(audiobuf + buffer_pos, data, size); 2182 data += size; 2183 count -= size; 2184 buffer_pos += size; 2185 if ((size_t)buffer_pos == chunk_bytes) { 2186 if ((size_t)(r = pcm_write(audiobuf, chunk_size)) != chunk_size) 2187 return r; 2188 buffer_pos = 0; 2189 } 2190 } 2191 return result; 2192 } 2193 2194 static void voc_write_silence(unsigned x) 2195 { 2196 unsigned l; 2197 u_char *buf; 2198 2199 buf = (u_char *) malloc(chunk_bytes); 2200 if (buf == NULL) { 2201 error(_("can't allocate buffer for silence")); 2202 return; /* not fatal error */ 2203 } 2204 snd_pcm_format_set_silence(hwparams.format, buf, chunk_size * hwparams.channels); 2205 while (x > 0 && !in_aborting) { 2206 l = x; 2207 if (l > chunk_size) 2208 l = chunk_size; 2209 if (voc_pcm_write(buf, l) != (ssize_t)l) { 2210 error(_("write error")); 2211 prg_exit(EXIT_FAILURE); 2212 } 2213 x -= l; 2214 } 2215 free(buf); 2216 } 2217 2218 static void voc_pcm_flush(void) 2219 { 2220 if (buffer_pos > 0) { 2221 size_t b; 2222 if (snd_pcm_format_set_silence(hwparams.format, audiobuf + buffer_pos, chunk_bytes - buffer_pos * 8 / bits_per_sample) < 0) 2223 fprintf(stderr, _("voc_pcm_flush - silence error")); 2224 b = chunk_size; 2225 if (pcm_write(audiobuf, b) != (ssize_t)b) 2226 error(_("voc_pcm_flush error")); 2227 } 2228 snd_pcm_nonblock(handle, 0); 2229 snd_pcm_drain(handle); 2230 snd_pcm_nonblock(handle, nonblock); 2231 } 2232 2233 static void voc_play(int fd, int ofs, char *name) 2234 { 2235 int l; 2236 VocBlockType *bp; 2237 VocVoiceData *vd; 2238 VocExtBlock *eb; 2239 size_t nextblock, in_buffer; 2240 u_char *data, *buf; 2241 char was_extended = 0, output = 0; 2242 u_short *sp, repeat = 0; 2243 off64_t filepos = 0; 2244 2245 #define COUNT(x) nextblock -= x; in_buffer -= x; data += x 2246 #define COUNT1(x) in_buffer -= x; data += x 2247 2248 data = buf = (u_char *)malloc(64 * 1024); 2249 buffer_pos = 0; 2250 if (data == NULL) { 2251 error(_("malloc error")); 2252 prg_exit(EXIT_FAILURE); 2253 } 2254 if (!quiet_mode) { 2255 fprintf(stderr, _("Playing Creative Labs Channel file '%s'...\n"), name); 2256 } 2257 /* first we waste the rest of header, ugly but we don't need seek */ 2258 while (ofs > (ssize_t)chunk_bytes) { 2259 if ((size_t)safe_read(fd, buf, chunk_bytes) != chunk_bytes) { 2260 error(_("read error")); 2261 prg_exit(EXIT_FAILURE); 2262 } 2263 ofs -= chunk_bytes; 2264 } 2265 if (ofs) { 2266 if (safe_read(fd, buf, ofs) != ofs) { 2267 error(_("read error")); 2268 prg_exit(EXIT_FAILURE); 2269 } 2270 } 2271 hwparams.format = DEFAULT_FORMAT; 2272 hwparams.channels = 1; 2273 hwparams.rate = DEFAULT_SPEED; 2274 set_params(); 2275 2276 in_buffer = nextblock = 0; 2277 while (!in_aborting) { 2278 Fill_the_buffer: /* need this for repeat */ 2279 if (in_buffer < 32) { 2280 /* move the rest of buffer to pos 0 and fill the buf up */ 2281 if (in_buffer) 2282 memcpy(buf, data, in_buffer); 2283 data = buf; 2284 if ((l = safe_read(fd, buf + in_buffer, chunk_bytes - in_buffer)) > 0) 2285 in_buffer += l; 2286 else if (!in_buffer) { 2287 /* the file is truncated, so simulate 'Terminator' 2288 and reduce the datablock for safe landing */ 2289 nextblock = buf[0] = 0; 2290 if (l == -1) { 2291 perror(name); 2292 prg_exit(EXIT_FAILURE); 2293 } 2294 } 2295 } 2296 while (!nextblock) { /* this is a new block */ 2297 if (in_buffer < sizeof(VocBlockType)) 2298 goto __end; 2299 bp = (VocBlockType *) data; 2300 COUNT1(sizeof(VocBlockType)); 2301 nextblock = VOC_DATALEN(bp); 2302 if (output && !quiet_mode) 2303 fprintf(stderr, "\n"); /* write /n after ASCII-out */ 2304 output = 0; 2305 switch (bp->type) { 2306 case 0: 2307 #if 0 2308 d_printf("Terminator\n"); 2309 #endif 2310 return; /* VOC-file stop */ 2311 case 1: 2312 vd = (VocVoiceData *) data; 2313 COUNT1(sizeof(VocVoiceData)); 2314 /* we need a SYNC, before we can set new SPEED, STEREO ... */ 2315 2316 if (!was_extended) { 2317 hwparams.rate = (int) (vd->tc); 2318 hwparams.rate = 1000000 / (256 - hwparams.rate); 2319 #if 0 2320 d_printf("Channel data %d Hz\n", dsp_speed); 2321 #endif 2322 if (vd->pack) { /* /dev/dsp can't it */ 2323 error(_("can't play packed .voc files")); 2324 return; 2325 } 2326 if (hwparams.channels == 2) /* if we are in Stereo-Mode, switch back */ 2327 hwparams.channels = 1; 2328 } else { /* there was extended block */ 2329 hwparams.channels = 2; 2330 was_extended = 0; 2331 } 2332 set_params(); 2333 break; 2334 case 2: /* nothing to do, pure data */ 2335 #if 0 2336 d_printf("Channel continuation\n"); 2337 #endif 2338 break; 2339 case 3: /* a silence block, no data, only a count */ 2340 sp = (u_short *) data; 2341 COUNT1(sizeof(u_short)); 2342 hwparams.rate = (int) (*data); 2343 COUNT1(1); 2344 hwparams.rate = 1000000 / (256 - hwparams.rate); 2345 set_params(); 2346 #if 0 2347 { 2348 size_t silence; 2349 silence = (((size_t) * sp) * 1000) / hwparams.rate; 2350 d_printf("Silence for %d ms\n", (int) silence); 2351 } 2352 #endif 2353 voc_write_silence(*sp); 2354 break; 2355 case 4: /* a marker for syncronisation, no effect */ 2356 sp = (u_short *) data; 2357 COUNT1(sizeof(u_short)); 2358 #if 0 2359 d_printf("Marker %d\n", *sp); 2360 #endif 2361 break; 2362 case 5: /* ASCII text, we copy to stderr */ 2363 output = 1; 2364 #if 0 2365 d_printf("ASCII - text :\n"); 2366 #endif 2367 break; 2368 case 6: /* repeat marker, says repeatcount */ 2369 /* my specs don't say it: maybe this can be recursive, but 2370 I don't think somebody use it */ 2371 repeat = *(u_short *) data; 2372 COUNT1(sizeof(u_short)); 2373 #if 0 2374 d_printf("Repeat loop %d times\n", repeat); 2375 #endif 2376 if (filepos >= 0) { /* if < 0, one seek fails, why test another */ 2377 if ((filepos = lseek64(fd, 0, 1)) < 0) { 2378 error(_("can't play loops; %s isn't seekable\n"), name); 2379 repeat = 0; 2380 } else { 2381 filepos -= in_buffer; /* set filepos after repeat */ 2382 } 2383 } else { 2384 repeat = 0; 2385 } 2386 break; 2387 case 7: /* ok, lets repeat that be rewinding tape */ 2388 if (repeat) { 2389 if (repeat != 0xFFFF) { 2390 #if 0 2391 d_printf("Repeat loop %d\n", repeat); 2392 #endif 2393 --repeat; 2394 } 2395 #if 0 2396 else 2397 d_printf("Neverending loop\n"); 2398 #endif 2399 lseek64(fd, filepos, 0); 2400 in_buffer = 0; /* clear the buffer */ 2401 goto Fill_the_buffer; 2402 } 2403 #if 0 2404 else 2405 d_printf("End repeat loop\n"); 2406 #endif 2407 break; 2408 case 8: /* the extension to play Stereo, I have SB 1.0 :-( */ 2409 was_extended = 1; 2410 eb = (VocExtBlock *) data; 2411 COUNT1(sizeof(VocExtBlock)); 2412 hwparams.rate = (int) (eb->tc); 2413 hwparams.rate = 256000000L / (65536 - hwparams.rate); 2414 hwparams.channels = eb->mode == VOC_MODE_STEREO ? 2 : 1; 2415 if (hwparams.channels == 2) 2416 hwparams.rate = hwparams.rate >> 1; 2417 if (eb->pack) { /* /dev/dsp can't it */ 2418 error(_("can't play packed .voc files")); 2419 return; 2420 } 2421 #if 0 2422 d_printf("Extended block %s %d Hz\n", 2423 (eb->mode ? "Stereo" : "Mono"), dsp_speed); 2424 #endif 2425 break; 2426 default: 2427 error(_("unknown blocktype %d. terminate."), bp->type); 2428 return; 2429 } /* switch (bp->type) */ 2430 } /* while (! nextblock) */ 2431 /* put nextblock data bytes to dsp */ 2432 l = in_buffer; 2433 if (nextblock < (size_t)l) 2434 l = nextblock; 2435 if (l) { 2436 if (output && !quiet_mode) { 2437 if (write(2, data, l) != l) { /* to stderr */ 2438 error(_("write error")); 2439 prg_exit(EXIT_FAILURE); 2440 } 2441 } else { 2442 if (voc_pcm_write(data, l) != l) { 2443 error(_("write error")); 2444 prg_exit(EXIT_FAILURE); 2445 } 2446 } 2447 COUNT(l); 2448 } 2449 } /* while(1) */ 2450 __end: 2451 voc_pcm_flush(); 2452 free(buf); 2453 } 2454 /* that was a big one, perhaps somebody split it :-) */ 2455 2456 /* setting the globals for playing raw data */ 2457 static void init_raw_data(void) 2458 { 2459 hwparams = rhwparams; 2460 } 2461 2462 /* calculate the data count to read from/to dsp */ 2463 static off64_t calc_count(void) 2464 { 2465 off64_t count; 2466 2467 if (timelimit == 0) { 2468 count = pbrec_count; 2469 } else { 2470 count = snd_pcm_format_size(hwparams.format, hwparams.rate * hwparams.channels); 2471 count *= (off64_t)timelimit; 2472 } 2473 return count < pbrec_count ? count : pbrec_count; 2474 } 2475 2476 /* write a .VOC-header */ 2477 static void begin_voc(int fd, size_t cnt) 2478 { 2479 VocHeader vh; 2480 VocBlockType bt; 2481 VocVoiceData vd; 2482 VocExtBlock eb; 2483 2484 memcpy(vh.magic, VOC_MAGIC_STRING, 20); 2485 vh.headerlen = LE_SHORT(sizeof(VocHeader)); 2486 vh.version = LE_SHORT(VOC_ACTUAL_VERSION); 2487 vh.coded_ver = LE_SHORT(0x1233 - VOC_ACTUAL_VERSION); 2488 2489 if (write(fd, &vh, sizeof(VocHeader)) != sizeof(VocHeader)) { 2490 error(_("write error")); 2491 prg_exit(EXIT_FAILURE); 2492 } 2493 if (hwparams.channels > 1) { 2494 /* write an extended block */ 2495 bt.type = 8; 2496 bt.datalen = 4; 2497 bt.datalen_m = bt.datalen_h = 0; 2498 if (write(fd, &bt, sizeof(VocBlockType)) != sizeof(VocBlockType)) { 2499 error(_("write error")); 2500 prg_exit(EXIT_FAILURE); 2501 } 2502 eb.tc = LE_SHORT(65536 - 256000000L / (hwparams.rate << 1)); 2503 eb.pack = 0; 2504 eb.mode = 1; 2505 if (write(fd, &eb, sizeof(VocExtBlock)) != sizeof(VocExtBlock)) { 2506 error(_("write error")); 2507 prg_exit(EXIT_FAILURE); 2508 } 2509 } 2510 bt.type = 1; 2511 cnt += sizeof(VocVoiceData); /* Channel_data block follows */ 2512 bt.datalen = (u_char) (cnt & 0xFF); 2513 bt.datalen_m = (u_char) ((cnt & 0xFF00) >> 8); 2514 bt.datalen_h = (u_char) ((cnt & 0xFF0000) >> 16); 2515 if (write(fd, &bt, sizeof(VocBlockType)) != sizeof(VocBlockType)) { 2516 error(_("write error")); 2517 prg_exit(EXIT_FAILURE); 2518 } 2519 vd.tc = (u_char) (256 - (1000000 / hwparams.rate)); 2520 vd.pack = 0; 2521 if (write(fd, &vd, sizeof(VocVoiceData)) != sizeof(VocVoiceData)) { 2522 error(_("write error")); 2523 prg_exit(EXIT_FAILURE); 2524 } 2525 } 2526 2527 /* write a WAVE-header */ 2528 static void begin_wave(int fd, size_t cnt) 2529 { 2530 WaveHeader h; 2531 WaveFmtBody f; 2532 WaveChunkHeader cf, cd; 2533 int bits; 2534 u_int tmp; 2535 u_short tmp2; 2536 2537 /* WAVE cannot handle greater than 32bit (signed?) int */ 2538 if (cnt == (size_t)-2) 2539 cnt = 0x7fffff00; 2540 2541 bits = 8; 2542 switch ((unsigned long) hwparams.format) { 2543 case SND_PCM_FORMAT_U8: 2544 bits = 8; 2545 break; 2546 case SND_PCM_FORMAT_S16_LE: 2547 bits = 16; 2548 break; 2549 case SND_PCM_FORMAT_S32_LE: 2550 case SND_PCM_FORMAT_FLOAT_LE: 2551 bits = 32; 2552 break; 2553 case SND_PCM_FORMAT_S24_LE: 2554 case SND_PCM_FORMAT_S24_3LE: 2555 bits = 24; 2556 break; 2557 default: 2558 error(_("Wave doesn't support %s format..."), snd_pcm_format_name(hwparams.format)); 2559 prg_exit(EXIT_FAILURE); 2560 } 2561 h.magic = WAV_RIFF; 2562 tmp = cnt + sizeof(WaveHeader) + sizeof(WaveChunkHeader) + sizeof(WaveFmtBody) + sizeof(WaveChunkHeader) - 8; 2563 h.length = LE_INT(tmp); 2564 h.type = WAV_WAVE; 2565 2566 cf.type = WAV_FMT; 2567 cf.length = LE_INT(16); 2568 2569 if (hwparams.format == SND_PCM_FORMAT_FLOAT_LE) 2570 f.format = LE_SHORT(WAV_FMT_IEEE_FLOAT); 2571 else 2572 f.format = LE_SHORT(WAV_FMT_PCM); 2573 f.channels = LE_SHORT(hwparams.channels); 2574 f.sample_fq = LE_INT(hwparams.rate); 2575 #if 0 2576 tmp2 = (samplesize == 8) ? 1 : 2; 2577 f.byte_p_spl = LE_SHORT(tmp2); 2578 tmp = dsp_speed * hwparams.channels * (u_int) tmp2; 2579 #else 2580 tmp2 = hwparams.channels * snd_pcm_format_physical_width(hwparams.format) / 8; 2581 f.byte_p_spl = LE_SHORT(tmp2); 2582 tmp = (u_int) tmp2 * hwparams.rate; 2583 #endif 2584 f.byte_p_sec = LE_INT(tmp); 2585 f.bit_p_spl = LE_SHORT(bits); 2586 2587 cd.type = WAV_DATA; 2588 cd.length = LE_INT(cnt); 2589 2590 if (write(fd, &h, sizeof(WaveHeader)) != sizeof(WaveHeader) || 2591 write(fd, &cf, sizeof(WaveChunkHeader)) != sizeof(WaveChunkHeader) || 2592 write(fd, &f, sizeof(WaveFmtBody)) != sizeof(WaveFmtBody) || 2593 write(fd, &cd, sizeof(WaveChunkHeader)) != sizeof(WaveChunkHeader)) { 2594 error(_("write error")); 2595 prg_exit(EXIT_FAILURE); 2596 } 2597 } 2598 2599 /* write a Au-header */ 2600 static void begin_au(int fd, size_t cnt) 2601 { 2602 AuHeader ah; 2603 2604 ah.magic = AU_MAGIC; 2605 ah.hdr_size = BE_INT(24); 2606 ah.data_size = BE_INT(cnt); 2607 switch ((unsigned long) hwparams.format) { 2608 case SND_PCM_FORMAT_MU_LAW: 2609 ah.encoding = BE_INT(AU_FMT_ULAW); 2610 break; 2611 case SND_PCM_FORMAT_U8: 2612 ah.encoding = BE_INT(AU_FMT_LIN8); 2613 break; 2614 case SND_PCM_FORMAT_S16_BE: 2615 ah.encoding = BE_INT(AU_FMT_LIN16); 2616 break; 2617 default: 2618 error(_("Sparc Audio doesn't support %s format..."), snd_pcm_format_name(hwparams.format)); 2619 prg_exit(EXIT_FAILURE); 2620 } 2621 ah.sample_rate = BE_INT(hwparams.rate); 2622 ah.channels = BE_INT(hwparams.channels); 2623 if (write(fd, &ah, sizeof(AuHeader)) != sizeof(AuHeader)) { 2624 error(_("write error")); 2625 prg_exit(EXIT_FAILURE); 2626 } 2627 } 2628 2629 /* closing .VOC */ 2630 static void end_voc(int fd) 2631 { 2632 off64_t length_seek; 2633 VocBlockType bt; 2634 size_t cnt; 2635 char dummy = 0; /* Write a Terminator */ 2636 2637 if (write(fd, &dummy, 1) != 1) { 2638 error(_("write error")); 2639 prg_exit(EXIT_FAILURE); 2640 } 2641 length_seek = sizeof(VocHeader); 2642 if (hwparams.channels > 1) 2643 length_seek += sizeof(VocBlockType) + sizeof(VocExtBlock); 2644 bt.type = 1; 2645 cnt = fdcount; 2646 cnt += sizeof(VocVoiceData); /* Channel_data block follows */ 2647 if (cnt > 0x00ffffff) 2648 cnt = 0x00ffffff; 2649 bt.datalen = (u_char) (cnt & 0xFF); 2650 bt.datalen_m = (u_char) ((cnt & 0xFF00) >> 8); 2651 bt.datalen_h = (u_char) ((cnt & 0xFF0000) >> 16); 2652 if (lseek64(fd, length_seek, SEEK_SET) == length_seek) 2653 write(fd, &bt, sizeof(VocBlockType)); 2654 if (fd != 1) 2655 close(fd); 2656 } 2657 2658 static void end_wave(int fd) 2659 { /* only close output */ 2660 WaveChunkHeader cd; 2661 off64_t length_seek; 2662 off64_t filelen; 2663 u_int rifflen; 2664 2665 length_seek = sizeof(WaveHeader) + 2666 sizeof(WaveChunkHeader) + 2667 sizeof(WaveFmtBody); 2668 cd.type = WAV_DATA; 2669 cd.length = fdcount > 0x7fffffff ? LE_INT(0x7fffffff) : LE_INT(fdcount); 2670 filelen = fdcount + 2*sizeof(WaveChunkHeader) + sizeof(WaveFmtBody) + 4; 2671 rifflen = filelen > 0x7fffffff ? LE_INT(0x7fffffff) : LE_INT(filelen); 2672 if (lseek64(fd, 4, SEEK_SET) == 4) 2673 write(fd, &rifflen, 4); 2674 if (lseek64(fd, length_seek, SEEK_SET) == length_seek) 2675 write(fd, &cd, sizeof(WaveChunkHeader)); 2676 if (fd != 1) 2677 close(fd); 2678 } 2679 2680 static void end_au(int fd) 2681 { /* only close output */ 2682 AuHeader ah; 2683 off64_t length_seek; 2684 2685 length_seek = (char *)&ah.data_size - (char *)&ah; 2686 ah.data_size = fdcount > 0xffffffff ? 0xffffffff : BE_INT(fdcount); 2687 if (lseek64(fd, length_seek, SEEK_SET) == length_seek) 2688 write(fd, &ah.data_size, sizeof(ah.data_size)); 2689 if (fd != 1) 2690 close(fd); 2691 } 2692 2693 static void header(int rtype, char *name) 2694 { 2695 if (!quiet_mode) { 2696 if (! name) 2697 name = (stream == SND_PCM_STREAM_PLAYBACK) ? "stdout" : "stdin"; 2698 fprintf(stderr, "%s %s '%s' : ", 2699 (stream == SND_PCM_STREAM_PLAYBACK) ? _("Playing") : _("Recording"), 2700 gettext(fmt_rec_table[rtype].what), 2701 name); 2702 fprintf(stderr, "%s, ", snd_pcm_format_description(hwparams.format)); 2703 fprintf(stderr, _("Rate %d Hz, "), hwparams.rate); 2704 if (hwparams.channels == 1) 2705 fprintf(stderr, _("Mono")); 2706 else if (hwparams.channels == 2) 2707 fprintf(stderr, _("Stereo")); 2708 else 2709 fprintf(stderr, _("Channels %i"), hwparams.channels); 2710 fprintf(stderr, "\n"); 2711 } 2712 } 2713 2714 /* playing raw data */ 2715 2716 static void playback_go(int fd, size_t loaded, off64_t count, int rtype, char *name) 2717 { 2718 int l, r; 2719 off64_t written = 0; 2720 off64_t c; 2721 2722 header(rtype, name); 2723 set_params(); 2724 2725 while (loaded > chunk_bytes && written < count && !in_aborting) { 2726 if (pcm_write(audiobuf + written, chunk_size) <= 0) 2727 return; 2728 written += chunk_bytes; 2729 loaded -= chunk_bytes; 2730 } 2731 if (written > 0 && loaded > 0) 2732 memmove(audiobuf, audiobuf + written, loaded); 2733 2734 l = loaded; 2735 while (written < count && !in_aborting) { 2736 do { 2737 c = count - written; 2738 if (c > chunk_bytes) 2739 c = chunk_bytes; 2740 c -= l; 2741 2742 if (c == 0) 2743 break; 2744 r = safe_read(fd, audiobuf + l, c); 2745 if (r < 0) { 2746 perror(name); 2747 prg_exit(EXIT_FAILURE); 2748 } 2749 fdcount += r; 2750 if (r == 0) 2751 break; 2752 l += r; 2753 } while ((size_t)l < chunk_bytes); 2754 l = l * 8 / bits_per_frame; 2755 r = pcm_write(audiobuf, l); 2756 if (r != l) 2757 break; 2758 r = r * bits_per_frame / 8; 2759 written += r; 2760 l = 0; 2761 } 2762 snd_pcm_nonblock(handle, 0); 2763 snd_pcm_drain(handle); 2764 snd_pcm_nonblock(handle, nonblock); 2765 } 2766 2767 2768 /* 2769 * let's play or capture it (capture_type says VOC/WAVE/raw) 2770 */ 2771 2772 static void playback(char *name) 2773 { 2774 int ofs; 2775 size_t dta; 2776 ssize_t dtawave; 2777 2778 pbrec_count = LLONG_MAX; 2779 fdcount = 0; 2780 if (!name || !strcmp(name, "-")) { 2781 fd = fileno(stdin); 2782 name = "stdin"; 2783 } else { 2784 init_stdin(); 2785 if ((fd = open(name, O_RDONLY, 0)) == -1) { 2786 perror(name); 2787 prg_exit(EXIT_FAILURE); 2788 } 2789 } 2790 /* read the file header */ 2791 dta = sizeof(AuHeader); 2792 if ((size_t)safe_read(fd, audiobuf, dta) != dta) { 2793 error(_("read error")); 2794 prg_exit(EXIT_FAILURE); 2795 } 2796 if (test_au(fd, audiobuf) >= 0) { 2797 rhwparams.format = hwparams.format; 2798 pbrec_count = calc_count(); 2799 playback_go(fd, 0, pbrec_count, FORMAT_AU, name); 2800 goto __end; 2801 } 2802 dta = sizeof(VocHeader); 2803 if ((size_t)safe_read(fd, audiobuf + sizeof(AuHeader), 2804 dta - sizeof(AuHeader)) != dta - sizeof(AuHeader)) { 2805 error(_("read error")); 2806 prg_exit(EXIT_FAILURE);; 2807 } 2808 if ((ofs = test_vocfile(audiobuf)) >= 0) { 2809 pbrec_count = calc_count(); 2810 voc_play(fd, ofs, name); 2811 goto __end; 2812 } 2813 /* read bytes for WAVE-header */ 2814 if ((dtawave = test_wavefile(fd, audiobuf, dta)) >= 0) { 2815 pbrec_count = calc_count(); 2816 playback_go(fd, dtawave, pbrec_count, FORMAT_WAVE, name); 2817 } else { 2818 /* should be raw data */ 2819 init_raw_data(); 2820 pbrec_count = calc_count(); 2821 playback_go(fd, dta, pbrec_count, FORMAT_RAW, name); 2822 } 2823 __end: 2824 if (fd != 0) 2825 close(fd); 2826 } 2827 2828 /** 2829 * mystrftime 2830 * 2831 * Variant of strftime(3) that supports additional format 2832 * specifiers in the format string. 2833 * 2834 * Parameters: 2835 * 2836 * s - destination string 2837 * max - max number of bytes to write 2838 * userformat - format string 2839 * tm - time information 2840 * filenumber - the number of the file, starting at 1 2841 * 2842 * Returns: number of bytes written to the string s 2843 */ 2844 size_t mystrftime(char *s, size_t max, const char *userformat, 2845 const struct tm *tm, const int filenumber) 2846 { 2847 char formatstring[PATH_MAX] = ""; 2848 char tempstring[PATH_MAX] = ""; 2849 char *format, *tempstr; 2850 const char *pos_userformat; 2851 2852 format = formatstring; 2853 2854 /* if mystrftime is called with userformat = NULL we return a zero length string */ 2855 if (userformat == NULL) { 2856 *s = '\0'; 2857 return 0; 2858 } 2859 2860 for (pos_userformat = userformat; *pos_userformat; ++pos_userformat) { 2861 if (*pos_userformat == '%') { 2862 tempstr = tempstring; 2863 tempstr[0] = '\0'; 2864 switch (*++pos_userformat) { 2865 2866 case '\0': // end of string 2867 --pos_userformat; 2868 break; 2869 2870 case 'v': // file number 2871 sprintf(tempstr, "%02d", filenumber); 2872 break; 2873 2874 default: // All other codes will be handled by strftime 2875 *format++ = '%'; 2876 *format++ = *pos_userformat; 2877 continue; 2878 } 2879 2880 /* If a format specifier was found and used, copy the result. */ 2881 if (tempstr[0]) { 2882 while ((*format = *tempstr++) != '\0') 2883 ++format; 2884 continue; 2885 } 2886 } 2887 2888 /* For any other character than % we simply copy the character */ 2889 *format++ = *pos_userformat; 2890 } 2891 2892 *format = '\0'; 2893 format = formatstring; 2894 return strftime(s, max, format, tm); 2895 } 2896 2897 static int new_capture_file(char *name, char *namebuf, size_t namelen, 2898 int filecount) 2899 { 2900 char *s; 2901 char buf[PATH_MAX+1]; 2902 time_t t; 2903 struct tm *tmp; 2904 2905 if (use_strftime) { 2906 t = time(NULL); 2907 tmp = localtime(&t); 2908 if (tmp == NULL) { 2909 perror("localtime"); 2910 prg_exit(EXIT_FAILURE); 2911 } 2912 if (mystrftime(namebuf, namelen, name, tmp, filecount+1) == 0) { 2913 fprintf(stderr, "mystrftime returned 0"); 2914 prg_exit(EXIT_FAILURE); 2915 } 2916 return filecount; 2917 } 2918 2919 /* get a copy of the original filename */ 2920 strncpy(buf, name, sizeof(buf)); 2921 2922 /* separate extension from filename */ 2923 s = buf + strlen(buf); 2924 while (s > buf && *s != '.' && *s != '/') 2925 --s; 2926 if (*s == '.') 2927 *s++ = 0; 2928 else if (*s == '/') 2929 s = buf + strlen(buf); 2930 2931 /* upon first jump to this if block rename the first file */ 2932 if (filecount == 1) { 2933 if (*s) 2934 snprintf(namebuf, namelen, "%s-01.%s", buf, s); 2935 else 2936 snprintf(namebuf, namelen, "%s-01", buf); 2937 remove(namebuf); 2938 rename(name, namebuf); 2939 filecount = 2; 2940 } 2941 2942 /* name of the current file */ 2943 if (*s) 2944 snprintf(namebuf, namelen, "%s-%02i.%s", buf, filecount, s); 2945 else 2946 snprintf(namebuf, namelen, "%s-%02i", buf, filecount); 2947 2948 return filecount; 2949 } 2950 2951 /** 2952 * create_path 2953 * 2954 * This function creates a file path, like mkdir -p. 2955 * 2956 * Parameters: 2957 * 2958 * path - the path to create 2959 * 2960 * Returns: 0 on success, -1 on failure 2961 * On failure, a message has been printed to stderr. 2962 */ 2963 int create_path(const char *path) 2964 { 2965 char *start; 2966 mode_t mode = S_IRWXU | S_IRGRP | S_IXGRP | S_IROTH | S_IXOTH; 2967 2968 if (path[0] == '/') 2969 start = strchr(path + 1, '/'); 2970 else 2971 start = strchr(path, '/'); 2972 2973 while (start) { 2974 char *buffer = strdup(path); 2975 buffer[start-path] = 0x00; 2976 2977 if (mkdir(buffer, mode) == -1 && errno != EEXIST) { 2978 fprintf(stderr, "Problem creating directory %s", buffer); 2979 perror(" "); 2980 free(buffer); 2981 return -1; 2982 } 2983 free(buffer); 2984 start = strchr(start + 1, '/'); 2985 } 2986 return 0; 2987 } 2988 2989 static int safe_open(const char *name) 2990 { 2991 int fd; 2992 2993 fd = open(name, O_WRONLY | O_CREAT, 0644); 2994 if (fd == -1) { 2995 if (errno != ENOENT || !use_strftime) 2996 return -1; 2997 if (create_path(name) == 0) 2998 fd = open(name, O_WRONLY | O_CREAT, 0644); 2999 } 3000 return fd; 3001 } 3002 3003 static void capture(char *orig_name) 3004 { 3005 int tostdout=0; /* boolean which describes output stream */ 3006 int filecount=0; /* number of files written */ 3007 char *name = orig_name; /* current filename */ 3008 char namebuf[PATH_MAX+1]; 3009 off64_t count, rest; /* number of bytes to capture */ 3010 struct stat statbuf; 3011 3012 /* get number of bytes to capture */ 3013 count = calc_count(); 3014 if (count == 0) 3015 count = LLONG_MAX; 3016 /* compute the number of bytes per file */ 3017 max_file_size = max_file_time * 3018 snd_pcm_format_size(hwparams.format, 3019 hwparams.rate * hwparams.channels); 3020 /* WAVE-file should be even (I'm not sure), but wasting one byte 3021 isn't a problem (this can only be in 8 bit mono) */ 3022 if (count < LLONG_MAX) 3023 count += count % 2; 3024 else 3025 count -= count % 2; 3026 3027 /* display verbose output to console */ 3028 header(file_type, name); 3029 3030 /* setup sound hardware */ 3031 set_params(); 3032 3033 /* write to stdout? */ 3034 if (!name || !strcmp(name, "-")) { 3035 fd = fileno(stdout); 3036 name = "stdout"; 3037 tostdout=1; 3038 if (count > fmt_rec_table[file_type].max_filesize) 3039 count = fmt_rec_table[file_type].max_filesize; 3040 } 3041 init_stdin(); 3042 3043 do { 3044 /* open a file to write */ 3045 if(!tostdout) { 3046 /* upon the second file we start the numbering scheme */ 3047 if (filecount || use_strftime) { 3048 filecount = new_capture_file(orig_name, namebuf, 3049 sizeof(namebuf), 3050 filecount); 3051 name = namebuf; 3052 } 3053 3054 /* open a new file */ 3055 if (!lstat(name, &statbuf)) { 3056 if (S_ISREG(statbuf.st_mode)) 3057 remove(name); 3058 } 3059 fd = safe_open(name); 3060 if (fd < 0) { 3061 perror(name); 3062 prg_exit(EXIT_FAILURE); 3063 } 3064 filecount++; 3065 } 3066 3067 rest = count; 3068 if (rest > fmt_rec_table[file_type].max_filesize) 3069 rest = fmt_rec_table[file_type].max_filesize; 3070 if (max_file_size && (rest > max_file_size)) 3071 rest = max_file_size; 3072 3073 /* setup sample header */ 3074 if (fmt_rec_table[file_type].start) 3075 fmt_rec_table[file_type].start(fd, rest); 3076 3077 /* capture */ 3078 fdcount = 0; 3079 while (rest > 0 && recycle_capture_file == 0 && !in_aborting) { 3080 size_t c = (rest <= (off64_t)chunk_bytes) ? 3081 (size_t)rest : chunk_bytes; 3082 size_t f = c * 8 / bits_per_frame; 3083 if (pcm_read(audiobuf, f) != f) { 3084 in_aborting = 1; 3085 break; 3086 } 3087 if (write(fd, audiobuf, c) != c) { 3088 perror(name); 3089 in_aborting = 1; 3090 break; 3091 } 3092 count -= c; 3093 rest -= c; 3094 fdcount += c; 3095 } 3096 3097 /* re-enable SIGUSR1 signal */ 3098 if (recycle_capture_file) { 3099 recycle_capture_file = 0; 3100 signal(SIGUSR1, signal_handler_recycle); 3101 } 3102 3103 /* finish sample container */ 3104 if (fmt_rec_table[file_type].end && !tostdout) { 3105 fmt_rec_table[file_type].end(fd); 3106 fd = -1; 3107 } 3108 3109 if (in_aborting) 3110 prg_exit(EXIT_FAILURE); 3111 3112 /* repeat the loop when format is raw without timelimit or 3113 * requested counts of data are recorded 3114 */ 3115 } while ((file_type == FORMAT_RAW && !timelimit) || count > 0); 3116 } 3117 3118 static void playbackv_go(int* fds, unsigned int channels, size_t loaded, off64_t count, int rtype, char **names) 3119 { 3120 int r; 3121 size_t vsize; 3122 3123 unsigned int channel; 3124 u_char *bufs[channels]; 3125 3126 header(rtype, names[0]); 3127 set_params(); 3128 3129 vsize = chunk_bytes / channels; 3130 3131 // Not yet implemented 3132 assert(loaded == 0); 3133 3134 for (channel = 0; channel < channels; ++channel) 3135 bufs[channel] = audiobuf + vsize * channel; 3136 3137 while (count > 0 && !in_aborting) { 3138 size_t c = 0; 3139 size_t expected = count / channels; 3140 if (expected > vsize) 3141 expected = vsize; 3142 do { 3143 r = safe_read(fds[0], bufs[0], expected); 3144 if (r < 0) { 3145 perror(names[channel]); 3146 prg_exit(EXIT_FAILURE); 3147 } 3148 for (channel = 1; channel < channels; ++channel) { 3149 if (safe_read(fds[channel], bufs[channel], r) != r) { 3150 perror(names[channel]); 3151 prg_exit(EXIT_FAILURE); 3152 } 3153 } 3154 if (r == 0) 3155 break; 3156 c += r; 3157 } while (c < expected); 3158 c = c * 8 / bits_per_sample; 3159 r = pcm_writev(bufs, channels, c); 3160 if ((size_t)r != c) 3161 break; 3162 r = r * bits_per_frame / 8; 3163 count -= r; 3164 } 3165 snd_pcm_nonblock(handle, 0); 3166 snd_pcm_drain(handle); 3167 snd_pcm_nonblock(handle, nonblock); 3168 } 3169 3170 static void capturev_go(int* fds, unsigned int channels, off64_t count, int rtype, char **names) 3171 { 3172 size_t c; 3173 ssize_t r; 3174 unsigned int channel; 3175 size_t vsize; 3176 u_char *bufs[channels]; 3177 3178 header(rtype, names[0]); 3179 set_params(); 3180 3181 vsize = chunk_bytes / channels; 3182 3183 for (channel = 0; channel < channels; ++channel) 3184 bufs[channel] = audiobuf + vsize * channel; 3185 3186 while (count > 0 && !in_aborting) { 3187 size_t rv; 3188 c = count; 3189 if (c > chunk_bytes) 3190 c = chunk_bytes; 3191 c = c * 8 / bits_per_frame; 3192 if ((size_t)(r = pcm_readv(bufs, channels, c)) != c) 3193 break; 3194 rv = r * bits_per_sample / 8; 3195 for (channel = 0; channel < channels; ++channel) { 3196 if ((size_t)write(fds[channel], bufs[channel], rv) != rv) { 3197 perror(names[channel]); 3198 prg_exit(EXIT_FAILURE); 3199 } 3200 } 3201 r = r * bits_per_frame / 8; 3202 count -= r; 3203 fdcount += r; 3204 } 3205 } 3206 3207 static void playbackv(char **names, unsigned int count) 3208 { 3209 int ret = 0; 3210 unsigned int channel; 3211 unsigned int channels = rhwparams.channels; 3212 int alloced = 0; 3213 int fds[channels]; 3214 for (channel = 0; channel < channels; ++channel) 3215 fds[channel] = -1; 3216 3217 if (count == 1 && channels > 1) { 3218 size_t len = strlen(names[0]); 3219 char format[1024]; 3220 memcpy(format, names[0], len); 3221 strcpy(format + len, ".%d"); 3222 len += 4; 3223 names = malloc(sizeof(*names) * channels); 3224 for (channel = 0; channel < channels; ++channel) { 3225 names[channel] = malloc(len); 3226 sprintf(names[channel], format, channel); 3227 } 3228 alloced = 1; 3229 } else if (count != channels) { 3230 error(_("You need to specify %d files"), channels); 3231 prg_exit(EXIT_FAILURE); 3232 } 3233 3234 for (channel = 0; channel < channels; ++channel) { 3235 fds[channel] = open(names[channel], O_RDONLY, 0); 3236 if (fds[channel] < 0) { 3237 perror(names[channel]); 3238 ret = EXIT_FAILURE; 3239 goto __end; 3240 } 3241 } 3242 /* should be raw data */ 3243 init_raw_data(); 3244 pbrec_count = calc_count(); 3245 playbackv_go(fds, channels, 0, pbrec_count, FORMAT_RAW, names); 3246 3247 __end: 3248 for (channel = 0; channel < channels; ++channel) { 3249 if (fds[channel] >= 0) 3250 close(fds[channel]); 3251 if (alloced) 3252 free(names[channel]); 3253 } 3254 if (alloced) 3255 free(names); 3256 if (ret) 3257 prg_exit(ret); 3258 } 3259 3260 static void capturev(char **names, unsigned int count) 3261 { 3262 int ret = 0; 3263 unsigned int channel; 3264 unsigned int channels = rhwparams.channels; 3265 int alloced = 0; 3266 int fds[channels]; 3267 for (channel = 0; channel < channels; ++channel) 3268 fds[channel] = -1; 3269 3270 if (count == 1) { 3271 size_t len = strlen(names[0]); 3272 char format[1024]; 3273 memcpy(format, names[0], len); 3274 strcpy(format + len, ".%d"); 3275 len += 4; 3276 names = malloc(sizeof(*names) * channels); 3277 for (channel = 0; channel < channels; ++channel) { 3278 names[channel] = malloc(len); 3279 sprintf(names[channel], format, channel); 3280 } 3281 alloced = 1; 3282 } else if (count != channels) { 3283 error(_("You need to specify %d files"), channels); 3284 prg_exit(EXIT_FAILURE); 3285 } 3286 3287 for (channel = 0; channel < channels; ++channel) { 3288 fds[channel] = open(names[channel], O_WRONLY + O_CREAT, 0644); 3289 if (fds[channel] < 0) { 3290 perror(names[channel]); 3291 ret = EXIT_FAILURE; 3292 goto __end; 3293 } 3294 } 3295 /* should be raw data */ 3296 init_raw_data(); 3297 pbrec_count = calc_count(); 3298 capturev_go(fds, channels, pbrec_count, FORMAT_RAW, names); 3299 3300 __end: 3301 for (channel = 0; channel < channels; ++channel) { 3302 if (fds[channel] >= 0) 3303 close(fds[channel]); 3304 if (alloced) 3305 free(names[channel]); 3306 } 3307 if (alloced) 3308 free(names); 3309 if (ret) 3310 prg_exit(ret); 3311 }